首页 > 解决方案 > 如何使用对服务上的事件发射器做出反应的订阅进行异步测试?

问题描述

我在让我的测试为我的组件工作时遇到了很多麻烦。特别是我在这个测试中遇到的问题:

it('should set its location string to the location of the first added result', async(() => {
  fixture.detectChanges();
  const result1: Result = new Result(1, 1, 1, 1);
  result1.addressString = 'Test String';
  resultsService.addResult(result1);
  fixture.detectChanges();
  fixture.whenStable().then( () => {
    expect(component.locationString).toBe('Test String');
  });
}));

我不明白如何让我的测试工作,异步测试的所有资源都不能帮助我理解我必须做什么。目前这个测试给出了这两个错误:1

Failed: Cannot read property 'addressString' of undefined
Expected undefined to be 'Test String'.

我假设原因是因为我的组件中有这个订阅:

ngOnInit() {
  this.resultSubscription = this.resultsService.resultListEmitter.subscribe(
    (results: Result[]) => {
      if (results.length < 1) {
        this.errorMode = true;
      }
      this.locationString = results[0].addressString;
      this.secondResultLoaded = results.length >= 2;
    }
  );
  this.resultsService.emitResults();
}

当结果服务发出其当前持有的结果时,它应该更新组件上的某些内容。

resultList: Result[];
resultListEmitter = new EventEmitter<Result[]>();

结果服务以下列方式处理结果:

emitResults() {
  this.resultListEmitter.emit(this.resultList);
}
addResult(result: Result) {
  if (this.resultList.length > 1) {
    console.log('Second result added.');
    this.resultList[1] = result;
  } else {
    this.resultList.push(result);
    console.log('First result added.');

  }
  this.emitResults();
}

/*Delete last result so that a comparison can be done again*/
wipeLastResult() {
  if (this.resultList.length > 0) {
    this.resultList.splice(this.resultList.length - 1, 1);
  }
  this.emitResults();
}

/*Wipe all results to start over*/
wipeAllResults() {
  this.resultList = [];
  this.emitResults();
}

如您所见,每当发生变化时,它都会发出其事件发射器,其中包含最多两个结果的列表数据。该组件应该对此做出反应。

这样做的问题是,当我测试时,我很难弄清楚如何对这些排放做出异步反应。这导致我的组件测试没有对服务进行操作后的数据,因为它不会等待我的订阅对数据做出反应。

标签: angularunit-testingjasminekarma-runnerangular-test

解决方案


推荐阅读