2017-11-01 9 views
1

サービスのユニットテストを書いています。このサービスは、Webサービスへのhttp呼び出しを行います。Httpコールは角度4ユニットテストでは機能しません - モックを使用したくない

import { Http, Response } from '@angular/http'; 
constructor(private http: Http) {} 

this.http.get('/assets/data/xyz.json').subscribe(
    (response: Response) => this.parseXYZ(response) 
); 

サービングモードで完全に機能します。私の人生では、それをテストモードで動作させることはできません。私が見つけたすべての方法を探すとき、専門家が私を何らかの形のモックを使用するように変換しようとしています。関連するモックを含むソリューションのチュートリアルがたくさんあります。

私はモックを使いたくありません。顧客は私に巨大なjson構造を与えてくれました。その構造を複製するためにモックを使用するには、膨大な労力が必要です。私は時間のクランチ予算にいる。ユニットテストでHttpを動作させる簡単な方法はありますか?

+0

いいえ、ありません。 – jonrsharpe

答えて

1

いわゆるモックオブジェクトは複雑である必要はありません。

TypeScriptの構造型システムを利用することで、目標をすばやく完全な型の安全性で達成できます。

私-service.ts

import {Http} from '@angular/http'; 

export default class MyService { 
    constructor(readonly http: Http) {} 

    getXyz() { 
    return this.http.get('/assets/data/xyz.json') 
     // I think you probably meant map here, not subscribe 
     .map(
     // Note: I removed the explicit type annotation on `response`. 
     // Don't put type annotations on callback parameters. They hide bugs! 
     response => this.parseXYZ(response) 
    ); 
    } 
} 

今テストいくつかの定義によって

私-service.spec.ts

import test from 'tape'; 
import {Observable} from 'rxjs/Observable'; 
import {Http} from '@angular/http'; 

import MyService from './my-service'; 

// TODO: extract into a test helper module for reuse 
async function createMockHttp() { 
    // might need to configure your loader/bundler to handle json files (not hard) 
    const data = await import('/assets/data/xyz.json'); 

    return { 
    get(_: string) { 
     return Observable.of({ 
     json:() => JSON.parse(data) 
     }); 
    } 
    } as Http; 
} 

test('`MyService.prototype.getXyz` something', async t => { 
    const http = await createMockHttp(); 
    const myService = new MyService(http); // no injector, nothing fancy 

    myService.getXyz().subscribe({ 
     next: xyzStuff => { 
     t.deepEqual(xyzStuff, 'expectedValue'); 
     }, 
     error: error => t.fail(error), 
     complete:() => t.end() 
    }); 
}); 

のために、それはモックですしかし、それはかなり基本的なスタブオブジェクトです。 JSONを静的ファイルとして取得し、必要なメソッドのみを実装します。模擬フレームワークを使用せず、Angularの厄介なテストライブラリも使用しません。コードを直接実行するだけです。

+0

私は回避策を見つけました。それは簡単ではなく、些細なことでもありませんでした。私はここでそれをコピー/貼り付けたくないので、それはちょうど価値があるよりも多くのトラブルを引き起こすほど狂った複雑です。私は幻想的なモックが気にしない。私はそれらを使いたくない。 Angular 6または7でうまくいけば、この問題は迷惑で解決されるでしょう。 – JackT

+1

@JackT私はあなたが複雑な嘲笑抽象を使用することを提案していません。私はそのようなことを嫌い、可能な限り避けます。ここで私が持っているものは、単に慣習の模擬と呼ばれています。これは、フレームワークとネットワークを分離してサービスをテストするために使用される単なるダミーオブジェクトです。これは単体テストに最適です。このコードを試しましたか?それは定義によって動作するからです。 –

+0

いいえ、私はコンポーネントのままでユニットテストを実行する方法を見つけました。 – JackT

関連する問題