我正在使用angular2 rc2和jasmin,试图测试我的组件。
首先,我的组件:
@Component ({
selector: '[toggleLogerStatusDirective]',
providers: [DataService],
template:
`
<button type="button" class="btn btn-link" (click)=toggleLoggerStatus()
data-toggle="tooltip" data-placement="right"
title="Click to enable/ disable the ServiceDebugMonitor"
>{{status}}</button>
`
})
export class ToggleLogerStatusDirective implements OnInit {
active: boolean;
constructor(private _dataService: DataService) {
}
toggleLoggerStatus() {
this._dataService.putData('/loggerStatus', !this.active)
.subscribe(
(data) => {
this.active = data;
},
(error) => {
console.log(error);
this.getLoggerStatus();
}
);
}
getLoggerStatus() {
this._dataService.getData('/loggerStatus')
.subscribe(
(data) => this.active = data,
(error) => {
console.log(error);
this.getLoggerStatus();
},
)
}
...
}
这将显示记录器是处于活动/非活动状态,并且可以切换active-boolean。 DataService将执行http请求以获取信息。 所有方法和DataService都经过(成功)测试。现在我想测试按钮上的点击。这看起来像:
//imports..
setBaseTestProviders(TEST_BROWSER_DYNAMIC_PLATFORM_PROVIDERS,
TEST_BROWSER_DYNAMIC_APPLICATION_PROVIDERS);
describe('Directive: ToggleLogerStatusDirective', () => {
let toggleLogerStatusDirective;
beforeEachProviders(() => [
provide(DataService, {useClass: MockDataService}),
TestComponentBuilder,
]);
it('Check if toggling via web-interface is possible', inject([TestComponentBuilder, DataService], (_tcb, _dataService) => {
_tcb.createAsync(MockToggleLogerStatusDirective)
.then( (fixture) => {
this.toggleLogerStatusDirective = new ToggleLogerStatusDirective(_dataService);
this.toggleLogerStatusDirective.active = false;
let container = fixture.componentInstance;
let div = fixture.nativeElement.querySelector('div');
div.click();
expect(this.toggleLogerStatusDirective.active).toEqual(true);
fixture.destroy();
});
}));
}
class MockDataService {
getData(appendedUrl: string, searchParamTimestamp? : string) : Observable<any> {
return Observable.of(false);
}
putData(appendedUrl: string, searchParam: boolean) : Observable<any> {
return Observable.of(true);
}
}
@Component({
selector: '[mockLogger]',
template: `<div toggleLogerStatusDirective></div>`,
directives: [ToggleLogerStatusDirective],
}) export class MockToggleLogerStatusDirective {
}
所以,我有一个TestComponent,它在div容器中有“to-test-comonent”,它将被点击,我的DataService将被没有http请求的MockDataService取代。 / p>
这将导致以下错误:
zone.js:461 Unhandled Promise rejection: EXCEPTION: Error in ./MockToggleLogerStatusDirective class MockToggleLogerStatusDirective - inline template:1:2
ORIGINAL EXCEPTION: No provider for Http!
ORIGINAL STACKTRACE:
Error: DI Exception
at NoProviderError.BaseException [as constructor] (http://127.0.0.1:8080/node_modules/@angular/core/src/facade/exceptions.js:20:23)
at NoProviderError.AbstractProviderError [as constructor] (http://127.0.0.1:8080/node_modules/@angular/core/src/di/reflective_exceptions.js:40:16)
at new NoProviderError (http://127.0.0.1:8080/node_modules/@angular/core/src/di/reflective_exceptions.js:77:16)
at ReflectiveInjector_._throwOrNull (http://127.0.0.1:8080/node_modules/@angular/core/src/di/reflective_injector.js:777:19)
at ReflectiveInjector_._getByKeyDefault (http://127.0.0.1:8080/node_modules/@angular/core/src/di/reflective_injector.js:805:25)
at ReflectiveInjector_._getByKey (http://127.0.0.1:8080/node_modules/@angular/core/src/di/reflective_injector.js:768:25)
at ReflectiveInjector_.get (http://127.0.0.1:8080/node_modules/@angular/core/src/di/reflective_injector.js:577:21)
at ElementInjector.get (http://127.0.0.1:8080/node_modules/@angular/core/src/linker/element_injector.js:23:48)
at DebugAppView._View_MockToggleLogerStatusDirective0.createInternal (MockToggleLogerStatusDirective.template.js:26:68)
at DebugAppView.AppView.create (http://127.0.0.1:8080/node_modules/@angular/core/src/linker/view.js:87:21)
有谁知道,导致此错误的原因是什么? (以及如何处理它?) 我可以想一想,DataService的“嵌套”调用是原因(MockToggleLogerStatusDirective - &gt; ToggleLogerStatusDirective - &gt; DataService)..。
谢谢, 好处
答案 0 :(得分:0)
您需要覆盖测试组件的提供程序,如:
it('Check if toggling via web-interface is possible', inject([TestComponentBuilder, DataService], (_tcb, _dataService) => {
_tcb.overrideProviders(MockToggleLogerStatusDirective,
[{provide: DataService, useClass: MockDataService}])
.createAsync(MockToggleLogerStatusDirective)
.then( (fixture) => {