これは、送信機能を備えたコントローラーです。
$scope.submit = function(){
$http.post('/api/project', $scope.project)
.success(function(data, status){
$modalInstance.dismiss(true);
})
.error(function(data){
console.log(data);
})
}
}
これは私のテストです
it('should make a post to /api/project on submit and close the modal on success', function() {
scope.submit();
$httpBackend.expectPOST('/api/project').respond(200, 'test');
$httpBackend.flush();
expect(modalInstance.dismiss).toHaveBeenCalledWith(true);
});
私が得るエラーは次のとおりです:
Error: Unexpected request: GET views/appBar.html
views/appBar.htmlは私のtemplateUrlです:
.state('project', {
url: '/',
templateUrl:'views/appBar.html',
controller: 'ProjectsCtrl'
})
だから何とかui-routerは私の$ httpBackendが私のsubmit関数の代わりにこれを指すようにしています。 $ httpBackendを使用するすべてのテストで同じ問題があります。
これに対する解決策はありますか?
この要点を取り上げてください https://Gist.github.com/wilsonwc/8358542
angular.module('stateMock',[]);
angular.module('stateMock').service("$state", function($q){
this.expectedTransitions = [];
this.transitionTo = function(stateName){
if(this.expectedTransitions.length > 0){
var expectedState = this.expectedTransitions.shift();
if(expectedState !== stateName){
throw Error("Expected transition to state: " + expectedState + " but transitioned to " + stateName );
}
}else{
throw Error("No more transitions were expected! Tried to transition to "+ stateName );
}
console.log("Mock transition to: " + stateName);
var deferred = $q.defer();
var promise = deferred.promise;
deferred.resolve();
return promise;
}
this.go = this.transitionTo;
this.expectTransitionTo = function(stateName){
this.expectedTransitions.Push(stateName);
}
this.ensureAllTransitionsHappened = function(){
if(this.expectedTransitions.length > 0){
throw Error("Not all transitions happened!");
}
}
});
Test/mockフォルダーのstateMockというファイルに追加し、まだ取得していない場合は、そのファイルをカルマ構成に含めます。
テスト前のセットアップは次のようになります。
beforeEach(module('stateMock'));
// Initialize the controller and a mock scope
beforeEach(inject(function ($state //other vars as needed) {
state = $state;
//initialize other stuff
}
次に、テストで追加する必要があります
state.expectTransitionTo('project');
nit Testing UI Router に関するこのGithubの問題は、何が起こっているかをより完全に説明しています。
問題は、$httpBackend.flush()
がブロードキャストをトリガーし、それがstateProvider
のその他の場合をトリガーすることです。
上記のGithubスレッドの@darinclarkで言及されているように、簡単な解決策は次のセットアップを行うことです。これは、状態遷移をテストする必要がない場合に有効です。それ以外の場合は、- @ rosswil's answer に目を向けてください。これは Githubの@Vratislav answer に触発されたものです。
beforeEach(module(function ($urlRouterProvider) {
$urlRouterProvider.otherwise(function(){return false;});
}));
[〜#〜]編集済み[〜#〜]
これをコメントで報告してくれたChris Tに感謝します。v0.2.14以降ですか?これを行う最良の方法は、使用することです
beforeEach(module(function($urlRouterProvider) {
$urlRouterProvider.deferIntercept();
}));
正しいソリューションにあるようにGistファイルを追加したくない場合は、$ httpBackendに「when」条件を追加して、次のようなビューのGETを無視できます。
$httpBackend.when("GET", function (url) {
// This condition works for my needs, but maybe you need to improve it
return url.indexOf(".tpl.html") !== -1;
}).passThrough();
あなたがコメントしたのと同じエラーがあります、コールサービスの後、彼らはそれ以外の場合はui-routeのURLについて尋ねます。
呼び出しの問題を解決するために、テストでのその他のui-routeはinject $ state in beforeach statmentです。私のテストでは、$ stateを使用する意味がありません。
Ui.routerに依存しない独自のモジュールにサービスを移動します。メインアプリがこのモジュールに依存するようにします。テストするときは、メインアプリをテストしないで、サービスが含まれているモジュールをテストします。このモジュールはui.routerについて何も知らないため、状態プロバイダーは状態/ルートを変更しようとしません。これは私のために働いた。