はじめに
この記事では、UI-Routerを使用した場合に、$stateParam
の値をJasmineによるテストでどのようにモックするかについて説明します。
- この記事では、ui-router 1.0以上を使用することを前提として記載しています。
-
$stateProvider.state()
によるルーティングはcontrollerではなくcomponentに対して行っています。
前提: $stateParamsを使用するcomponent
次のサンプルコードのように、movie
というcomponentを$stateProvider.state()
によってルーティング設定した場合の例について考えてみましょう。
angular
.module('movies', [])
.component('movie', {
templateUrl: './movieView.html',
controller: controller
})
function controller($stateParams){
this.$onInit = function(){
// 指定されたIDを元に情報を取得
var item = getItem($stateParams.id);
// Do something...
}
}
$stateProvider
.state('movieDetail', {
url: '/movies/{id:int}',
component: 'movie',
});
このサンプルコードでは、URLから渡されたidをmovie
componentの中で$stateParams.id
をとして受け取ります。Jasmineを使用して、このmovie
componentをテストする際、何らかのidを渡してその挙動を確認する必要がありますが、Jasmineではどのようにして$stateParams
の値を定義すればよいでしょうか。これにはいくつかの方法があります。
$stateParamsのモック
$stateParams
をモックしてid
に1
という値をセットすることを考えてみます。これを実現してJasmineによるテストを行うには、以下のような方法があります。
$provide.constant
$provide.constant
を使用して$stateParams
の値を定義する方法です。これは、以下のように実装します。
beforeEach(module('movies'));
beforeEach(() => {
module(function ($provide) {
$provide.constant('$stateParams', { id: 1 });
});
});
$provide.factory
$provide.factory
を使用して$stateParams
の値を定義する方法です。これは、以下のように実装します。
beforeEach(module('movies'));
beforeEach(() => {
module(function ($provide) {
$provide.factory('$stateParams', () => {
return { id: 1 };
});
});
});
angular.copy
angular.copy
を使用して、$stateParams
に値をセットします。この場合、$stateParams
のオブジェクトを保持したまま、そのコンテンツだけを更新することができます。以下が実装例です。
beforeEach(module('movies'));
beforeEach(() => {
inject(($stateParams) => {
angular.copy({ id: 1 }, _$stateParams_);
});
});