You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

NX Angular单元测试因NullInjectorError失败求助

NX Angular项目中Injection Token单元测试失败问题排查

问题场景

在NX Angular项目中使用Angular Injection Tokens时,执行npx nx run test:test运行单元测试持续失败,报错如下:

NullInjectorError: R3InjectorError(Standalone[ComponentsComponent])[InjectionToken TEST_INJECTION_TOKEN -> InjectionToken TEST_INJECTION_TOKEN -> InjectionToken TEST_INJECTION_TOKEN]:
NullInjectorError: No provider for InjectionToken TEST_INJECTION_TOKEN!

项目已在app.config.ts和app.component.spec.ts中配置该Injection Token的提供者,运行npx nx run test:serve --configuration=development时应用正常,单独测试AppComponent能通过,但执行全局测试命令就失败。

问题原因

ComponentsComponent是独立组件,其对应的components.component.spec.ts未配置TEST_INJECTION_TOKEN的提供者。尽管app.config.ts中全局注册了该Token的提供者,但Angular单元测试环境下,独立组件的测试不会自动继承全局配置;app.component.spec.ts中的配置仅对AppComponent的测试生效,无法覆盖ComponentsComponent的测试。当执行npx nx run test:test时会运行项目内所有测试用例,包括ComponentsComponent的测试,因此出现注入失败报错。

解决方案

修改components.component.spec.ts,在测试配置中添加TEST_INJECTION_TOKEN的提供者:

import { ComponentFixture, TestBed } from '@angular/core/testing';
import { ComponentsComponent } from './components.component';
import { TEST_INJECTION_TOKEN } from '../test.token';

describe('ComponentsComponent', () => {
  let component: ComponentsComponent;
  let fixture: ComponentFixture<ComponentsComponent>;

  beforeEach(async () => {
    await TestBed.configureTestingModule({
      imports: [ComponentsComponent],
      providers: [
        { provide: TEST_INJECTION_TOKEN, useValue: 'test-value' }
      ]
    })
    .compileComponents();
    
    fixture = TestBed.createComponent(ComponentsComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

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

也可以复用全局配置,比如导入app.config.ts中的提供者数组,但直接在组件测试中添加所需提供者是最直接的解决方式。

内容的提问来源于stack exchange,提问作者Sam Redmond

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.27 08:33:31