How to Unit Test a Directive In Angular 2? How to Unit Test a Directive In Angular 2? angularjs angularjs

How to Unit Test a Directive In Angular 2?


Testing compiled directive using TestBed

Let's say you have a following directive:

@Directive({  selector: '[my-directive]',})class MyDirective {  public directiveProperty = 'hi!';}

What you have to do, is to create a component that uses the directive (it can be just for testing purpose):

@Component({  selector: 'my-test-component',  template: ''})class TestComponent {}

Now you need to create a module that has them declared:

describe('App', () => {  beforeEach(() => {    TestBed.configureTestingModule({      declarations: [        TestComponent,        MyDirective      ]    });  });  // ...});

You can add the template (that contains directive) to the component, but it can be handled dynamically by overwriting the template in test:

it('should be able to test directive', async(() => {  TestBed.overrideComponent(TestComponent, {    set: {      template: '<div my-directive></div>'    }  });  // ...      }));

Now you can try to compile the component, and query it using By.directive. At the very end, there is a possibility to get a directive instance using the injector:

TestBed.compileComponents().then(() => {  const fixture = TestBed.createComponent(TestComponent);  const directiveEl = fixture.debugElement.query(By.directive(MyDirective));  expect(directiveEl).not.toBeNull();  const directiveInstance = directiveEl.injector.get(MyDirective);  expect(directiveInstance.directiveProperty).toBe('hi!');}); 

# Old answer:

To test a directive you need to create a fake component with it:

@Component({  selector: 'test-cmp',  directives: [MyAttrDirective],  template: ''})class TestComponent {}

You can add the template in the component itself but it can be handled dynamically by overwriting the template in test:

it('Should setup with conversation', inject([TestComponentBuilder], (testComponentBuilder: TestComponentBuilder) => {    return testComponentBuilder      .overrideTemplate(TestComponent, `<div my-attr-directive></div>`)      .createAsync(TestComponent)      .then((fixture: ComponentFixture<TestComponent>) => {        fixture.detectChanges();        const directiveEl = fixture.debugElement.query(By.css('[my-attr-directive]'));        expect(directiveEl.nativeElement).toBeDefined();      });  }));

Note that you're able to test what directive renders but I couldn't find the way to test a directive in a way components are (there is no TestComponentBuilder for directives).


Took me a while to find a good example, a good person on angular gitter channel pointed me to look at the Angular Material Design 2 repository for examples. You can find a Directive test example here. This is the test file for the tooltip directive of Material Design 2. It looks like you have to test it as part of a component.