9

Angular2コンポーネントのテストでRouteParams依存関係のモックを注入するときに問題があります。私の一般的な考えは、私はいくつかのプロバイダーが足りないかもしれないということです。Angular2 - mocking RouteParams in test

テストが失敗すると:問題が何であるか、誰を知ってい

 
Cannot resolve all parameters for 'RouteParams'(?). Make sure that all the parameters are decorated with Inject 
or have valid type annotations and that 'RouteParams' is decorated with Injectable. 

import { 
    it, 
    inject, 
    injectAsync, 
    describe, 
    beforeEach, 
    beforeEachProviders, 
    TestComponentBuilder 
} from 'angular2/testing'; 

import {Component, provide} from 'angular2/core'; 
import {BaseRequestOptions, Http} from 'angular2/http'; 
import {MockBackend} from 'angular2/http/testing'; 
import {RouteParams, ROUTER_PROVIDERS, ROUTER_PRIMARY_COMPONENT} from 'angular2/router'; 

// Load the implementations that should be tested 
import {Home} from './home'; 
import {Title} from './providers/title'; 

describe('Home',() => { 
    // provide our implementations or mocks to the dependency injector 

    beforeEachProviders(() => [ 
    Title, 
    Home, 
    provide(RouteParams, { useValue: new RouteParams({ id: '1' }) }), 
    BaseRequestOptions, 
    MockBackend, 
    provide(Http, { 
     useFactory: function(backend, defaultOptions) { 
      return new Http(backend, defaultOptions); 
     }, 
     deps: [MockBackend, BaseRequestOptions] 
    }), 
    provide(RouteParams, { 
     useFactory: function() { 
      return new RouteParams({ 'id':'1' }); 
     } 
    }) 
    ]); 

    it('should have a title', inject([ Home ], (home) => { 
    expect(home.title.value).toEqual('Angular 2'); 
    })); 

    it('should have a http', inject([ Home ], (home) => { 
    expect(!!home.http).toEqual(true); 
    })); 

    it('should log ngOnInit', inject([ Home ], (home) => { 
    spyOn(console, 'log'); 
    spyOn(console, 'info'); 
    expect(console.log).not.toHaveBeenCalled(); 
    expect(console.info).not.toHaveBeenCalled(); 

    home.ngOnInit(); 
    expect(console.log).toHaveBeenCalled(); 
    expect(console.info).toHaveBeenCalledWith('1'); 
    })); 

}); 

答えて

1

を使用してRouteProviderを模擬しますモック。私はあなたが必要とするActivatedRouteの部分を模倣することがそのトリックだと思う。その後、

import {ActivatedRoute, ParamMap} from '@angular/router'; 

/** 
* Mocking the ActivatedRoute which is injected in the Component on creation. 
* This allows for easier testing as values can be set as needed. 
*/ 
class MockActivatedRoute { 
    paramMap = Observable.of(new Params()); 
} 

/** 
* Bare bones implementation of ParamMap used in mock. Further tests can expand 
* on this implementation as needed. 
*/ 
class Params implements ParamMap { 
    keys: string[]; 

    private routes: {[key: string]: string|null} = { 
    subject: 'foo', 
    time: 'd-123-1', 
    device: 'all', 
    location: 'c-123' 
    }; 

    constructor() { 
    this.keys = Object.keys(this.routes); 
    } 

    has(name: string): boolean { 
    throw new Error('Method not implemented.'); 
    } 
    get(name: string): string|null { 
    return this.routes[name]; 
    } 
    getAll(name: string): string[] { 
    throw new Error('Method not implemented.'); 
    } 
} 

そして、あなたは本当のActivatedRouteオーバー嘲笑サービス提供あなたのテストモジュールで確認してください:完了するために

providers: [ 
    { 
    provide: ActivatedRoute, 
    useValue: new MockActivatedRoute(), 
    } 
] 

、私はコンポーネントIにそれを使用する方法を私にとって、これはそれをやりましたテスト:

ngOnInit() { 
    this.route.paramMap 
     .map((params: ParamMap) => params.get('subject') as string) 
     .subscribe((subject: string) => this.subject = subject); 
} 
9

自分でこの問題を解決するために管理され、あなたはここで、彼らは

Angular4で作業している私は先に行って、作成されていても、土地の人々のために

provide(RouteParams, { useValue: new RouteParams({ id: '1' }) })

import { 
    it, 
    inject, 
    injectAsync, 
    describe, 
    beforeEach, 
    beforeEachProviders, 
    TestComponentBuilder 
} from 'angular2/testing'; 

import {Component, provide} from 'angular2/core'; 
import {BaseRequestOptions, Http} from 'angular2/http'; 
import {MockBackend} from 'angular2/http/testing'; 
import {RouteParams, ROUTER_PROVIDERS, ROUTER_PRIMARY_COMPONENT} from 'angular2/router'; 

// Load the implementations that should be tested 
import {Home} from './home'; 
import {Title} from './providers/title'; 

describe('Home',() => { 
    // provide our implementations or mocks to the dependency injector 

    beforeEachProviders(() => [ 
    Title, 
    Home, 
    provide(RouteParams, { useValue: new RouteParams({ id: '1' }) }), 
    BaseRequestOptions, 
    MockBackend, 
    provide(Http, { 
     useFactory: function(backend, defaultOptions) { 
      return new Http(backend, defaultOptions); 
     }, 
     deps: [MockBackend, BaseRequestOptions] 
    }) 
    ]); 

    it('should have a title', inject([ Home ], (home) => { 
    expect(home.title.value).toEqual('Angular 2'); 
    })); 

    it('should have a http', inject([ Home ], (home) => { 
    expect(!!home.http).toEqual(true); 
    })); 

    it('should log ngOnInit', inject([ Home ], (home) => { 
    spyOn(console, 'log'); 
    spyOn(console, 'info'); 
    expect(console.log).not.toHaveBeenCalled(); 
    expect(console.info).not.toHaveBeenCalled(); 

    home.ngOnInit(); 
    expect(console.log).toHaveBeenCalled(); 
    expect(console.info).toHaveBeenCalledWith('1'); 
    })); 

}); 
+0

ありがとうございます!これはうまくいった。 – Charlie