tutorial test run karma jasmine matcher

test - Jasmine toEqual para objetos complejos(mezclado con funciones)



karma js (5)

Extendiendo la respuesta de @Vlad Magdalin, esto funcionó en Jasmine 2:

http://jasmine.github.io/2.0/custom_matcher.html

beforeEach(function() { jasmine.addMatchers({ toDeepEqual: function(util, customEqualityTesters) { return { compare: function(actual, expected) { var result = {}; result.pass = _.isEqual(actual, expected); return result; } } } }); });

Si estás usando Karma, ponlo en la devolución de llamada de inicio:

callback: function() { // Add custom Jasmine matchers. beforeEach(function() { jasmine.addMatchers({ toDeepEqual: function(util, customEqualityTesters) { return { compare: function(actual, expected) { var result = {}; result.pass = _.isEqual(actual, expected); return result; } } } }); }); window.__karma__.start(); });

Actualmente, tengo una función que algunas veces devuelve un objeto con algunas funciones adentro. Cuando se usa expect(...).toEqual({...}) no parece coincidir con esos objetos complejos. Objetos que tienen funciones o la clase File (desde el archivo de tipo de entrada), simplemente no puede. ¿Cómo superar esto?


Pruebe la función Underscore _.isEqual () :

expect(_.isEqual(obj1, obj2)).toEqual(true);

Si eso funciona, puedes crear un marcador personalizado :

this.addMatchers({ toDeepEqual: function(expected) { return _.isEqual(this.actual, expected); }); });

Entonces puedes escribir especificaciones como estas:

expect(some_obj).toDeepEqual(expected_obj);


Como Vlad Magdalin señaló en los comentarios, haciendo el objeto de una cadena JSON, puede ser tan profundo como lo es, y las funciones y la clase File / FileList. Por supuesto, en lugar de toString() en la función, podría llamarse ''Función''

function replacer(k, v) { if (typeof v === ''function'') { v = v.toString(); } else if (window[''File''] && v instanceof File) { v = ''[File]''; } else if (window[''FileList''] && v instanceof FileList) { v = ''[FileList]''; } return v; } beforeEach(function(){ this.addMatchers({ toBeJsonEqual: function(expected){ var one = JSON.stringify(this.actual, replacer).replace(/(//t|//n)/g,''''), two = JSON.stringify(expected, replacer).replace(/(//t|//n)/g,''''); return one === two; } }); }); expect(obj).toBeJsonEqual(obj2);


Si alguien está usando node.js como yo, el siguiente método es el que uso en mis pruebas de Jasmine cuando solo me interesa comparar las propiedades simples sin tener en cuenta todas las funciones. Este método requiere json-stable-stringify que se usa para ordenar las propiedades del objeto antes de la serialización.

Uso:

var stringify = require(''json-stable-stringify''); var obj1 = { func: function() { }, str1: ''str1 value'', str2: ''str2 value'', nest1: { nest2: { val1:''value 1'', val2:''value 2'', someOtherFunc: function() { } } } }; var obj2 = { str2: ''str2 value'', str1: ''str1 value'', func: function() { }, nest1: { nest2: { otherFunc: function() { }, val2:''value 2'', val1:''value 1'' } } }; it(''should compare object properties'', function () { expect(stringify(obj1)).toEqual(stringify(obj2)); });


así es como lo hice usando la sintaxis de Jasmine 2 .

Creé un módulo customMatchers en ../support/customMatchers.js (me gusta hacer módulos).

"use strict"; /** * Custom Jasmine matchers to make unit testing easier. */ module.exports = { // compare two functions. toBeTheSameFunctionAs: function(util, customEqualityTesters) { let preProcess = function(func) { return JSON.stringify(func.toString()).replace(/(//t|//n)/g,''''); }; return { compare: function(actual, expected) { return { pass: (preProcess(actual) === preProcess(expected)), message: ''The functions were not the same'' }; } }; } }

Que luego se usa en mi prueba de la siguiente manera:

"use strict"; let someExternalFunction = require(''../../lib/someExternalFunction''); let thingBeingTested = require(''../../lib/thingBeingTested''); let customMatchers = require(''../support/customMatchers''); describe(''myTests'', function() { beforeEach(function() { jasmine.addMatchers(customMatchers); let app = { use: function() {} }; spyOn(app, ''use''); thingBeingTested(app); }); it(''calls app.use with the correct function'', function() { expect(app.use.calls.count()).toBe(1); expect(app.use.calls.argsFor(0)).toBeTheSameFunctionAs(someExternalFunction); }); });