I'm new to testing in Jasmine and Karma and I'm trying to figure out how to test the observable of a component which gets set in the ngOnInit.
I have the following component:
export class Component implements OnInit{
currentConfig$: Observable<Config>;
constructor(
private someService: someService,
private route: ActivatedRoute
){}
ngOnInit() {
this.route.params.subscribe(params => {
this.someService.init(params.name)
})
this.currentConfig = this.someService.config$
}
}
Here's the service:
export class SomeService {
private subject: Subject<Config> = new Subject()
readonly config$ = subject.asObservable()
init(name: string): void {
this.findOne(name).subscribe(res => {
if (res)
this.subject.next({name})
})
}
findOne(name): Observable<any> {
return this.http.get('api');
}
}
And then I can subscribe to the currentConfig observable with the async pipe in the template.
I'm trying to test the values emitted by currentConfig$ of the Component.
Here's what my test looks like now:
fit('should show create component', fakeAsync(() => {
const component = fixture.componentInstance;
const debugElement = fixture.debugElement;
const expected = {name: 'ok'}
// this works
someService.config$.subscribe(config => console.log(config));
// this doesn't work even if I put it after the detect changes
// component.currentConfig$.subscribe(config => console.log(config));
spyOn(someService, 'findOne').and.returnValue(of(expected));
fixture.detectChanges();
}));
The component currentConfig$ is undefined if I try to subscribe to it. Could it be because of the async pipe which consumes the value emitted? Or I'm totally in the wrong direction? And how could I test it then?
I'm also still pretty confused about the spyOn. Should spy on a function of the service that deep inside of the ngOnInit?
EDIT
I think I solved it. I had to call component.ngOnInit() instead of fixture.detectChanges(), then subscribe to the component observable and then call fixture.detectChanges().
Here's the final test working:
fit('should get room config given room name', fakeAsync(() => {
const component = fixture.componentInstance;
const config: Config= {
name: 'name',
};
// mock service response
spyOn(roomService, 'findOne').and.returnValue(of(response));
// call ngOnInit instead. Detect changes keeps observable cold.
component.ngOnInit();
component.roomConfig$.subscribe(config => expect(config).toEqual(roomConfig));
// trigger second change detection.
fixture.detectChanges();
}));
I'm not sure why detectChanges kept the observable cold. If anyone can clear that out?