With Angular 4 it is possible to test the Component's template, for example checking if clicking a button triggers the expected method and stuff like that.
But how can templates be included in the test coverage? By default they are not (using Angular CLI tests with Karma+Jasmine+Istanbul).
Did you by any chance mean that you want to test the actual representation of the templates? Then you have to completely switch to jest instead of karma/jasmine combination. With jest you can generate template snapshots in your tests which are pushed alongside the component and checked on CI tests.
For example let's say you have a main.component which shows a loader while a SessionService is not ready and then the router-outlet for route content when it's done. A jest snapshot would look somewhat like this:
exports[`MainComponent renders: default state 1`] = `
<main
isReady$={[Function BehaviorSubject]}
sessionService={[Function Object]}
>
<loader-line
ng-reflect-active="true"
/>
</main>
`;
exports[`MainComponent session storage is ready renders 1`] = `
<main
isReady$={[Function BehaviorSubject]}
sessionService={[Function Object]}
>
<main>
<router-outlet />
</main>
</main>
`;
And the test code looks like that:
describe('MainComponent', () => {
let fixture: ComponentFixture<MainComponent>;
const isReady$ = new BehaviorSubject(false);
const mockSessionStorage = Mock.all<SessionService>();
beforeEach(async(() => {
TestBed.configureTestingModule({
declarations: [MainComponent, MockComponents(LoaderLineComponent)],
imports: [RouterTestingModule],
providers: [mockWith(SessionService, mockSessionStorage)],
})
.compileComponents();
}));
afterAll(() => {
isReady$.complete();
});
beforeEach(() => {
Mock.extend(mockSessionStorage).with({isReady$});
fixture = TestBed.createComponent(MainComponent);
detectChanges(fixture);
});
it(`creates instance`, () => expect(fixture.componentInstance).toBeTruthy());
it(`renders`, () => expect(fixture).toMatchSnapshot(`default state`));
describe(`session storage is ready`, () => {
beforeEach(() => {
isReady$.next(true);
detectChanges(fixture);
});
it(`renders`, () => expect(fixture).toMatchSnapshot());
});
});
That's it, no more querying of <loader-line>
or <router-outlet>
in the spec file code, just look at the snapshot and you're done.
Note: I'm also using ng-mocks, ts-mockery and some own util functions, but the main thing for you to look for are the expect(fixture).toMatchSnapshot()
lines which are jest native.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With