⚠️ Use ng-mocks
in your unit tests
More details after about this lib. Just keep in mind that it's awesome.
Standard first
I love use standard. Angular makes the choice to use Karma/Jasmine, so I continue to use it.
😇 YES, Jest is also a great challenger and a powerful tool to write and execute your unit tests
Testing your components
There are two things to test with your components.
- Template (.html)
- Logic (.ts).
Testing template
What can be tested and needed to be tested ?
- All Angular directive
*ngIf
,*ngFor
, ... - All inputs
@Input()
- All outputs
@Output()
🤔 Why we need to test
*ngIf
for example ?Image in your commit #1 you add
*ngIf
in your template without tests. Someone commit the #2 and erase by accident the conditional directive. No test cover this regression.
🔥 Use MockRender
from ng-mocks
to create your component fixture.
import { TestBed } from '@angular/core/testing';
import { YourComponent } from './your-component.component.ts';
import { MockRender } from 'ng-mocks';
describe('YourComponent', () => {
beforeEach(() => {
TestBed.configureTestingModule({
declarations: [YourComponent]
});
});
it('should create', () => {
const fixture = MockRender(`<your-component></your-component>`);
expect(fixture.componentInstance).toBeTruthy();
});
it('should display description', () => {
const fixture = MockRender(
`<your-component [description]="description"></your-component>`,
{ description: 'hello world' }
);
fixture.detectChanges();
const descriptionEl = fixture.debugElement.query(By.css('.description');
expect(descriptionEl.nativeElement.innerHTML).toEqual('hello world');
});
});
🚀 To improve performance and to scope your unit test, use MockComponent
from ng-mocks
With this method, child components become black box.
import { TestBed } from '@angular/core/testing';
import { YourComponent } from './your-component.component.ts';
import { YourChildComponent } from './your-child-component.component.ts';
import { MockRender, MockComponent } from 'ng-mocks';
describe('YourComponent', () => {
beforeEach(() => {
TestBed.configureTestingModule({
declarations: [YourComponent, MockComponent(YourChildComponent)]
});
});
it('should trigger data', () => {
let receivedData = null;
const fixture = MockRender(
`<my-component (getData)="getData($event)></my-component>`,
{ getData: data => receivedData = data; }
);
fixture.detectChanges();
const triggerDataEl = fixture.debugElement.query(By.css('.trigger-data'));
const childComponent: YourChildComponent = triggerDataEl.componentInstance;
childComponent.triggerData.emit('hello world');
fixture.detectChanges();
expect(receivedData).toEqual('hello world');
});
});
In this example, we trigger the output from the child component. And get an output from our component.
Testing logic
In the next post.
I hope this article can helps you in your development. 🐼