Karma with jsdom+custom shims/polyfills should create the right environment for the tests
- Ngôn ngữ chính
- TypeScript
- Star
- 27k
- Fork
- 11.8k
- Merge trung bình
- 14 giờ 23 phút
- Pull request đã merge (30 ngày)
- 162
Mô tả
# 🐞 Bug report
### Command (mark with an `x`)
- [ ] new
- [ ] build
- [ ] serve
- [X] test
- [ ] e2e
- [ ] generate
- [ ] add
- [ ] update
- [ ] lint
- [ ] xi18n
- [ ] run
- [ ] config
- [ ] help
- [ ] version
- [ ] doc
### Is this a regression?
No, the previous mayor version (8.x.x) the issue was present as well.
### Description
We are using `jsdom` as the target browser for unit testing in our Angular library. Our library uses the `crypto` API which is not implemented in `jsdom`, so we need a shim for this API. We did it as it's indicated in its docs:
```js
const dom = new JSDOM(`
Hello
`, {beforeParse(window) {
window.document.childNodes.length === 0;
window.someCoolAPI = () => { /* ... */ };
}
});
```
Luckely the `karma-json-launcher` offers the posibility to configure the `jsdom` instance throught `karma.conf.js` file:
```js
// karma.conf.js
const jsdom = require("jsdom");
module.exports = function(config) {
config.set({
browsers: ['jsdom'],
jsdomLauncher: {
jsdom: {
beforeParse(window) {
window.someCoolAPI = () => { /* ... */ };
}
}
}
});
};
```
The karma plugin creates the jsdom [instance correctly](https://github.com/badeball/karma-jsdom-launcher/blob/3c364d8988a7a1bc8d4687ec76810cb530adfffe/index.js#L28-L40) with the passed options, and it tries to parse the url where karma is running. But unfortunalety the `someCoolAPI` is not present in test context inside `window` property and test fails with a `ReferenceError: someCoolAPI is not defined`
On the other hand, when you try to manually create your own `jsdom` instance (same way `karma-json-launcher does`), with `someCoolAPI` polyfill, and parse any html document which use that API inside it works, jsdom parses the document and the scripst are executed correctly, so that makes me think is not a `jsdom` or `karma-jsdom-launcher` problem. Can be an issue with the CLI, or Karma itself?
## 🔬 Minimal Reproduction
1.
```sh
$ ng new foo
$ cd foo
$ npm install karma-jsdom-launcher jsdom
```
2. Configure `angular.json` file as @badeball indicates [here ](https://github.com/badeball/karma-jsdom-launcher#i-am-using-angular-cli-and-the-test-suite-hangs-indefinitely) due to #11561 and #13580
3. Configure `karma.config.js` file as `karma-jsdom-launcher` docs indicates:
```js
// karma.config.js
...
plugins: [
....
require('karma-jsdom-launcher'),
....
],
...
browsers: ['jsdom'],
jsdomLauncher: {
jsdom: {
beforeParse(window) {
window.someCoolAPI = () => { /* ... */ };
}
}
},
...
```
4. Create `app.component.ts` that uses that `someCoolAPI` in some way.
```
@Component({...})
export class AppComponent {
constructor() {
window.someCoolAPI(); //the test will fail here because someCoolAPI is not defined
}
}
```
5.
```sh
ng test
```
## 🔥 Exception or Error
> ng test
10% building 2/2 modules 0 active24 04 2020 23:56:59.854:WARN [karma]: No captured browser, open http://localhost:9877/
24 04 2020 23:56:59.871:INFO [karma-server]: Karma v4.4.1 server started at http://0.0.0.0:9877/
24 04 2020 23:56:59.873:INFO [launcher]: Launching browsers jsdom with concurrency unlimited
24 04 2020 23:56:59.911:INFO [launcher]: Starting browser jsdom
24 04 2020 23:57:12.239:WARN [karma]: No captured browser, open http://localhost:9877/
24 04 2020 23:57:12.552:INFO [Mozilla/5.0 (win32) AppleWebKit/537.36 (KHTML, like Gecko) jsdom/16.2.2]: Connected on socket BdQYHk1WXZIxjHKdAAAA with id 85109278
Mozilla/5.0 (win32) AppleWebKit/537.36 (KHTML, like Gecko) jsdom/16.2.2 AppComponent should create the app FAILED
ReferenceError: crypto is not defined
at
at new AppComponent (http://localhost:9877/_karma_webpack_/main.js:580:21)
at NodeInjectorFactory.AppComponent_Factory [as factory] (ng:///AppComponent/ɵfac.js:5:10)
at getNodeInjectable (http://localhost:9877/_karma_webpack_/vendor.js:41519:44)
at instantiateRootComponent (http://localhost:9877/_karma_webpack_/vendor.js:47483:23)
at createRootComponent (http://localhost:9877/_karma_webpack_/vendor.js:60827:23)
at ComponentFactory$1.create (http://localhost:9877/_karma_webpack_/vendor.js:66890:25)
at initComponent (http://localhost:9877/_karma_webpack_/vendor.js:82940:51)
at ZoneDelegate.invoke (http://localhost:9877/_karma_webpack_/polyfills.js:3836:30)
at ProxyZoneSpec.push../node_modules/zone.js/dist/zone-testing.js.ProxyZoneSpec.onInvoke (http://localhost:9877/_karma_webpack_/vendor.js:100670:43)
at ZoneDelegate.invoke (http://localhost:9877/_karma_webpack_/polyfills.js:3835:36)
Mozilla/5.0 (win32) AppleWebKit/537.36 (KHTML, like Gecko) jsdom/16.2.2: Executed 1 of 3 (1 FAILED) (0 secs / 0.294 secs)
Mozilla/5.0 (win32) AppleWebKit/537.36 (KHTML, like Gecko) jsdom/16.2.2 AppComponent should create the app FAILED
ReferenceError: crypto is not defined
at
at new AppComponent (http://localhost:9877/_karma_webpack_/main.js:580:21)
at NodeInjectorFactory.AppComponent_Factory [as factory] (ng:///AppComponent/ɵfac.js:5:10)
at getNodeInjectable (http://localhost:9877/_karma_webpack_/vendor.js:41519:44)
at instantiateRootComponent (http://localhost:9877/_karma_webpack_/vendor.js:47483:23)
at createRootComponent (http://localhost:9877/_karma_webpack_/vendor.js:60827:23)
at ComponentFactory$1.create (http://localhost:9877/_karma_webpack_/vendor.js:66890:25)
at initComponent (http://localhost:9877/_karma_webpack_/vendor.js:82940:51)
at ZoneDelegate.invoke (http://localhost:9877/_karma_webpack_/polyfills.js:3836:30)
at ProxyZoneSpec.push../node_modules/zone.js/dist/zone-testing.js.ProxyZoneSpec.onInvoke (http://localhost:9877/_karma_webpack_/vendor.js:100670:43)
## 🌍 Your Environment
Angular CLI: 9.1.3
Node: 12.10.0
OS: win32 x64
Angular: 9.1.3
... animations, cli, common, compiler, compiler-cli, core, forms
... language-service, platform-browser, platform-browser-dynamic
... router
Ivy Workspace: Yes
Package Version
-----------------------------------------------------------
@angular-devkit/architect 0.901.3
@angular-devkit/build-angular 0.901.3
@angular-devkit/build-optimizer 0.901.3
@angular-devkit/build-webpack 0.901.3
@angular-devkit/core 9.1.3
@angular-devkit/schematics 9.1.3
@ngtools/webpack 9.1.3
@schematics/angular 9.1.3
@schematics/update 0.901.3
rxjs 6.5.5
typescript 3.8.3
webpack 4.42.0
Hướng dẫn đóng góp
Hướng nghiên cứu
Bắt đầu bằng cách tái hiện lỗi với thiết lập angular.json và karma.config.js được tài liệu hóa, sau đó chạy ng test bằng karma-jsdom-launcher và beforeParse shim. Truy vết cách môi trường jsdom đi đến ngữ cảnh kiểm thử; hoàn thành có nghĩa là các shim tùy chỉnh như someCoolAPI hoặc crypto khả dụng trong quá trình kiểm thử mà không làm hỏng thiết lập launcher hiện có.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Đánh giá
- Công nghệ
- javascript, typescript
- Lĩnh vực
- cli, testing
- Loại issue
- Lỗi
- Độ khó
- 4/5
- Thời gian dự kiến
- 3-5 ngày
- Mức độ hoạt động
- Đình trệ
- Độ rõ ràng
- Khá rõ ràng
- Mức phù hợp với người mới
- 35/100