2016-11-16 82 views
3

Hello stackoverflow社區。如何在調用父組件的方法的組件中測試函數

我正在使用組件結構並正在編寫一些單元測試的Angular項目(1.5.6)。我仍然學習了很多關於單元測試的知識 - 尤其是與Angular有關的問題 - 並且希望我可以請求你爲下列問題提供幫助:

我嘗試測試一個組件,它從它的父組件接收一個回調方法。我試圖嘲笑方法foo(參見下面的代碼示例)。而不幸的是這個方法調用父控制器。

所以當我嘗試測試它時,它抱怨說方法是未定義的。然後我想我可以用spyOn嘲笑它,但後來我得到了錯誤Error: <spyOn> : foobar() method does not exist

所以我覺得我無法嘲笑這種方法。

模塊:

angular.module("myApp") 
.component("sample", { 
    "templateUrl": "components/sample/sample.html", 
    "controller": "SampleController", 
    "controllerAs": "sampleCtrl", 
    "bindings": { 
     "config": "<", 
     "foobar": "&" 
    } 
}) 
.controller("SampleController", 
      ["$scope", 
    function($scope) { 
     this.isActive = true; 

     this.foo = function() { 
      // do stuff 
      this.isActive = false; 

      // also do 
      this.foobar(); 
     }; 
    } 
); 

單元測試

describe("Component: SampleComponent", function() { 

    beforeEach(module("myApp")); 

    var sampleComponent, scope, $httpBackend; 

    beforeEach(inject(function($componentController, $rootScope, _$httpBackend_) { 
     scope = $rootScope.$new(); 
     sampleComponent = $componentController("sample", { 
      "$scope": scope 
     }); 
     $httpBackend = _$httpBackend_; 
    })); 

    it("should do set isActive to false on 'foo' and call method...", function() { 
     spyOn(sampleComponent, "foobar") 

     expect(sampleComponent.isActive).toBe(true); 
     expect(sampleComponent).toBe(""); 
     expect(sampleComponent.foobar).not.toHaveBeenCalled(); 

     sampleComponent.foo(); 

     expect(sampleComponent.foobar).toHaveBeenCalled(); 
     expect(sampleComponent.foobar.calls.count()).toBe(1); 
     expect(sampleComponent.isActive).toBe(false); 
    }); 
}); 

我希望我沒有任何錯誤添加到這一點,但是這上面是什麼,我想做。歡迎任何建議,如果方法錯誤或需要更多信息,請告訴我!

+1

'$ componentController'僅用於測試組件控制器。所以你必須把一個存根分配給'foobar'屬性。 – estus

+0

我只是認爲這可以工作,因爲'foobar'被賦值給控制器的作用域this.foobar()'。 @estus你的存根意味着什麼?一個方法? – skofgar

+1

存根是一個空的間諜,就像'sampleComponent.foobar = jasmine.createSpy()'。 $ componentController是$ controller的包裝器。它只是從定義的組件控制器創建一個控制器,並忽略其他所有內容。要使用綁定完全測試一個組件,它應該使用'$ compile'等進行編譯,與本例中的指令沒有區別。 – estus

回答

1

在@estus的幫助之後(請參閱相關評論) - 我瞭解到我可以使用createSpy解決此問題。

it("should do set isActive to false on 'foo' and call method...", function() { 
     sampleComponent.foobar = jasmine.createSpy(); 

     expect(sampleComponent.isActive).toBe(true); 
     expect(sampleComponent).toBe(""); 
     expect(sampleComponent.foobar).not.toHaveBeenCalled(); 

     sampleComponent.foo(); 

     expect(sampleComponent.foobar).toHaveBeenCalled(); 
     expect(sampleComponent.foobar.calls.count()).toBe(1); 
     expect(sampleComponent.isActive).toBe(false); 
    }); 

我使用了一些額外的來源是:

相關問題