12

The application was built on Angular v4 and was gradually updated with every release up until now. Currently we're on Angular v7 and finally the CEO has agreed to write unit test while it wasn't the case before.

I just created a simple spec to just get started with the tests and start implementing it throughout the project but got stuck for two days with the following error:

AsyncTestZoneSpec is needed for the async() test helper but could not be >found. Please make sure that your environment includes zone.js/dist/async->test.js

While googling for the above error, I found some answers but that was related to Wallaybyjs but rather specific to Angular.

I've tried to reproduce the issue with the brand new installation of the angular project but couldn't really. This might be issue with some dependencies required to be missing to run tests on Angular 7.

Following is the test.ts file:

// This file is required by karma.conf.js and loads recursively all the .spec and framework files

import 'zone.js/dist/long-stack-trace-zone';
import 'zone.js/dist/proxy.js';
import 'zone.js/dist/sync-test';
import 'zone.js/dist/jasmine-patch';
import 'zone.js/dist/async-test';
import 'zone.js/dist/fake-async-test';
import { getTestBed } from '@angular/core/testing';
import {
  BrowserDynamicTestingModule,
  platformBrowserDynamicTesting
} from '@angular/platform-browser-dynamic/testing';

// Unfortunately there's no typing for the `__karma__` variable. Just declare it as any.
declare const __karma__: any;
declare const require: any;

// Prevent Karma from running prematurely.
__karma__.loaded = function () {};

// First, initialize the Angular testing environment.
getTestBed().initTestEnvironment(
  BrowserDynamicTestingModule,
  platformBrowserDynamicTesting()
);
// Then we find all the tests.
const context = require.context('./', true, /\.spec\.ts$/);
// And load the modules.
context.keys().map(context);
// Finally, start Karma to run the tests.
__karma__.start();

and Package.json:

{
    "name": "frontend",
    "version": "0.1.2-7",
    "appVersion": "2.104",
    "license": "MIT",
    "scripts": {
        "ng": "ng",
        "start": "ng serve",
        "build": "ng build",
        "test": "ng test",
        "lint": "ng lint",
        "e2e": "ng e2e",
        "build-staging": "bash build-staging.sh",
        "build-production": "bash build-production.sh",
        "compodoc": "npx compodoc -p src/tsconfig.app.json"
    },
    "private": true,
    "dependencies": {
        "@angular-devkit/build-angular": "^0.13.9",
        "@angular/animations": "7.0.3",
        "@angular/common": "7.0.3",
        "@angular/compiler": "7.0.3",
        "@angular/core": "7.0.3",
        "@angular/forms": "7.0.3",
        "@angular/http": "7.0.3",
        "@angular/platform-browser": "7.0.3",
        "@angular/platform-browser-dynamic": "7.0.3",
        "@angular/router": "7.0.3",
        "@fortawesome/fontawesome-free": "^5.9.0",
        "@mobiscroll/angular": "^4.7.3",
        "@ng-bootstrap/ng-bootstrap": "^4.2.1",
        "@ngx-translate/core": "^11.0.1",
        "@ngx-translate/http-loader": "^4.0.0",
        "angular2-virtual-scroll": "^0.4.16",
        "core-js": "^2.6.9",
        "moment": "^2.22.2",
        "ng-block-ui": "^2.1.5",
        "ng2-charts": "^1.6.0",
        "ngx-infinite-scroll": "^7.2.0",
        "ngx-lazy-load-images": "^1.3.1",
        "rxjs": "^6.5.2",
        "rxjs-compat": "^6.5.2",
        "zone.js": "^0.8.29"
    },
    "devDependencies": {
        "@angular/cli": "7.0.5",
        "@angular/compiler-cli": "^7.2.15",
        "@angular/language-service": "7.0.3",
        "@compodoc/compodoc": "^1.1.9",
        "@types/jasmine": "^2.8.16",
        "@types/jasminewd2": "~2.0.2",
        "@types/node": "^10.14.10",
        "codelyzer": "^4.4.2",
        "jasmine-core": "~3.3.0",
        "jasmine-spec-reporter": "~4.1.0",
        "karma": "^4.1.0",
        "karma-chrome-launcher": "~2.1.1",
        "karma-cli": "~1.0.1",
        "karma-coverage-istanbul-reporter": "^2.0.5",
        "karma-jasmine": "~1.1.0",
        "karma-jasmine-html-reporter": "^1.4.2",
        "protractor": "^5.4.2",
        "ts-node": "~7.0.1",
        "tslint": "~5.7.0",
        "typescript": "3.1.6"
    }
}

Following is the component spec:

import { async, ComponentFixture, TestBed } from '@angular/core/testing';

