库中的单元测试组件时生成的测试失败
Generated test fails when unit testing component inside the library
我的项目是使用 nx 原理图创建的,我在库中有一些组件,我想使用 jest.js 对其进行单元测试。每个测试都失败并出现以下错误:
● MyComponent › should create
Failed: "Zone is needed for the async() test helper but could not be found. Please make sure that your environment includes zone.js/dist/zone.js"
7 | let fixture: ComponentFixture<MyComponent>;
8 |
> 9 | beforeEach(async(() => {
| ^
10 | TestBed.configureTestingModule({
11 | declarations: [ MyComponent ]
12 | })
at Env.beforeEach (node_modules/jest-jasmine2/build/jasmineAsyncInstall.js:41:24)
at Suite.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:9:3)
at Object.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:5:1)
● MyComponent › should create
TypeError: Cannot read property 'getComponentFromError' of null
at TestBedViewEngine._initIfNeeded (../../packages/core/testing/src/test_bed.ts:393:46)
at TestBedViewEngine.createComponent (../../packages/core/testing/src/test_bed.ts:594:10)
at Function.TestBedViewEngine.createComponent (../../packages/core/testing/src/test_bed.ts:247:36)
at Object.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:17:23)
● MyComponent › should create
expect(received).toBeTruthy()
Received: undefined
21 |
22 | it('should create', () => {
> 23 | expect(component).toBeTruthy();
| ^
24 | });
25 | });
26 |
at Object.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:23:23)
我已经尝试在规范文件中导入 zone.js、导入模块、删除异步、在每次测试前重置测试环境,但一切都失败了,并出现了一些不同的错误。我还应该提到我正在使用 vmware 的清晰度组件。
这是 .spec 文件:
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { MyComponent } from './my-component.component';
describe('MyComponent', () => {
let component: MyComponent;
let fixture: ComponentFixture<MyComponent>;
beforeEach(async(() => {
TestBed.configureTestingModule({
declarations: [ MyComponent ]
})
.compileComponents();
}));
beforeEach(() => {
fixture = TestBed.createComponent(MyComponent);
component = fixture.componentInstance;
});
it('should create', () => {
expect(component).toBeTruthy();
});
});
我期待在使用 nx 时这应该能像预期的那样工作。我在这里错过了什么?
我找到了解决办法!
问题是在创建 nx 工作区时,jest 没有立即配置。所以我采取了以下步骤使其工作:
1.安装 jest-zone-patch
npm install jest-zone-patch --save-dev
2。编辑文件
对于每个库,您必须将 test-setup.ts 文件编辑为如下所示:
import 'zone.js/dist/zone.js';
import 'zone.js/dist/proxy';
import 'zone.js/dist/sync-test';
import 'zone.js/dist/async-test.js';
import 'zone.js/dist/proxy.js';
import 'jest-zone-patch';
import 'jest-preset-angular';
import './jestGlobalMocks';
此外,将 setupFilesAfterEnv: ['<rootDir>/src/test-setup.ts']
添加到您的库的 jest.config.js
文件中,使其看起来像这样:
module.exports = {
name: 'my-library',
preset: '../../../jest.config.js',
coverageDirectory: '../../../coverage/libs/administration/identification',
setupFilesAfterEnv: ['<rootDir>/src/test-setup.ts']
};
并将 jestGlobalMocks.ts
文件添加到与 test-setup.ts
文件相同的文件夹中。你可以找到它 here,或者直接复制下面的代码:
Object.defineProperty(window, 'CSS', {value: null});
Object.defineProperty(document, 'doctype', {
value: '<!DOCTYPE html>'
});
Object.defineProperty(window, 'getComputedStyle', {
value: () => {
return {
display: 'none',
appearance: ['-webkit-appearance']
};
}
});
/**
* ISSUE: https://github.com/angular/material2/issues/7101
* Workaround for JSDOM missing transform property
*/
Object.defineProperty(document.body.style, 'transform', {
value: () => {
return {
enumerable: true,
configurable: true,
};
},
});
3。更改规范文件
将生成的规范文件更改为如下内容:
describe('MyComponent', () => {
let component: MyComponent;
let fixture: ComponentFixture<MyComponent>;
beforeEach(async(() => {
TestBed.configureTestingModule({
declarations: [MyComponent]
})
.compileComponents()
.then(() => {
fixture = TestBed.createComponent(MyComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
}));
it('should create', () => {
expect(component).toBeTruthy();
});
});
这样,在 compileComponents
promise 完成后创建组件和夹具,从而避免竞争条件和潜在的 undefined 单元测试中的 'should create'
错误.
4. 运行库测试
最后,您可以 运行 您的测试,希望它会通过。
ng test my-library
希望这对某人有所帮助。
我刚遇到同样的问题
Using Nrwl's Nx to scaffold a new application plus a "feature-shell" library (the design pattern suggested by Nx's "Enterprise Angular Monorepo Patterns" 书),我也很困惑为什么我的 Jest 单元测试 Angular 组件 类 在 apps/
中开箱即用,但是不是 libs/
.
我可能找到了一个更简单的解决方案:
查看工作区根目录中 angular.json
的内部。注意 属性 projects.<your-app>.architect.test.options.setupFile
。它的值应该类似于 "apps/<your-app>/src/test-setup.ts"
.
对我有用的解决方案是将 属性 和 angular.json
中的值添加到 projects.<your-lib>.architect.test.options
。
示例解决方案
// angular.json
{
...
"projects": {
"my-app": {
...
"architect": {
...
"test": {
...
"setupFile": "apps/my-app/src/test-setup.ts" // <- This was already here...
}
}
},
"my-lib": {
...
"architect": {
...
"test": {
...
"setupFile": "apps/my-app/src/test-setup.ts" // <- ...and I just added it here
}
}
}
}
}
希望 one-liner 也适合你!
如果有人在 Angular 11 上使用 Jest 并遇到此问题,请帮我解决这个问题。
确保我的 package.json
文件中有这两个属性。
{
"jest": {
"preset": "jest-preset-angular",
"setupFilesAfterEnv": [
"<rootDir>/setupJest.ts"
],
}
}
setupJest.ts
import 'jest-preset-angular'
还要确保您的 jest 配置不包含 "testEnvironment": "node",
。我从一个节点项目中复制了它,它也破坏了我的测试。
我的项目是使用 nx 原理图创建的,我在库中有一些组件,我想使用 jest.js 对其进行单元测试。每个测试都失败并出现以下错误:
● MyComponent › should create
Failed: "Zone is needed for the async() test helper but could not be found. Please make sure that your environment includes zone.js/dist/zone.js"
7 | let fixture: ComponentFixture<MyComponent>;
8 |
> 9 | beforeEach(async(() => {
| ^
10 | TestBed.configureTestingModule({
11 | declarations: [ MyComponent ]
12 | })
at Env.beforeEach (node_modules/jest-jasmine2/build/jasmineAsyncInstall.js:41:24)
at Suite.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:9:3)
at Object.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:5:1)
● MyComponent › should create
TypeError: Cannot read property 'getComponentFromError' of null
at TestBedViewEngine._initIfNeeded (../../packages/core/testing/src/test_bed.ts:393:46)
at TestBedViewEngine.createComponent (../../packages/core/testing/src/test_bed.ts:594:10)
at Function.TestBedViewEngine.createComponent (../../packages/core/testing/src/test_bed.ts:247:36)
at Object.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:17:23)
● MyComponent › should create
expect(received).toBeTruthy()
Received: undefined
21 |
22 | it('should create', () => {
> 23 | expect(component).toBeTruthy();
| ^
24 | });
25 | });
26 |
at Object.<anonymous> (libs/componentlib/src/lib/components/my-component/my-component.component.spec.ts:23:23)
我已经尝试在规范文件中导入 zone.js、导入模块、删除异步、在每次测试前重置测试环境,但一切都失败了,并出现了一些不同的错误。我还应该提到我正在使用 vmware 的清晰度组件。
这是 .spec 文件:
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { MyComponent } from './my-component.component';
describe('MyComponent', () => {
let component: MyComponent;
let fixture: ComponentFixture<MyComponent>;
beforeEach(async(() => {
TestBed.configureTestingModule({
declarations: [ MyComponent ]
})
.compileComponents();
}));
beforeEach(() => {
fixture = TestBed.createComponent(MyComponent);
component = fixture.componentInstance;
});
it('should create', () => {
expect(component).toBeTruthy();
});
});
我期待在使用 nx 时这应该能像预期的那样工作。我在这里错过了什么?
我找到了解决办法!
问题是在创建 nx 工作区时,jest 没有立即配置。所以我采取了以下步骤使其工作:
1.安装 jest-zone-patch
npm install jest-zone-patch --save-dev
2。编辑文件
对于每个库,您必须将 test-setup.ts 文件编辑为如下所示:
import 'zone.js/dist/zone.js';
import 'zone.js/dist/proxy';
import 'zone.js/dist/sync-test';
import 'zone.js/dist/async-test.js';
import 'zone.js/dist/proxy.js';
import 'jest-zone-patch';
import 'jest-preset-angular';
import './jestGlobalMocks';
此外,将 setupFilesAfterEnv: ['<rootDir>/src/test-setup.ts']
添加到您的库的 jest.config.js
文件中,使其看起来像这样:
module.exports = {
name: 'my-library',
preset: '../../../jest.config.js',
coverageDirectory: '../../../coverage/libs/administration/identification',
setupFilesAfterEnv: ['<rootDir>/src/test-setup.ts']
};
并将 jestGlobalMocks.ts
文件添加到与 test-setup.ts
文件相同的文件夹中。你可以找到它 here,或者直接复制下面的代码:
Object.defineProperty(window, 'CSS', {value: null});
Object.defineProperty(document, 'doctype', {
value: '<!DOCTYPE html>'
});
Object.defineProperty(window, 'getComputedStyle', {
value: () => {
return {
display: 'none',
appearance: ['-webkit-appearance']
};
}
});
/**
* ISSUE: https://github.com/angular/material2/issues/7101
* Workaround for JSDOM missing transform property
*/
Object.defineProperty(document.body.style, 'transform', {
value: () => {
return {
enumerable: true,
configurable: true,
};
},
});
3。更改规范文件
将生成的规范文件更改为如下内容:
describe('MyComponent', () => {
let component: MyComponent;
let fixture: ComponentFixture<MyComponent>;
beforeEach(async(() => {
TestBed.configureTestingModule({
declarations: [MyComponent]
})
.compileComponents()
.then(() => {
fixture = TestBed.createComponent(MyComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
}));
it('should create', () => {
expect(component).toBeTruthy();
});
});
这样,在 compileComponents
promise 完成后创建组件和夹具,从而避免竞争条件和潜在的 undefined 单元测试中的 'should create'
错误.
4. 运行库测试
最后,您可以 运行 您的测试,希望它会通过。
ng test my-library
希望这对某人有所帮助。
我刚遇到同样的问题
Using Nrwl's Nx to scaffold a new application plus a "feature-shell" library (the design pattern suggested by Nx's "Enterprise Angular Monorepo Patterns" 书),我也很困惑为什么我的 Jest 单元测试 Angular 组件 类 在 apps/
中开箱即用,但是不是 libs/
.
我可能找到了一个更简单的解决方案:
查看工作区根目录中 angular.json
的内部。注意 属性 projects.<your-app>.architect.test.options.setupFile
。它的值应该类似于 "apps/<your-app>/src/test-setup.ts"
.
对我有用的解决方案是将 属性 和 angular.json
中的值添加到 projects.<your-lib>.architect.test.options
。
示例解决方案
// angular.json
{
...
"projects": {
"my-app": {
...
"architect": {
...
"test": {
...
"setupFile": "apps/my-app/src/test-setup.ts" // <- This was already here...
}
}
},
"my-lib": {
...
"architect": {
...
"test": {
...
"setupFile": "apps/my-app/src/test-setup.ts" // <- ...and I just added it here
}
}
}
}
}
希望 one-liner 也适合你!
如果有人在 Angular 11 上使用 Jest 并遇到此问题,请帮我解决这个问题。
确保我的 package.json
文件中有这两个属性。
{
"jest": {
"preset": "jest-preset-angular",
"setupFilesAfterEnv": [
"<rootDir>/setupJest.ts"
],
}
}
setupJest.ts
import 'jest-preset-angular'
还要确保您的 jest 配置不包含 "testEnvironment": "node",
。我从一个节点项目中复制了它,它也破坏了我的测试。