Skip to content

Instantly share code, notes, and snippets.

@sidwood
Created June 7, 2013 16:55
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save sidwood/5730701 to your computer and use it in GitHub Desktop.
Save sidwood/5730701 to your computer and use it in GitHub Desktop.
An example of asserting that a test double is implementing it's role/interface correctly in AngularJS test suites suing Jasmine. http://www.meetup.com/AngularJS-London/events/106468592/
// client/test/support/matchers.js
beforeEach(function() {
this.addMatchers({
toRespondTo: function(method) {
return void 0 !== this.actual[method];
}
});
});
// client/app/modules/productsList.js
angular.module('productsList', [
'productsResource',
'templates'
])
.config(function($routeProvider) {
$routeProvider
.when('/products', {
controller: 'ProductListCtrl',
templateUrl: 'productsList.html'
});
})
.controller('ProductsListCtrl', function($scope, productsResource) {
$scope.products = [];
productsResource.query().then(function(res) {
$scope.products = res.data;
});
});
// client/test/modules/productsListSpec.js
describe('Module productsList:', function () {
var productsResource = {};
beforeEach(module('productsList'));
beforeEach(function() {
productsResource.rolePlayer = sinon.stub({ query: function() {} });
});
describe('mockProductsResource', function () {
implementsResourcefulRole(productsResource);
});
describe('ProductsListCtrl', function() {
var $controller,
$scope;
beforeEach(inject(function($rootScope, _$controller_) {
$scope = $rootScope.$new();
$controller = _$controller_;
}));
it('scopes the "products" collection', function() {
productsResource.rolePlayer.query.returns({
then: function(callback) {
callback({ data: [{ foo: 'bar' }] });
}
});
$controller('ProductsListCtrl', {
$scope: $scope,
productsResource: productsResource.rolePlayer
});
expect($scope.products).toEqual([{ foo: 'bar' }]);
});
});
});
// client/app/modules/productsResource.js
angular.module('productsResource', [])
.factory('productsResource', function($http) {
function query() {
return $http.get('/api/products');
}
return {
query: query
};
});
// client/test/modules/productsResourceSpec.js
describe('Module productsResource:', function() {
beforeEach(module('productsResource'));
describe('productsResource', function() {
var productsResource = {},
mockBackend;
beforeEach(module('productsResource'));
beforeEach(inject(function($injector, _$httpBackend_) {
productsResource.rolePlayer = $injector.get('productsResource');
mockBackend = _$httpBackend_;
}));
it('retrieves a collection of products', function() {
var promise;
mockBackend.expectGET('/api/products').respond([{ foo: 'bar' }]);
promise = productsResource.rolePlayer.query();
promise.then(function(res) {
expect(res.data).toEqual([{ foo: 'bar' }]);
});
mockBackend.flush();
});
implementsResourcefulRole(productsResource);
});
});
// client/test/roles/resourcefulSpec.js
function implementsResourcefulRole(context){
describe('[Resourceful Role]', function () {
var rolePlayer;
beforeEach(function() {
rolePlayer = context.rolePlayer;
});
it('honours the "resourceful" interface', function() {
// expect(rolePlayer).toRespondTo('get');
// expect(rolePlayer).toRespondTo('save');
expect(rolePlayer).toRespondTo('query');
// expect(rolePlayer).toRespondTo('remove');
// expect(rolePlayer).toRespondTo('delete');
});
});
}
// client/testem.json
{
"framework": "jasmine",
"launch_in_dev": [
"chrome"
],
"serve_files": [
"test/support/*.js",
"vendor/jquery/jquery.js",
"vendor/lodash/lodash.js",
"vendor/angular/angular.js",
"vendor/angular-mocks/angular-mocks.js",
"tmp/.scratch/templates.js",
"app/modules/**/*.js",
"test/roles/**/*.js",
"test/modules/**/*.js"
],
"src_files": [
"tmp/.scratch/templates.js",
"app/modules/**/*.js",
"test/**/*.js"
]
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment