Pruebas de Autenticación en Login con JavaScript

Clase 11 de 25Curso de End to End Testing para APIs REST con Node.js

Contenido del curso

Pruebas a la API de Fake Store

Pruebas en Entornos de Desarrollo Avanzados

Resumen

Validar que un endpoint de autenticación responda correctamente ante credenciales válidas e inválidas es una de las pruebas más importantes en cualquier API. Aquí se aborda paso a paso cómo construir pruebas end-to-end al endpoint de login, optimizar los hooks de testing y limpiar los logs innecesarios de la terminal para obtener un output claro y profesional.

¿Cómo optimizar los hooks de before each a before all?

Antes de escribir nuevas pruebas, conviene hacer una optimización clave en la configuración del entorno de testing. Los hooks before each y after each ejecutan código antes y después de cada test individual [01:30]. Esto significa que se levanta una nueva instancia de la aplicación por cada prueba, lo cual es innecesario.

Al cambiar a before all y after all, la aplicación se crea una sola vez por bloque describe, es decir, por archivo [02:05]. Todos los tests dentro de ese bloque comparten la misma instancia del servidor. Esto reduce el tiempo de ejecución y el consumo de recursos sin afectar los resultados.

  • Se crea una sola aplicación por archivo de pruebas.
  • Se comparte esa instancia entre todos los tests del describe.
  • Los resultados siguen funcionando de manera normal tras el cambio.

¿Cómo probar un 401 unauthorized en el login?

El primer caso de prueba consiste en enviar credenciales inválidas y verificar que el servidor responda con un status code 401, que significa unauthorized [03:40]. Se crea un archivo nuevo llamado auth.e2e.test.js para separar las pruebas de autenticación de las pruebas de usuarios.

El test envía un email falso como emailfake@gmail.com y un password inventado mediante una petición POST a la ruta /auth/login [04:10]. Como ese usuario no existe en la base de datos, el servidor debe contestar con un 401. Esta prueba valida el comportamiento esperado cuando alguien intenta acceder con datos incorrectos.

¿Cómo validar un login exitoso con status 200?

El segundo caso prueba el flujo correcto: enviar un usuario que sí existe en la base de datos y verificar que la respuesta sea un status code 200 [05:15]. Además del código de respuesta, se validan dos cosas importantes:

  • Que exista un campo access token en la respuesta, usando toBeTruthy() [06:00]. No se puede comparar contra un valor específico porque el token se genera dinámicamente y solo el servidor puede verificar su validez.
  • Que el email del usuario devuelto coincida con el email enviado en la petición.

¿Cómo consultar la base de datos dentro de las pruebas?

Para hacer la validación más robusta, se puede traer información directamente desde los models de la base de datos [07:10]. Por ejemplo, usar models.User.findByPk(1) para obtener un usuario específico y comparar su email con el que devuelve el endpoint. Es importante usar el nombre correcto del modelo tal como se definió en el archivo de configuración; un error de typo como escribir users en lugar de User genera un fallo al intentar leer la propiedad findByPk [09:00].

El password almacenado en la base de datos tiene hash, por lo que no se puede extraer para enviarlo como credencial. Esto implica que el password de prueba debe conocerse de antemano.

¿Cómo verificar que el password no se retorne en la respuesta?

Una buena práctica de seguridad es nunca devolver el password en la respuesta, ni siquiera encriptado [10:45]. Para probarlo, se agrega una aserción que valide que el campo password dentro del objeto user sea undefined.

Si alguien elimina accidentalmente la línea de código que borra el password del objeto de respuesta en el servicio de autenticación, la prueba falla inmediatamente [11:30]. Esto funciona como una red de seguridad que alerta sobre cambios peligrosos en el código.

Para limpiar la terminal de logs innecesarios generados por Sequelize y Express, se condiciona el logger para que solo imprima en consola cuando la variable de entorno NODE_ENV sea igual a dev [08:15]. Así, durante las pruebas, el output muestra únicamente los resultados de los tests.

  • Condición config.env === 'dev' para activar logs de base de datos.
  • Mismo criterio para el middleware de manejo de errores de Express.
  • Terminal limpia con solo información relevante de las pruebas.

¿Has implementado pruebas que validen que información sensible no se filtre en las respuestas de tu API? Comparte tu experiencia y las estrategias que utilizas para proteger datos críticos en tus endpoints.