我正在测试一个已注入服务的组件。正如我所看到的,问题是它没有进入 ngOnDestroy()。每次测试后我都会明确要求测试 destroy() 我收到错误消息“无法取消订阅未定义”。可能是什么问题?
成分:
//...
subscription: Subscription;
constructor(private readonly router: Router,
private dialog: MatDialog,
private readonly carService: carService) {
}
ngOnInit(): void {
this.cars$ = this.carService.getCars();
this.subscription= this.cars$.subscribe(cars=> {
this.cars= cars;
});
}
ngOnDestroy() {
this.subscription.unsubscribe();
}
测试:
//...
beforeEach(async () => {
await TestBed.configureTestingModule({
providers: [
{provide: MatDialog, useClass: dialogMock},
{provide: Router, useValue: routerMock},
{provide: APP_BASE_HREF, useValue: '/cars'}
]
}).compileComponents();
component = TestBed.createComponent(CarComponent).componentInstance;
service = TestBed.inject(CarService);
service.setProjects([firstCar, secondCar]);
component.ngOnInit();
});
it('test', () => {
expect(component).toBeInstanceOf(CarComponent);
});
我认为问题是在运行
ngOnInit
之前没有运行 ngOnDestroy
。
你怎么嘲笑
carService
和getCars
?您需要嘲笑此服务和 getCars
方法。查看如何根据服务模拟组件:https://testing-angular.com/testing-components-depending-on-services/#testing-components-depending-on-services。
要快速解锁,您可以将
ngOnDestroy
更改为:
ngOnDestroy() {
if (this.subscription) {
this.subscription.unsubscribe();
}
}
如果订阅存在,那么我们取消订阅。
问题是 ngOnInit 改变了你的汽车的状态 Typescript 文件,并且您没有告诉您的测试接受更改。 所以不要输入:
component.ngOnInit();
你应该在它的位置放入:
let fixture = TestBed.createComponent(CarComponent);
fixture.detectChanges();
这样,当程序自然地更改汽车中的值时,您的测试文件将拾取它,并且您不必担心有条件地销毁订阅。
就我而言,这是缺少提供商的问题。
ngOnDestroy
调用了测试配置中未提供的服务功能。
一旦我在测试配置中提供服务,错误就消失了。