How to write an HTTP mock unit test in Angular 2 final release?

angular, unit-testing

Solution

First thing you need to do is configure the `TestBed`. There's no more `TestComponentBuilder`. With the `TestBed`, it's like configuring an `@NgModule` from scratch, just for the test environment. This means you will add the component under test to the `declarations`, add any providers to the `provider`, and any imports to the `imports`.

To configure the mock backend for `Http` provider, you would just create the `Http` from the `MockBackend`.

beforeEach(() => {
  TestBed.configureTestingModule({
    imports: [ HttpModule ],
    declarations: [ RouteListComponent ],
    providers: [
      MockBackend,
      BaseRequestOptions,
      {
        provide: Http,
        useFactory: (backend: MockBackend, options: BaseRequestOptions) => {
          return new Http(backend, options);
        },
        deps: [ MockBackend, BaseRequestOptions ]
      }
    ]
  })
})

That should be it for the configuration, assuming you don't need any other providers or imports I don't know about.

For the test you'll first want to make it an `async` test, as you'll be doing asynchronous operations in the test. This hasn't changed from RC, you just use `async`. If the component uses `templateUrl` (and you're not using Webpack), then you will need to call `TestBed.compileComponents()`, otherwise no need to. After that you can create the component with `TestBed.createComponent`

let fixture: ComponentFixture<RouteListComponent>;
let component: RouteListComponent;

beforeEach(async(() => {
  TestBed.configureTestingModule({ ... })
  .compileComponents().then(() => {
    fixture = TestBed.createComponent(RouteListComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });
}));

it('...', async(inject([MockBackend], (backend: MockBackend) => {

})))

Pretty much all the things above related to testing can be imported from `@angular/core/testing`. Your use of the `MockBackend` would still be the same.

Another note, you don't need to call the `component.ngOnInit`. That is called by the framework when you call `fixture.detectChanges()`

See Also:

- Testing documentation for more complete examination of testing support.

Problem

I have moved from RC4 to final release (2.1.0) and I am refactoring my unit tests to conform to 2.1.0 syntax. This is easy except for HTTP mocking. I cannot find any examples for how to mock HTTP requests in 2.1.0 Here is an RC4 HTTP unit test. How would I re-write this in final release 2.1.0? ``` it('ngOnInit()', async(inject([TestComponentBuilder, XHRBackend], (tcb:TestComponentBuilder, mockBackend:MockBackend) => { tcb.createAsync(Route1ListComponent).then((fix:ComponentFixture<Route1ListComponent>) => { // THIS BLOCK OF CODE I NEED RE-WRITE TO 2.1.0 mockBackend.connections.subscribe( (connection:MockConnection) => { connection.mockRespond(new Response( new ResponseOptions({ body: persons } ))); }); // THIS BLOCK OF CODE WILL NOT CHANGE let instance = fix.componentInstance; instance.ngOnInit(); expect(instance.persons.length).toBe(3); }); }))); ``` Unfortunately, I cannot use RC code.

Original source