import { InsuranceComponent } from './insurance.component';
import { CartModule } from '../../cart/cart.module';
import { SharedModule } from '../../shared/shared.module';
import { CommonModule } from '@angular/common';
import { MbscModule } from '@mobiscroll/angular';
import { FormsModule } from '@angular/forms';
import { NgbModule } from '@ng-bootstrap/ng-bootstrap';
import { PipeModule } from '../../pipe/pipe.module';
import { InfiniteScrollModule } from 'ngx-infinite-scroll';
import { InsuranceRoutingModule } from '../insurance-routing/insurance-routing.module';
import { InsuranceSearchItemComponent } from '../insurance-search-item/insurance-search-item.component';
// tslint:disable-next-line:max-line-length
import { InsuranceSearchItemDetailsComponent } from '../insurance-search-item/insurance-search-item-details/insurance-search-item-details.component';

describe('Insurance Component', () => {
    let component: InsuranceComponent;
    let fixture: ComponentFixture<InsuranceComponent>;

    beforeEach(async(() => {
        TestBed.configureTestingModule({
            imports: [
                CartModule,
                SharedModule,
                CommonModule,
                MbscModule,
                FormsModule,
                NgbModule,
                PipeModule,
                InfiniteScrollModule,
                InsuranceRoutingModule
            ],
            declarations: [InsuranceComponent, InsuranceSearchItemComponent, InsuranceSearchItemDetailsComponent]
        }).compileComponents();

        fixture = TestBed.createComponent(InsuranceComponent);
        component = fixture.componentInstance;
        fixture.detectChanges();
    }));

    it('should create', () => {
        expect(component).toBeTruthy();
    });
});

Any help would be appreciated alot. Thanks

Vinay sharma
  • 745
  • 5
  • 14
Clean Code
  • 291
  • 1
  • 2
  • 9

6 Answers6

30

I was getting this error after Angular 11 upgrade.

This line must be the first line in test.ts, before all other imports:

import 'zone.js/dist/zone-testing'; // zone-testing needs to be first import!
Chris Fremgen
  • 4,649
  • 1
  • 26
  • 26
  • Confirmed! Since today we had this issue, upgrading our package-lock. Moving the import to be the first resolved the issue. We had to /* tslint:disable */ the file, because we have automatic import ordering otherwise. The upgrade changed dependencies from 11.0.2 to 11.0.3. – Jan Dockx Dec 09 '20 at 11:46
  • In my case I had to additionally put this import as my first one in that file (before importing getTestBed etc). – Sielu Jan 29 '21 at 17:05
  • This was exactly my issue! I also had to disable organize imports in VS code, it kept reorganizing the imports to put this last and causing issues. – RocketMan Mar 16 '21 at 13:17
  • for me, after adding this, running the test now shows: `cannot find module ''zone.js/dist/zone-testing' – Menahem Jul 12 '21 at 15:57
17

The following command was likely deprecated:

ng test --main somecomponent.spec.ts

Instead, use:

ng test

To just run a specific spec instead of all, prefix your describe and it block with f:

fdescribe('whatever', () => {})
THansen
  • 3
  • 3
Clean Code
  • 291
  • 1
  • 2
  • 9
5

I use this command in order to test one file only:

ng test --include somecomponent.spec.ts

You are going to have issues with the --main option as @clean-code has stated.

stackovermat
  • 406
  • 6
  • 10
2

I had the same problem with with the spectator testing framework.

The solution was, to import jest-preset-angular before the spectator imports.

wrong:


import { defineGlobalsInjections } from '@ngneat/spectator';
import 'jest-preset-angular';

correct:


import 'jest-preset-angular';
import { defineGlobalsInjections } from '@ngneat/spectator';

Ruderer
  • 345
  • 2
  • 11
1

I had similar issue but with jest testing framework.

After you removed all the karma and jasmine related stuff and installed jest related staff you could have a similar error

    zone-testing.js is needed for the async() test helper but could not be found.
        Please make sure that your environment includes zone.js/dist/zone-testing.js

And here it is my setup-jest.ts file

import 'jest-preset-angular';
import 'jest-extended';

When I changed one of the imports in the file setup-jest.ts to this

import 'jest-preset-angular/setup-jest';
import 'jest-extended';

Everything works fine now.

Volodymyr Khmil
  • 1,078
  • 15
  • 13
0

To use async() functionality, you need to import zone-testing. Try importing zone-testing package into your test.ts file.

import 'zone.js/dist/zone-testing'

Refer this link - Angular Documentation

Vinay sharma
  • 745
  • 5
  • 14
  • Thank you for your answer but the issue was with the command `ng test --main abc.component.spec.ts` and when I run just `ng test` then it worked – Clean Code Jul 16 '19 at 09:24