@happy-dom/jest-environment 9.20.3 → 10.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintrc.cjs +1 -0
- package/.prettierrc.cjs +1 -0
- package/README.md +7 -37
- package/package.json +7 -5
- package/tsconfig.json +2 -6
- package/.eslintrc.js +0 -1
- package/.prettierrc.js +0 -1
- package/test/angular/Angular.test.ts +0 -23
- package/test/angular/AngularComponent.ts +0 -9
- package/test/angular/AngularModule.ts +0 -13
- package/test/javascript/JavaScript.test.ts +0 -140
- package/test/jquery/JQuery.test.ts +0 -28
- package/test/lit-element/LitElement.test.ts +0 -40
- package/test/lit-element/LitElementComponent.ts +0 -24
- package/test/react/React.test.tsx +0 -46
- package/test/react/ReactComponents.tsx +0 -75
- package/test/testing-library/TestingLibrary.test.tsx +0 -59
- package/test/tsconfig.json +0 -41
- package/test/vue/Vue.test.ts +0 -28
package/.eslintrc.cjs
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
module.exports = require('happy-dom/.eslintrc.cjs');
|
package/.prettierrc.cjs
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
module.exports = require('../happy-dom/.prettierrc.cjs');
|
package/README.md
CHANGED
@@ -38,6 +38,10 @@ And much more..
|
|
38
38
|
|
39
39
|
- [Vue](https://vuejs.org/)
|
40
40
|
|
41
|
+
### Module Systems
|
42
|
+
|
43
|
+
- [CommonJS](https://nodejs.org/api/modules.html#modules-commonjs-modules) (ESM is not supported due to limitations with Jest)
|
44
|
+
|
41
45
|
# Installation
|
42
46
|
|
43
47
|
```bash
|
@@ -91,43 +95,9 @@ Jest uses `node` as test environment by default. In order to tell Jest to use a
|
|
91
95
|
|
92
96
|
3. Save the file.
|
93
97
|
|
94
|
-
#
|
95
|
-
|
96
|
-
Happy DOM exposes two functions that may be useful when testing asynchrounous code.
|
97
|
-
|
98
|
-
**whenAsyncComplete()**
|
99
|
-
|
100
|
-
Returns a [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) that is resolved when all async tasks has been completed.
|
101
|
-
|
102
|
-
```javascript
|
103
|
-
describe('scrollToTop()', () => {
|
104
|
-
it('scrolls to top using the built in browser animation', async () => {
|
105
|
-
element.scrollToTop();
|
106
|
-
|
107
|
-
// Waits for asynchronous tasks like setTimeout(), requestAnimationFrame() etc. to complete
|
108
|
-
await happyDOM.whenAsyncComplete();
|
98
|
+
# Documentation
|
109
99
|
|
110
|
-
|
111
|
-
});
|
112
|
-
});
|
113
|
-
```
|
114
|
-
|
115
|
-
**cancelAsync()**
|
116
|
-
|
117
|
-
This method will cancel all running async tasks.
|
118
|
-
|
119
|
-
```javascript
|
120
|
-
describe('runAnimation()', () => {
|
121
|
-
it('runs animation', () => {
|
122
|
-
element.runAnimation();
|
123
|
-
|
124
|
-
// Cancels all asynchronous tasks like setTimeout(), requestAnimationFrame() etc.
|
125
|
-
happyDOM.cancelAsync();
|
126
|
-
|
127
|
-
expect(element.animationCompleted).toBe(true);
|
128
|
-
});
|
129
|
-
});
|
130
|
-
```
|
100
|
+
Read more about how Happy DOM works in our [documentation](https://github.com/capricorn86/happy-dom/wiki).
|
131
101
|
|
132
102
|
# Performance
|
133
103
|
|
@@ -143,7 +113,7 @@ describe('runAnimation()', () => {
|
|
143
113
|
| querySelectorAll('[class~="name"]') | 5.5 ms | 2.9 ms |
|
144
114
|
| querySelectorAll(':nth-child(2n+1)') | 10.4 ms | 3.8 ms |
|
145
115
|
|
146
|
-
|
116
|
+
See how the test was done [here](https://github.com/capricorn86/happy-dom-performance-test)
|
147
117
|
|
148
118
|
# Sponsors
|
149
119
|
|
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "@happy-dom/jest-environment",
|
3
|
-
"version": "
|
3
|
+
"version": "10.0.1",
|
4
4
|
"license": "MIT",
|
5
5
|
"homepage": "https://github.com/capricorn86/happy-dom/tree/master/packages/jest-environment",
|
6
6
|
"repository": "https://github.com/capricorn86/happy-dom",
|
@@ -54,7 +54,7 @@
|
|
54
54
|
"@jest/types": "^29.4.0",
|
55
55
|
"jest-mock": "^29.4.0",
|
56
56
|
"jest-util": "^29.4.0",
|
57
|
-
"happy-dom": "^
|
57
|
+
"happy-dom": "^10.0.1"
|
58
58
|
},
|
59
59
|
"devDependencies": {
|
60
60
|
"@typescript-eslint/eslint-plugin": "^5.16.0",
|
@@ -64,19 +64,20 @@
|
|
64
64
|
"@testing-library/react": "^12.1.2",
|
65
65
|
"@testing-library/user-event": "^14.4.3",
|
66
66
|
"@types/react-dom": "^17.0.2",
|
67
|
+
"@types/jest": "29.5.2",
|
67
68
|
"eslint": "^8.11.0",
|
68
69
|
"eslint-config-prettier": "^8.5.0",
|
69
70
|
"eslint-plugin-prettier": "^4.0.0",
|
70
71
|
"eslint-plugin-filenames": "^1.3.2",
|
71
|
-
"eslint-plugin-import": "^2.
|
72
|
+
"eslint-plugin-import": "^2.27.5",
|
72
73
|
"eslint-plugin-jest": "^26.1.2",
|
73
74
|
"eslint-plugin-jsdoc": "^38.0.6",
|
74
75
|
"eslint-plugin-json": "^3.1.0",
|
75
76
|
"eslint-plugin-turbo": "^0.0.7",
|
76
77
|
"prettier": "^2.6.0",
|
77
|
-
"typescript": "^
|
78
|
+
"typescript": "^5.0.4",
|
78
79
|
"jest": "^29.4.0",
|
79
|
-
"ts-jest": "^29.
|
80
|
+
"ts-jest": "^29.1.1",
|
80
81
|
"react": "^17.0.2",
|
81
82
|
"react-dom": "^17.0.2",
|
82
83
|
"vue": "^3.2.31",
|
@@ -89,6 +90,7 @@
|
|
89
90
|
"@angular/platform-browser": "^10.0.7",
|
90
91
|
"@angular/compiler": "^10.0.7",
|
91
92
|
"@angular/common": "^10.0.7",
|
93
|
+
"rxjs": "^6.5.3",
|
92
94
|
"jquery": "^3.6.0",
|
93
95
|
"zone.js": "^0.10.3",
|
94
96
|
"glob": "^7.2.0",
|
package/tsconfig.json
CHANGED
@@ -21,20 +21,16 @@
|
|
21
21
|
"baseUrl": ".",
|
22
22
|
"composite": true,
|
23
23
|
"incremental": true,
|
24
|
-
"jsx": "react",
|
25
24
|
"types": [
|
26
25
|
"node"
|
27
26
|
],
|
28
27
|
"lib": [
|
29
|
-
"
|
30
|
-
"es2016",
|
31
|
-
"es2017",
|
28
|
+
"es2020",
|
32
29
|
"dom"
|
33
30
|
]
|
34
31
|
},
|
35
32
|
"include": [
|
36
33
|
"@types/node",
|
37
|
-
"src"
|
38
|
-
"src/**/*.json"
|
34
|
+
"src"
|
39
35
|
]
|
40
36
|
}
|
package/.eslintrc.js
DELETED
@@ -1 +0,0 @@
|
|
1
|
-
module.exports = require('happy-dom/.eslintrc');
|
package/.prettierrc.js
DELETED
@@ -1 +0,0 @@
|
|
1
|
-
module.exports = require('../happy-dom/.prettierrc.js');
|
@@ -1,23 +0,0 @@
|
|
1
|
-
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
|
2
|
-
import { enableProdMode } from '@angular/core';
|
3
|
-
import 'zone.js';
|
4
|
-
import AngularModule from './AngularModule';
|
5
|
-
|
6
|
-
describe('React', () => {
|
7
|
-
let appElement: Element;
|
8
|
-
|
9
|
-
beforeEach(() => {
|
10
|
-
appElement = document.createElement('app');
|
11
|
-
document.body.appendChild(appElement);
|
12
|
-
});
|
13
|
-
|
14
|
-
afterEach(() => {
|
15
|
-
document.body.removeChild(appElement);
|
16
|
-
});
|
17
|
-
|
18
|
-
it('Tests integration with Angular.', async () => {
|
19
|
-
enableProdMode();
|
20
|
-
await platformBrowserDynamic().bootstrapModule(AngularModule);
|
21
|
-
expect(appElement.innerHTML).toBe('<div>Test</div>');
|
22
|
-
});
|
23
|
-
});
|
@@ -1,13 +0,0 @@
|
|
1
|
-
import { NgModule } from '@angular/core';
|
2
|
-
import { BrowserModule } from '@angular/platform-browser';
|
3
|
-
import AngularComponent from './AngularComponent';
|
4
|
-
|
5
|
-
/**
|
6
|
-
*
|
7
|
-
*/
|
8
|
-
@NgModule({
|
9
|
-
imports: [BrowserModule],
|
10
|
-
declarations: [AngularComponent],
|
11
|
-
bootstrap: [AngularComponent]
|
12
|
-
})
|
13
|
-
export default class AngularModule {}
|
@@ -1,140 +0,0 @@
|
|
1
|
-
import Express from 'express';
|
2
|
-
|
3
|
-
describe('JavaScript', () => {
|
4
|
-
it('Functions should have the constructor global.Function', () => {
|
5
|
-
expect((() => {}).constructor).toBe(Function);
|
6
|
-
});
|
7
|
-
|
8
|
-
it('Object should have the constructor global.Object', () => {
|
9
|
-
expect({}.constructor).toBe(Object);
|
10
|
-
});
|
11
|
-
|
12
|
-
it('Can perform a real fetch()', async () => {
|
13
|
-
const express = Express();
|
14
|
-
|
15
|
-
express.get('/get/json', (_req, res) => {
|
16
|
-
res.set('Content-Type', 'application/json');
|
17
|
-
res.send('{ "key1": "value1" }');
|
18
|
-
});
|
19
|
-
|
20
|
-
const server = express.listen(3000);
|
21
|
-
|
22
|
-
const response = await fetch('http://localhost:3000/get/json');
|
23
|
-
|
24
|
-
server.close();
|
25
|
-
|
26
|
-
expect(response.headers.get('content-type')).toBe('application/json; charset=utf-8');
|
27
|
-
expect(response.ok).toBe(true);
|
28
|
-
expect(response.status).toBe(200);
|
29
|
-
expect(response.statusText).toBe('OK');
|
30
|
-
expect(response.url).toBe('http://localhost:3000/get/json');
|
31
|
-
expect(response.redirected).toBe(false);
|
32
|
-
|
33
|
-
const json = await response.json();
|
34
|
-
|
35
|
-
expect(json.key1).toBe('value1');
|
36
|
-
});
|
37
|
-
|
38
|
-
it('Can perform a real FormData post request using fetch()', async () => {
|
39
|
-
const express = Express();
|
40
|
-
|
41
|
-
express.post('/post/formdata', (req, res) => {
|
42
|
-
let body = '';
|
43
|
-
res.set('Content-Type', 'text/html');
|
44
|
-
req.on('data', function (chunk) {
|
45
|
-
body += chunk.toString();
|
46
|
-
});
|
47
|
-
req.on('end', function () {
|
48
|
-
res.send(`header:\n${req.headers['content-type']}\n\nbody:\n${body}`);
|
49
|
-
});
|
50
|
-
});
|
51
|
-
|
52
|
-
const server = express.listen(3000);
|
53
|
-
|
54
|
-
const requestFormData = new FormData();
|
55
|
-
|
56
|
-
requestFormData.append('key1', 'value1');
|
57
|
-
requestFormData.append('key2', 'value2');
|
58
|
-
|
59
|
-
const response = await fetch('http://localhost:3000/post/formdata', {
|
60
|
-
method: 'POST',
|
61
|
-
body: requestFormData
|
62
|
-
});
|
63
|
-
|
64
|
-
expect(response.headers.get('content-type')).toBe('text/html; charset=utf-8');
|
65
|
-
expect(response.ok).toBe(true);
|
66
|
-
expect(response.status).toBe(200);
|
67
|
-
expect(response.statusText).toBe('OK');
|
68
|
-
expect(response.url).toBe('http://localhost:3000/post/formdata');
|
69
|
-
expect(response.redirected).toBe(false);
|
70
|
-
|
71
|
-
const text = await response.text();
|
72
|
-
|
73
|
-
server.close();
|
74
|
-
|
75
|
-
expect(
|
76
|
-
text.replace(
|
77
|
-
/\-\-\-\-HappyDOMFormDataBoundary0\.[a-zA-Z0-9]+/gm,
|
78
|
-
'----HappyDOMFormDataBoundary0.noRandom'
|
79
|
-
)
|
80
|
-
).toBe(
|
81
|
-
'header:\nmultipart/form-data; boundary=----HappyDOMFormDataBoundary0.noRandom\n\nbody:\n------HappyDOMFormDataBoundary0.noRandom\r\nContent-Disposition: form-data; name="key1"\r\n\r\nvalue1\r\n------HappyDOMFormDataBoundary0.noRandom\r\nContent-Disposition: form-data; name="key2"\r\n\r\nvalue2\r\n'
|
82
|
-
);
|
83
|
-
});
|
84
|
-
|
85
|
-
it('Can perform a real asynchronous XMLHttpRequest request', (done) => {
|
86
|
-
const express = Express();
|
87
|
-
|
88
|
-
express.get('/get/json', (_req, res) => {
|
89
|
-
res.set('Content-Type', 'application/json');
|
90
|
-
res.send('{ "key1": "value1" }');
|
91
|
-
});
|
92
|
-
|
93
|
-
const server = express.listen(3000);
|
94
|
-
|
95
|
-
const request = new XMLHttpRequest();
|
96
|
-
|
97
|
-
request.open('GET', 'http://localhost:3000/get/json', true);
|
98
|
-
|
99
|
-
request.addEventListener('load', () => {
|
100
|
-
expect(request.getResponseHeader('content-type')).toBe('application/json; charset=utf-8');
|
101
|
-
expect(request.responseText).toBe('{ "key1": "value1" }');
|
102
|
-
expect(request.status).toBe(200);
|
103
|
-
expect(request.statusText).toBe('OK');
|
104
|
-
expect(request.responseURL).toBe('http://localhost:3000/get/json');
|
105
|
-
|
106
|
-
server.close();
|
107
|
-
|
108
|
-
done();
|
109
|
-
});
|
110
|
-
|
111
|
-
request.send();
|
112
|
-
});
|
113
|
-
|
114
|
-
it('Can perform a real synchronous XMLHttpRequest request to Github.com', () => {
|
115
|
-
const request = new XMLHttpRequest();
|
116
|
-
|
117
|
-
request.open(
|
118
|
-
'GET',
|
119
|
-
'https://raw.githubusercontent.com/capricorn86/happy-dom/master/.gitignore',
|
120
|
-
false
|
121
|
-
);
|
122
|
-
|
123
|
-
request.send();
|
124
|
-
|
125
|
-
expect(request.getResponseHeader('content-type')).toBe('text/plain; charset=utf-8');
|
126
|
-
expect(request.responseText.includes('node_modules')).toBe(true);
|
127
|
-
expect(request.status).toBe(200);
|
128
|
-
expect(request.statusText).toBe('OK');
|
129
|
-
expect(request.responseURL).toBe(
|
130
|
-
'https://raw.githubusercontent.com/capricorn86/happy-dom/master/.gitignore'
|
131
|
-
);
|
132
|
-
});
|
133
|
-
|
134
|
-
it('Binds global methods to the Window context', () => {
|
135
|
-
const eventListener = (): void => {};
|
136
|
-
addEventListener('click', eventListener);
|
137
|
-
removeEventListener('click', eventListener);
|
138
|
-
clearTimeout(setTimeout(eventListener));
|
139
|
-
});
|
140
|
-
});
|
@@ -1,28 +0,0 @@
|
|
1
|
-
import JQuery from 'jquery';
|
2
|
-
|
3
|
-
describe('JQuery', () => {
|
4
|
-
beforeEach(() => {
|
5
|
-
document.body.innerHTML = `
|
6
|
-
<div class="class1 class2" id="id">
|
7
|
-
<!-- Comment 1 !-->
|
8
|
-
<b>Bold</b>
|
9
|
-
<!-- Comment 2 !-->
|
10
|
-
<span>Span</span>
|
11
|
-
</div>
|
12
|
-
<article class="class1 class2" id="id">
|
13
|
-
<!-- Comment 1 !-->
|
14
|
-
<b>Bold</b>
|
15
|
-
<!-- Comment 2 !-->
|
16
|
-
</article>
|
17
|
-
`;
|
18
|
-
});
|
19
|
-
|
20
|
-
afterEach(() => {
|
21
|
-
document.body.innerHTML = '';
|
22
|
-
});
|
23
|
-
|
24
|
-
it('Tests integration.', () => {
|
25
|
-
JQuery('span').addClass('test-span');
|
26
|
-
expect(document.body.children[0].children[1].getAttribute('class')).toBe('test-span');
|
27
|
-
});
|
28
|
-
});
|
@@ -1,40 +0,0 @@
|
|
1
|
-
import LitElementComponent from './LitElementComponent';
|
2
|
-
import './LitElementComponent';
|
3
|
-
|
4
|
-
const PROP1 = 'PROP1';
|
5
|
-
|
6
|
-
describe('LitElementComponent', () => {
|
7
|
-
beforeEach(() => {
|
8
|
-
document.body.innerHTML = `<lit-element-component prop1="${PROP1}"></lit-element-component>`;
|
9
|
-
});
|
10
|
-
|
11
|
-
afterEach(() => {
|
12
|
-
document.body.innerHTML = '';
|
13
|
-
});
|
14
|
-
|
15
|
-
it('Tests integration.', () => {
|
16
|
-
const litElement = <LitElementComponent>document.body.querySelector('lit-element-component');
|
17
|
-
const shadowRoot = litElement.shadowRoot;
|
18
|
-
|
19
|
-
expect(document.body.innerHTML).toBe(
|
20
|
-
`<lit-element-component prop1="${PROP1}"></lit-element-component>`
|
21
|
-
);
|
22
|
-
|
23
|
-
expect(shadowRoot.querySelector('span').innerText).toBe(PROP1);
|
24
|
-
expect(
|
25
|
-
shadowRoot.innerHTML
|
26
|
-
.replace(/[\s]/gm, '')
|
27
|
-
.replace(/<!--\?lit\$[0-9]+\$-->/gm, '<!--?lit$123456$-->')
|
28
|
-
).toBe(
|
29
|
-
`
|
30
|
-
<!---->Some text
|
31
|
-
<span><!--?lit$123456$-->${PROP1}</span>!
|
32
|
-
<style>
|
33
|
-
span {
|
34
|
-
color: green;
|
35
|
-
}
|
36
|
-
</style>
|
37
|
-
`.replace(/[\s]/gm, '')
|
38
|
-
);
|
39
|
-
});
|
40
|
-
});
|
@@ -1,24 +0,0 @@
|
|
1
|
-
import { LitElement, TemplateResult, html, css, CSSResult } from '../../lib/node_modules/lit';
|
2
|
-
import { customElement, property } from '../../lib/node_modules/lit/decorators';
|
3
|
-
|
4
|
-
/**
|
5
|
-
*
|
6
|
-
*/
|
7
|
-
@customElement('lit-element-component')
|
8
|
-
export default class LitElementComponent extends LitElement {
|
9
|
-
public static styles: CSSResult = css`
|
10
|
-
span {
|
11
|
-
color: green;
|
12
|
-
}
|
13
|
-
`;
|
14
|
-
|
15
|
-
@property({ type: String })
|
16
|
-
public prop1: string = null;
|
17
|
-
|
18
|
-
/**
|
19
|
-
* Renders the component.
|
20
|
-
*/
|
21
|
-
public render(): TemplateResult {
|
22
|
-
return html` Some text <span>${this.prop1}</span>! `;
|
23
|
-
}
|
24
|
-
}
|
@@ -1,46 +0,0 @@
|
|
1
|
-
import React from 'react';
|
2
|
-
import ReactDOM from 'react-dom';
|
3
|
-
import * as ReactTestingLibrary from '@testing-library/react';
|
4
|
-
import ReactTestingLibraryUserEvent from '@testing-library/user-event';
|
5
|
-
import { ReactDivComponent, ReactSelectComponent, ReactInputComponent } from './ReactComponents';
|
6
|
-
|
7
|
-
/* eslint-disable @typescript-eslint/consistent-type-assertions */
|
8
|
-
|
9
|
-
const TESTING_LIBRARY_USER = ReactTestingLibraryUserEvent.setup();
|
10
|
-
|
11
|
-
describe('React', () => {
|
12
|
-
let appElement: Element;
|
13
|
-
|
14
|
-
beforeEach(() => {
|
15
|
-
appElement = document.createElement('app');
|
16
|
-
document.body.appendChild(appElement);
|
17
|
-
});
|
18
|
-
|
19
|
-
afterEach(() => {
|
20
|
-
document.body.removeChild(appElement);
|
21
|
-
});
|
22
|
-
|
23
|
-
it('Tests integration.', () => {
|
24
|
-
ReactDOM.render(<ReactDivComponent />, appElement);
|
25
|
-
expect(appElement.innerHTML).toBe('<div>Test</div>');
|
26
|
-
});
|
27
|
-
|
28
|
-
it('Can unmount a component.', () => {
|
29
|
-
ReactDOM.render(<ReactDivComponent />, appElement);
|
30
|
-
ReactDOM.unmountComponentAtNode(appElement);
|
31
|
-
expect(appElement.innerHTML).toBe('');
|
32
|
-
});
|
33
|
-
|
34
|
-
it('Handles adding and removing event listeners.', () => {
|
35
|
-
ReactDOM.render(<ReactSelectComponent onChange={() => {}} />, appElement);
|
36
|
-
});
|
37
|
-
|
38
|
-
it('Testing library handles input', async () => {
|
39
|
-
const { getByPlaceholderText } = ReactTestingLibrary.render(<ReactInputComponent />);
|
40
|
-
const input: HTMLInputElement = getByPlaceholderText('input field') as HTMLInputElement;
|
41
|
-
|
42
|
-
await TESTING_LIBRARY_USER.type(input, 'hello');
|
43
|
-
|
44
|
-
expect(input.value).toBe('hello');
|
45
|
-
});
|
46
|
-
});
|
@@ -1,75 +0,0 @@
|
|
1
|
-
import React from 'react';
|
2
|
-
|
3
|
-
/* eslint-disable @typescript-eslint/consistent-type-assertions */
|
4
|
-
|
5
|
-
/**
|
6
|
-
*
|
7
|
-
*/
|
8
|
-
export class ReactDivComponent extends React.Component<{}, {}> {
|
9
|
-
public $props = {};
|
10
|
-
|
11
|
-
/**
|
12
|
-
* @override
|
13
|
-
*/
|
14
|
-
public render(): React.ReactElement {
|
15
|
-
return <div>Test</div>;
|
16
|
-
}
|
17
|
-
}
|
18
|
-
|
19
|
-
const OPTIONS = [
|
20
|
-
{ value: 't1', label: 'test 1' },
|
21
|
-
{ value: 't2', label: 'test 2' }
|
22
|
-
];
|
23
|
-
|
24
|
-
/**
|
25
|
-
*
|
26
|
-
*/
|
27
|
-
export class ReactSelectComponent extends React.Component<
|
28
|
-
{
|
29
|
-
value?: string;
|
30
|
-
onChange?: (value: string) => void;
|
31
|
-
},
|
32
|
-
{}
|
33
|
-
> {
|
34
|
-
public $props = {
|
35
|
-
value: OPTIONS[0].value,
|
36
|
-
onChange: null
|
37
|
-
};
|
38
|
-
|
39
|
-
/**
|
40
|
-
* @override
|
41
|
-
*/
|
42
|
-
public render(): React.ReactElement {
|
43
|
-
return (
|
44
|
-
<select
|
45
|
-
value={this.props.value}
|
46
|
-
onChange={
|
47
|
-
this.props.onChange
|
48
|
-
? (event: React.ChangeEvent) =>
|
49
|
-
this.props.onChange((event.target as HTMLSelectElement).value)
|
50
|
-
: undefined
|
51
|
-
}
|
52
|
-
>
|
53
|
-
{OPTIONS.map((option) => (
|
54
|
-
<option key={option.value} value={option.value}>
|
55
|
-
{option.label}
|
56
|
-
</option>
|
57
|
-
))}
|
58
|
-
</select>
|
59
|
-
);
|
60
|
-
}
|
61
|
-
}
|
62
|
-
|
63
|
-
/**
|
64
|
-
*
|
65
|
-
*/
|
66
|
-
export class ReactInputComponent extends React.Component<{}, {}> {
|
67
|
-
public $props = {};
|
68
|
-
|
69
|
-
/**
|
70
|
-
* @override
|
71
|
-
*/
|
72
|
-
public render(): React.ReactElement {
|
73
|
-
return <input placeholder="input field" />;
|
74
|
-
}
|
75
|
-
}
|
@@ -1,59 +0,0 @@
|
|
1
|
-
import { render, screen } from '@testing-library/react';
|
2
|
-
import userEvent from '@testing-library/user-event';
|
3
|
-
import React from 'react';
|
4
|
-
|
5
|
-
describe('TestingLibrary', () => {
|
6
|
-
it('Triggers change event in input when typing.', async () => {
|
7
|
-
const user = userEvent.setup();
|
8
|
-
const onChange = jest.fn();
|
9
|
-
|
10
|
-
render(<input onChange={(event) => onChange(event.target.value)} />);
|
11
|
-
|
12
|
-
await user.type(screen.getByRole('textbox'), 'hello');
|
13
|
-
expect(onChange).toHaveBeenCalledWith('hello');
|
14
|
-
});
|
15
|
-
|
16
|
-
it('Triggers click and submit event once.', async () => {
|
17
|
-
const user = userEvent.setup();
|
18
|
-
const handleSubmit = jest.fn((ev) => {
|
19
|
-
ev.preventDefault();
|
20
|
-
});
|
21
|
-
const clickHandler = jest.fn();
|
22
|
-
|
23
|
-
render(
|
24
|
-
<form onSubmit={handleSubmit}>
|
25
|
-
<button type="submit" onClick={clickHandler}>
|
26
|
-
submit
|
27
|
-
</button>
|
28
|
-
</form>
|
29
|
-
);
|
30
|
-
|
31
|
-
await user.click(screen.getByRole('button'));
|
32
|
-
expect(handleSubmit).toHaveBeenCalledTimes(1);
|
33
|
-
expect(clickHandler).toHaveBeenCalledTimes(1);
|
34
|
-
});
|
35
|
-
|
36
|
-
it('Triggers change event once.', async () => {
|
37
|
-
const user = userEvent.setup();
|
38
|
-
const changeHandler = jest.fn();
|
39
|
-
|
40
|
-
render(<input type="checkbox" onChange={changeHandler} />);
|
41
|
-
|
42
|
-
await user.click(screen.getByRole('checkbox'));
|
43
|
-
|
44
|
-
expect(changeHandler).toHaveBeenCalledTimes(1);
|
45
|
-
});
|
46
|
-
|
47
|
-
it('Finds elements using "screen.getByText()".', async () => {
|
48
|
-
const user = userEvent.setup();
|
49
|
-
const clickHandler = jest.fn();
|
50
|
-
|
51
|
-
render(<input type="submit" value="Submit Button" onClick={clickHandler} />);
|
52
|
-
|
53
|
-
const element = screen.getByText('Submit Button');
|
54
|
-
|
55
|
-
await user.click(element);
|
56
|
-
|
57
|
-
expect(clickHandler).toHaveBeenCalledTimes(1);
|
58
|
-
});
|
59
|
-
});
|
package/test/tsconfig.json
DELETED
@@ -1,41 +0,0 @@
|
|
1
|
-
{
|
2
|
-
"compilerOptions": {
|
3
|
-
"outDir": "../tmp",
|
4
|
-
"rootDir": ".",
|
5
|
-
"tsBuildInfoFile": "../tmp/.tsbuildinfo-test",
|
6
|
-
"target": "es2020",
|
7
|
-
"declaration": true,
|
8
|
-
"module": "CommonJS",
|
9
|
-
"moduleResolution": "node",
|
10
|
-
"esModuleInterop": true,
|
11
|
-
"experimentalDecorators": true,
|
12
|
-
"allowSyntheticDefaultImports": true,
|
13
|
-
"resolveJsonModule": true,
|
14
|
-
"noUnusedLocals": true,
|
15
|
-
"noUnusedParameters": true,
|
16
|
-
"removeComments": false,
|
17
|
-
"preserveConstEnums": true,
|
18
|
-
"sourceMap": true,
|
19
|
-
"skipLibCheck": true,
|
20
|
-
"baseUrl": ".",
|
21
|
-
"composite": true,
|
22
|
-
"incremental": true,
|
23
|
-
"jsx": "react",
|
24
|
-
"types": [
|
25
|
-
"jest"
|
26
|
-
],
|
27
|
-
"lib": [
|
28
|
-
"es2015",
|
29
|
-
"es2016",
|
30
|
-
"es2017",
|
31
|
-
"dom"
|
32
|
-
]
|
33
|
-
},
|
34
|
-
"include": [
|
35
|
-
"@types/node",
|
36
|
-
"@types/jest",
|
37
|
-
"@types/react",
|
38
|
-
"@types/react-dom",
|
39
|
-
"."
|
40
|
-
]
|
41
|
-
}
|
package/test/vue/Vue.test.ts
DELETED
@@ -1,28 +0,0 @@
|
|
1
|
-
import { createApp } from 'vue';
|
2
|
-
|
3
|
-
describe('Vue', () => {
|
4
|
-
let appElement: Element;
|
5
|
-
|
6
|
-
beforeEach(() => {
|
7
|
-
appElement = document.createElement('div');
|
8
|
-
appElement.id = 'app';
|
9
|
-
appElement.innerHTML = '{{ message }}';
|
10
|
-
document.body.appendChild(appElement);
|
11
|
-
});
|
12
|
-
|
13
|
-
afterEach(() => {
|
14
|
-
document.body.innerHTML = '';
|
15
|
-
});
|
16
|
-
|
17
|
-
it('Tests integration.', () => {
|
18
|
-
const app = createApp({
|
19
|
-
data() {
|
20
|
-
return {
|
21
|
-
message: 'Test'
|
22
|
-
};
|
23
|
-
}
|
24
|
-
});
|
25
|
-
app.mount('#app');
|
26
|
-
expect(document.body.innerHTML).toBe('<div id="app" data-v-app="">Test</div>');
|
27
|
-
});
|
28
|
-
});
|