我是角度测试的初学者,我的问题可能是“角度测试最佳实践”的一部分。
我正在寻找一种方法,在测试中包括最小的模块,并覆盖我需要嘲笑的某些部分。
比方说,我有一个需要路由器工作的按钮组件。它的模块是这样的:
import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';
import { MyButtonComponent } from './mybutton.component';
import { Router } from '@angular/router';
@NgModule({
imports: [
CommonModule,
],
declarations: [
MyButtonComponent,
],
exports: [
MyButtonComponent,
],
providers: [
Router,
]
})
export class MyButtonModule { }
现在我要像这样测试它:
import { TestBed, ComponentFixture } from '@angular/core/testing';
import { MyButtonModule } from './viewer-button.module';
import { RouterTestingModule } from '@angular/router/testing';
// Tests Begining
describe('ViewerButtonComponent', () => {
let component: MyButtonComponent;
let fixture: ComponentFixture<MyButtonComponent>;
beforeEach(() => {
TestBed.configureTestingModule({
imports: [
ViewerButtonModule,
RouterTestingModule.withRoutes([]),
],
})
.compileComponents();
fixture = TestBed.createComponent(MyButtonComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
it('#should create the component', () => {
expect(component).toBeTruthy(' fail at creation');
});
});
但是Router
不会覆盖RouterTestingModule
的导入。 (出现了Can't resolve all parameters for Router: (?, ?, ?, ?, ?, ?, ?, ?).
错误)
对于这个示例,我知道一个更好的方法是只声明MyButtonComponent,然后导入RouterTestingModule,但是我在问是否有一种方法可以在没有NO_ERRORS_SCHEMA
浅的情况下使用较大的组件。
例如:
beforeEach(() => {
TestBed.configureTestingModule({
imports: [
// my childs component module
MyChildComponentModule1,
MyChildComponentModule2,
...
MyChildComponentModuleX,
//the modules that mock what needed (or use custom mock in the providers part)
RouterTestingModule,
HttpClientTestingModule,
....
SomethingTestingModule
],
})
.compileComponents();
fixture = TestBed.createComponent(MyButtonComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
答案 0 :(得分:0)
RouterTestingModule
用于暂存路由和导航。
这里有几点:
1)您不应该在小部件模块中提供Router
。相反,您应该在RouterModule.forRoot()
上添加AppModule
,以提供Router
服务及其依赖项。
2)您不应创建混合的Angular模块,这意味着不要在单个Angular模块中提供和声明。
3)Angular模块导入顺序很重要。使用此导入顺序,RouterTestingModule
的提供者将覆盖Router
中的ViewButtonModule
提供者。
TestBed.configureTestingModule({
imports: [
ViewerButtonModule,
RouterTestingModule.withRoutes([]),
],
});
4)您始终可以使用Angular测试模块覆盖提供程序。例如
TestBed.overrideProvider(Router, { useValue: routerStub });
或
TestBed.configureTestingModule({
providers: [
{ provide: Router, useValue: routerStub },
],
});
如果您有兴趣学习更多内容,可以保留我的文章Testing and Faking Angular Dependencies作为那些难以记住的细节的参考。