一、寫個簡單的Angular App
在開始寫測試之前,我們先寫一個簡單的計算App,它會計算兩個數字之和。
程式碼如下:
<html> <head> <script type="text/javascript" src="https://code.angularjs.org/1.4.0-rc.2/angular.min.js"></script> </head> <body> <!-- This div element corresponds to the CalculatorController we created via the JavaScript--> <div ng-controller="CalculatorController"> <input ng-model="x" type="number"> <input ng-model="y" type="number"> <strong>{{z}}</strong> <!-- the value for ngClick maps to the sum function within the controller body --> <input type="button" ng-click="sum()" value="+"> </div> </body> <script type="text/javascript"> // Creates a new module called 'calculatorApp' angular.module('calculatorApp', []); // Registers a controller to our module 'calculatorApp'. angular.module('calculatorApp').controller('CalculatorController', function CalculatorController($scope) { $scope.z = 0; $scope.sum = function() { $scope.z = $scope.x + $scope.y; }; }); // load the app angular.element(document).ready(function() { angular.bootstrap(document, ['calculatorApp']); }); </script> </html>
二、簡單說說裡面涉及的一些基本概念:
module
它是用於創建,回收模組的地方 。我們建立一個名為calculatorApp新的模組,我們並將元件加入這個模組。
angular.module('calculatorApp', []);
關於第二個參數?第二個參數必須的,表示我們正在創造一個新的模組。如果需要我們的應用程式有其他的依賴,我們可以將它們['ngResource','ngCookies']傳入進去。 第二個參數的存在的表示這是一個請求傳回的模組的實例。
從概念上講,它本來就是類似下面的意思:
* angular.module.createInstance(name, requires); * angular.module.getInstance(name)
然而實際我們是這樣寫的:
* angular.module('calculatorApp', []); // i.e. createInstance * angular.module('calculatorApp'); // i.e. getInstance
.org/api/ng/function/angular.module
2.給module添加controller
接著我們給angular module的示例添加一個controllerangular.module('calculatorApp').controller('CalculatorController', function CalculatorController($scope) { $scope.z = 0; $scope.sum = function() { $scope.z = $scope.x + $scope.y; }; });
3.連接視圖中的元素
<div ng-controller="CalculatorController"> <input ng-model="x" type="number"> <input ng-model="y" type="number"> <strong>{{z}}</strong> <!-- the value for ngClick maps to the sum function within the controller body --> <input type="button" ng-click="sum()" value="+"> </div>
三、新增測試
angular.module('calculatorApp').controller('CalculatorController', function CalculatorController($scope) { $scope.z = 0; $scope.sum = function() { $scope.z = $scope.x + $scope.y; }; });
describe('calculator', function () { beforeEach(angular.mock.module('calculatorApp')); var $controller; beforeEach(angular.mock.inject(function(_$controller_){ $controller = _$controller_; })); describe('sum', function () { it('1 + 1 should equal 2', function () { var $scope = {}; var controller = $controller('CalculatorController', { $scope: $scope }); $scope.x = 1; $scope.y = 2; $scope.sum(); expect($scope.z).toBe(3); }); }); });
開始前我們需要引入ngMock,我們在測試的程式碼加入$angular.mock
開始前我們需要引入ngMock,我們在測試的程式碼加入模組提供了一種機制進行諸如以及虛擬的service進行單元測試。
四、如何取得controller的實例
使用ngMock我們可以註冊一個calculator app實例。beforeEach(angular.mock.module('calculatorApp'));
beforeEach(angular.mock.inject(function(_$controller_) { $controller = _$controller_; }));
一旦app載入完了,我們使用了inject函數,$controller service可以取得 CalculatorController 的實例。
var controller = $controller('CalculatorController', { $scope: $scope });
五、如何get/set一個物件的屬性
在上篇程式碼中我們已經可以取得一個controller的實例,在括號的第二個參數實際上是controller只有自己,我們的controller只有自己一個參數 $scope物件function CalculatorController($scope) { ... }
var $scope = {}; var controller = $controller('CalculatorController', { $scope: $scope }); // set some properties on the scope object $scope.x = 1; $scope.y = 2;
我們設定x,y的值,模擬剛才的gif中的所顯示的一樣。我們同意也可以讀取物件中的屬性,就像下面這段測驗的斷言:
expect($scope.z).toBe(3);
六、如何呼叫$scope裡面的函數
最後一件事情就是我們如何模擬使用者的點擊,就像我們在絕大多數JS中使用的一致,,其實就是簡單的呼叫函數就行,$scope.sum();