3

我的项目是使用 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 时这应该像预期的那样工作。我在这里想念什么?

4

3 回答 3

4

我刚刚遇到了同样的问题。

使用Nrwl 的 Nx 构建一个新应用程序和一个“功能外壳”库(Nx 的“企业 Angular Monorepo 模式”一书建议的设计模式),我也很困惑为什么我的 Angular 组件类的 Jest 单元测试开箱即用里面apps/,但不是libs/

我可能找到了一个更简单的解决方案:

angular.json在工作区根目录中查看。注意属性projects.<your-app>.architect.test.options.setupFile。它的值应该类似于"apps/<your-app>/src/test-setup.ts".

对我有用的解决方案是将确切的属性和值添加angular.jsonprojects.<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
        }
      }
    }
  }
}

希望单线也适合您!

于 2019-07-04T16:37:32.633 回答
2

如果有人在 Angular 11 中使用 Jest 并遇到此问题,那么为我解决的问题是。

确保我的package.json文件中有这两个属性。

{
  "jest": {
    "preset": "jest-preset-angular",
    "setupFilesAfterEnv": [
      "<rootDir>/setupJest.ts"
    ],
  }
}

setupJest.ts

import 'jest-preset-angular'

还要确保您的笑话配置不包括"testEnvironment": "node",. 我从一个节点项目中复制了它,它也破坏了我的测试。

于 2020-12-30T07:41:38.137 回答
1

我找到了解决方案!

问题是在创建 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。你可以在这里找到它,或者直接复制下面的代码:

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();
  });
});

这样,在compileComponentsPromise 完成后创建组件和夹具,从而避免单元测试中的竞争条件和潜在的未定义错误。'should create'

4.运行库测试

最后,您可以运行您的测试,并希望它会通过。

ng test my-library

希望这会对某人有所帮助。

于 2019-03-28T14:22:20.353 回答