Skip to content

Commit 3d13051

Browse files
committed
Initial bun testing implementation (blocked by oven-sh/bun#198)
1 parent 0df92fc commit 3d13051

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

56 files changed

+1975
-14
lines changed

benchmarks/bun/bunfig.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
[test]
2+
preload = ["./helpers/happydom.ts"]

benchmarks/bun/helpers/happydom.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
import { GlobalRegistrator } from "@happy-dom/global-registrator";
2+
3+
GlobalRegistrator.register();

benchmarks/bun/package.json

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
{
2+
"name": "bun",
3+
"version": "0.2.0",
4+
"description": "",
5+
"scripts": {
6+
"test": "TZ=UTC bun test"
7+
},
8+
"author": "",
9+
"license": "MIT",
10+
"dependencies": {
11+
"@blueprintjs/icons": "4.6.3",
12+
"@floating-ui/react-dom-interactions": "0.10.1",
13+
"clsx": "1.2.1",
14+
"date-fns": "2.29.3",
15+
"framer-motion": "7.5.3",
16+
"react": "18.2.0",
17+
"react-dom": "18.2.0"
18+
},
19+
"devDependencies": {
20+
"@happy-dom/global-registrator": "9.19.2",
21+
"happy-dom": "7.4.0",
22+
"jsdom": "22.0.0",
23+
"sinon": "15.1.0"
24+
}
25+
}

benchmarks/bun/tests/.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
replica*
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
.main {
2+
border: 1px solid transparent;
3+
border-radius: 8px;
4+
display: flex;
5+
font-size: 14px;
6+
padding: 16px;
7+
}
8+
9+
.error {
10+
background: var(--R50);
11+
border-color: var(--R400);
12+
color: var(--R400);
13+
}
14+
15+
/* stylelint-disable-next-line selector-max-type, selector-max-combinators */
16+
.error a, .error strong { color: inherit }
17+
18+
.info {
19+
background: var(--N50);
20+
border-color: var(--N400);
21+
color: var(--N400);
22+
}
23+
24+
/* stylelint-disable-next-line selector-max-type, selector-max-combinators */
25+
.info a, .info strong { color: inherit }
26+
27+
.success {
28+
background: var(--G50);
29+
border-color: var(--G400);
30+
color: var(--G400);
31+
}
32+
33+
/* stylelint-disable-next-line selector-max-type, selector-max-combinators */
34+
.success a, .success strong { color: inherit }
35+
36+
.warning {
37+
background: var(--Y50);
38+
border-color: var(--Y400);
39+
color: var(--Y500);
40+
}
41+
42+
/* stylelint-disable-next-line selector-max-type, selector-max-combinators */
43+
.warning a, .warning strong { color: inherit }
44+
45+
.icon {
46+
margin-right: 16px;
47+
}
48+
49+
.title {
50+
color: inherit;
51+
font-weight: bold;
52+
margin: 0 0 8px;
53+
}
54+
55+
.text {
56+
display: flex;
57+
flex-direction: column;
58+
}
59+
60+
.children { color: var(--COLOR-GRAY-800) }
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import Alert from '.';
2+
import {cleanup, render} from '@testing-library/react';
3+
import {afterEach, describe, expect, it} from "bun:test";
4+
import React from 'react';
5+
6+
describe('<Alert />', () => {
7+
// Ideally Bun can give us a way to set this globally
8+
afterEach(cleanup);
9+
10+
it('should render the given message', () => {
11+
const {getByText} = render(<Alert>Hello World</Alert>);
12+
expect(getByText('Hello World')).toBeDefined();
13+
});
14+
15+
it('should render with only a title', () => {
16+
const {getByText} = render(<Alert title='Hello World' />);
17+
expect(getByText('Hello World')).toBeDefined();
18+
});
19+
20+
it('should support all the different icons', () => {
21+
const {getByLabelText, rerender} = render(<Alert intent='warning' />);
22+
expect(getByLabelText('warning-sign')).toBeDefined();
23+
24+
rerender(<Alert intent='info' />)
25+
expect(getByLabelText('info-sign')).toBeDefined();
26+
27+
rerender(<Alert intent='success' />)
28+
expect(getByLabelText('tick-circle')).toBeDefined();
29+
});
30+
});
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import Icon, {IconNames} from '../Icon';
2+
import clsx from 'clsx';
3+
import React from 'react';
4+
import styles from './Alert.module.css';
5+
6+
type IntentType = 'error' | 'info' | 'success' | 'warning';
7+
8+
type PropsType = {
9+
className?: string | null,
10+
children?: React.ReactNode,
11+
intent?: IntentType,
12+
title?: string | null,
13+
}
14+
15+
const getIcon = (intent: IntentType) => {
16+
switch (intent) {
17+
case 'info': return IconNames.InfoSign;
18+
case 'success': return IconNames.TickCircle;
19+
case 'warning': return IconNames.WarningSign;
20+
case 'error': return IconNames.Error;
21+
}
22+
return IconNames.Error;
23+
};
24+
25+
const Alert = ({
26+
className,
27+
children,
28+
intent = 'error',
29+
title,
30+
}: PropsType) => {
31+
const classes = clsx(styles.main, styles[intent], className);
32+
33+
return (
34+
<div className={classes} role='alert'>
35+
<Icon
36+
className={styles.icon}
37+
name={getIcon(intent)} />
38+
<div className={styles.text}>
39+
{title ? <h4 className={styles.title}>{title}</h4> : null}
40+
{children ? (
41+
<div className={styles.children}>{children}</div>
42+
) : null}
43+
</div>
44+
</div>
45+
);
46+
};
47+
48+
export default Alert;
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export {default} from './Alert';
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
.main {
2+
align-items: center;
3+
border-radius: 100%;
4+
display: inline-flex;
5+
font-size: 15px;
6+
height: 40px;
7+
justify-content: center;
8+
width: 40px;
9+
}
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
import Avatar from '.';
2+
import {cleanup, render} from '@testing-library/react';
3+
import {afterEach, describe, expect, it} from "bun:test";
4+
import React from 'react';
5+
6+
describe('<Avatar />', () => {
7+
// Ideally Bun can give us a way to set this globally
8+
afterEach(cleanup);
9+
10+
it('should render the avatar with the initials of the title', () => {
11+
const {getByText} = render(<Avatar title='Hello World' />);
12+
expect(getByText('HW')).toBeDefined();
13+
});
14+
});
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
import clsx from 'clsx';
2+
import React from 'react';
3+
import styles from './Avatar.module.css';
4+
5+
type PropsType = {
6+
className?: string | null,
7+
colorKey?: SupportedColorsType | null,
8+
title?: string | null,
9+
}
10+
11+
type SupportedColorsType = typeof SUPPORTED_COLORS[number];
12+
13+
const SUPPORTED_COLORS = [
14+
'N', 'B', 'G', 'Y', 'R', 'V', 'T', 'P', 'O',
15+
] as const;
16+
17+
const stringToColorIndex = (str: string) => {
18+
// This gives us a number between 0 and 41
19+
const chr = (str.length ? str.charCodeAt(0) : 0) - 49;
20+
21+
// This gives us an index in our supported color range
22+
return Math.floor(chr / (41 / SUPPORTED_COLORS.length));
23+
};
24+
25+
const getColor = (initials: string, colorKey?: string | null) => {
26+
const colorIndex = stringToColorIndex(initials);
27+
const key = colorKey || SUPPORTED_COLORS[colorIndex];
28+
const background = `var(--${key}100)`;
29+
const color = `var(--${key}600)`;
30+
return {background, color};
31+
};
32+
33+
const Avatar = ({
34+
className,
35+
colorKey,
36+
title,
37+
}: PropsType) => {
38+
const classes = clsx(styles.main, className);
39+
const initials = title?.length ?
40+
title
41+
.trim()
42+
.split(' ')
43+
.map((word) => word[0].toUpperCase())
44+
.slice(0, 2)
45+
.join('') :
46+
null;
47+
const {background, color} = getColor(initials || '', colorKey);
48+
const style = {background, color};
49+
50+
return (
51+
<div
52+
className={classes}
53+
style={style}
54+
title={title || ''}>
55+
{initials}
56+
</div>
57+
);
58+
};
59+
60+
export default Avatar;
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export {default} from './Avatar';
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
.main {
2+
align-items: center;
3+
border-radius: 4px;
4+
display: inline-flex;
5+
font-size: 11px;
6+
height: 16px;
7+
padding: 0 6px;
8+
}
9+
10+
.blue {
11+
background: var(--B200);
12+
color: var(--B600);
13+
}
14+
15+
.green {
16+
background: var(--G300);
17+
color: var(--G600);
18+
}
19+
20+
.neutral {
21+
background: var(--N300);
22+
color: var(--N800);
23+
}
24+
25+
.orange {
26+
background: var(--O200);
27+
color: var(--O600);
28+
}
29+
30+
.purple {
31+
background: var(--P200);
32+
color: var(--P600);
33+
}
34+
35+
.red {
36+
background: var(--R200);
37+
color: var(--R600);
38+
}
39+
40+
.turquoise {
41+
background: var(--T200);
42+
color: var(--T600);
43+
}
44+
45+
.violet {
46+
background: var(--V200);
47+
color: var(--V600);
48+
}
49+
50+
.yellow {
51+
background: var(--Y200);
52+
color: var(--Y600);
53+
}
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
import Badge from '.';
2+
import {cleanup, render} from '@testing-library/react';
3+
import {afterEach, describe, expect, it} from "bun:test";
4+
import React from 'react';
5+
6+
describe('<Badge />', () => {
7+
// Ideally Bun can give us a way to set this globally
8+
afterEach(cleanup);
9+
10+
it('should render the given badge', () => {
11+
const {getByText} = render(<Badge>Hello World</Badge>);
12+
expect(getByText('Hello World')).toBeDefined();
13+
});
14+
});
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
import clsx from 'clsx';
2+
import React from 'react';
3+
import styles from './Badge.module.css';
4+
5+
type PropsType = {
6+
className?: string | null,
7+
children: string,
8+
color?: 'blue' | 'green' | 'neutral' | 'orange' | 'purple' | 'red' | 'turquoise' | 'violet' | 'yellow',
9+
}
10+
11+
const Badge = ({
12+
className,
13+
children,
14+
color = 'neutral',
15+
}: PropsType) => (
16+
<strong
17+
className={clsx(styles.main, styles[color], className)}
18+
title={children}>
19+
{children}
20+
</strong>
21+
);
22+
23+
export default Badge;
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export {default} from './Badge';

0 commit comments

Comments
 (0)