Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

253
Vistas
Jasmine: cómo probar funciones que solo deben llamarse una vez (ejecutadas a través de una variable de cierre)

Estoy usando un cierre para asegurarme de que algo solo se llame una vez:

 var pageDOM = (function() { var mounted = false return { initializePage: function() { if (mounted == false) { pageDOM.addBoxes(); mount = true } pageDOM.otherInitProcedures(); }, otherFunction: function() { } } })();

No estoy seguro de cuál es la forma correcta de pensar en las pruebas unitarias pageDOM.initializePage . Las especificaciones de Jasmine se ejecutan en orden aleatorio, y creo que es importante mantener esto para probar la integridad (es decir, NO me gustaría imponer un orden). Este es mi código de especificación:

 describe("pageDOM", function() { describe("initializePage", function() { beforeEach(function() { spyOn(pageDOM, "addBoxes") spyOn(pageDOM, "otherInitProcedures") }) describe("calling initializePage first time", function() { beforeEach(function() { pageDOM.initializePage(); }) it("should call both functions", function() { expect(pageDOM.otherInitProcedures).toHaveBeenCalled() expect(pageDOM.addBoxes).toHaveBeenCalled() }) describe("calling initializePage again", function() { beforeEach(function() { pageDOM.initializePage(); }) it("should only call otherInitProcedures", function() { expect(pageDOM.otherInitProcedures).toHaveBeenCalled() expect(pageDOM.addBoxes).not.toHaveBeenCalled() }) }) }) }) })

El problema es que si las especificaciones no se ejecutan en orden, ambas fallarán. ¿Cuál es una manera de probar esto, o debería incluso intentar probar esto?

about 4 years ago · Juan Pablo Isaza
3 Respuestas
Responde la pregunta

0

Asignaría los espías a las variables y restablecería los espías en un gancho afterEach .

Algo como esto (sigue el !! en los comentarios):

 describe("pageDOM", function() { describe("initializePage", function() { // !! initialize these variables let addBoxesSpy; let otherInitProceduresSpy; beforeEach(function() { // !! assign the variables addBoxesSpy = spyOn(pageDOM, "addBoxes") otherInitProceduresSpy = spyOn(pageDOM, "otherInitProcedures") }) describe("calling initializePage first time", function() { beforeEach(function() { pageDOM.initializePage(); }) it("should call both functions", function() { expect(pageDOM.otherInitProcedures).toHaveBeenCalled() expect(pageDOM.addBoxes).toHaveBeenCalled() }) describe("calling initializePage again", function() { beforeEach(function() { pageDOM.initializePage(); }) it("should only call otherInitProcedures", function() { expect(pageDOM.otherInitProcedures).toHaveBeenCalled() expect(pageDOM.addBoxes).not.toHaveBeenCalled() }) }) }) // !! Reset the spies in an afterEach afterEach(() => { addBoxesSpy.calls.reset(); otherInitProceduresSpy.calls.reset(); }); }) })

Después de restablecer las llamadas a lo que está espiando, el orden ya no debería importar.

about 4 years ago · Juan Pablo Isaza Denunciar

0

Entonces, su método "pageDOM" está lleno de estado, entonces, ¿por qué usar 2 veces describir y configurar la llamada al método "initializePage" cada vez al conectarlo beforeEach? No tiene sentido. En su lugar, puedes hacer esto:

 describe("pageDOM:initializePage", function() { describe("calling initializePage first time", function() { beforeEach(function() { spyOn(pageDOM, "addBoxes"); spyOn(pageDOM, "otherInitProcedures"); }) it("should call both functions", function() { pageDOM.initializePage(); expect(pageDOM.otherInitProcedures).toHaveBeenCalled() expect(pageDOM.addBoxes).toHaveBeenCalled() }) it("should only call otherInitProcedures", function() { pageDOM.initializePage(); expect(pageDOM.otherInitProcedures).toHaveBeenCalled() expect(pageDOM.addBoxes).not.toHaveBeenCalled() }) }) })

Jasmine ejecuta los bloques dentro de una descripción secuencialmente y también puede obtener los controles deseados. Enlace de stackblitz en funcionamiento para usted (ignore otros casos de prueba)

about 4 years ago · Juan Pablo Isaza Denunciar

0

Para hacer que el código sea más comprobable, no iniciaría la función de inmediato.

 var pageDOMConstructor = vfunction() { var mounted = false return { initializePage: function() { if (mounted == false) { pageDOM.addBoxes(); mount = true } pageDOM.otherInitProcedures(); }, otherFunction: function() { } } }; var pageDOM = pageDOMConstructor();

entonces puedes probar pageDOMConstructor fácilmente. Para verificar con qué frecuencia se ha llamado a algo, puede usar toHaveBeenCalledTimes

esto no está del todo completo y puede necesitar algunos pequeños cambios, es solo para darle una idea de cómo resolver esto:

 describe("pageDOMConstructor", function () { describe("initializePage", function () { // setup variable, its a let because it will be reset before every test let pageDom; beforeEach(function () { pageDom = pageDOMConstructor(); spyOn(pageDOM, "addBoxes"); spyOn(pageDOM, "otherInitProcedures"); }); it("should call both functions when calling initializePage first time", function () { pageDOM.initializePage(); expect(pageDOM.otherInitProcedures).toHaveBeenCalledTimes(1); expect(pageDOM.addBoxes).toHaveBeenCalledTimes(1); }); it("should only call otherInitProcedures when calling initializePage again", function () { pageDOM.initializePage(); // you could remove these two lines because they are in the other test expect(pageDOM.otherInitProcedures).toHaveBeenCalledTimes(1); expect(pageDOM.addBoxes).toHaveBeenCalledTimes(1); pageDOM.initializePage(); expect(pageDOM.otherInitProcedures).toHaveBeenCalledTimes(1); expect(pageDOM.addBoxes).not.toHaveBeenCalledTimes(1); }); }); });

Cada it debe tratarse como una prueba separada, y deben ser completamente autosuficientes, con algunas excepciones como beforeEach

Cuando el código es difícil de probar, a menudo es una señal de que podría beneficiarse de refactorizarlo un poco. Descubrí que el código comprobable es igual a un código usable y flexible en producción.

about 4 years ago · Juan Pablo Isaza Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda