Tests con ExUnit

ExUnit es un framework para escribir tests en Elixir. En este vídeo, por qué los tests nos vienen bien, y un ejemplo rápido de cómo crear tests con Elixir que profundizaremos en siguientes episodios.

Los tests son una herramienta fundamental para asegurarnos de que nuestras funciones se comportan tal y como esperamos. En Elixir, el sistema de testeo más utilizado es ExUnit, que nos permite automatizar estas pruebas y mantener nuestro código fiable a lo largo del tiempo.

Un test no es más que un pequeño bloque de código que utiliza las funciones que hemos programado para comprobar que ciertas condiciones se cumplen. Por ejemplo, si tenemos una función llamada suma que recibe dos parámetros y devuelve su suma, un test básico podría verificar que suma(2, 2) devuelve efectivamente 4. Si la función devuelve lo esperado, el test pasa; si no, nos indica que hay un error que debemos corregir.

En proyectos reales, los tests son aún más importantes. Si estamos desarrollando un servidor web con Phoenix, por ejemplo, podemos escribir tests que verifiquen que al hacer una petición a /users recibimos un JSON con código HTTP 200. En aplicaciones que trabajan con operaciones matemáticas, como multiplicar matrices, los tests nos ayudan a comprobar que los resultados son correctos según la lógica que hemos definido.

Aunque en Elixir contamos con la REPL (IEx) para probar funciones de forma interactiva, automatizar estas pruebas con ExUnit es mucho más eficiente. La REPL es útil para experimentar y validar ideas rápidamente, pero escribir tests automatizados nos permite ejecutar todas las pruebas de forma rápida y sin errores humanos, ya que no tenemos que reescribir comandos cada vez que queremos verificar algo.

Además, una suite de tests puede correr decenas o incluso cientos de pruebas en segundos, lo que es especialmente valioso cuando nuestro proyecto crece y tiene muchos módulos y funciones. Esto nos ayuda a detectar rápidamente si un cambio en el código ha roto alguna funcionalidad que antes funcionaba correctamente.

Cuando creamos un proyecto con Mix, automáticamente se genera una carpeta test junto a la carpeta lib donde ponemos nuestro código. En test encontramos un archivo llamado test_helper.exs, que se encarga de arrancar ExUnit con ExUnit.start(). Este archivo no suele modificarse mucho, pero es esencial para que el sistema de tests funcione correctamente.

Los tests se escriben en archivos que terminan en -test.exs. Por ejemplo, si tenemos un módulo Calculadora en lib/calculadora.ex, el archivo de tests correspondiente será test/calculadora_test.exs. Dentro de este archivo definimos un módulo, por ejemplo CalculadoraTest, y usamos use ExUnit.Case para poder utilizar las funciones y macros que ExUnit nos ofrece.

Un test se define con la macro test que recibe un nombre descriptivo y un bloque de código donde hacemos las comprobaciones. Para verificar que una condición es verdadera usamos assert. Por ejemplo:

defmodule CalculadoraTest do
  use ExUnit.Case

  test "suma dos números" do
    assert Calculadora.suma(2, 2) == 4
  end
end

Al ejecutar mix test, ExUnit corre todos los tests y nos muestra un punto por cada test que pasa correctamente. Si algún test falla, nos indica cuál fue, qué esperaba y qué recibió realmente, facilitando la localización del error.

Por ejemplo, si escribimos mal la función resta y en lugar de restar multiplica, el test correspondiente fallará y nos mostrará que el resultado no es el esperado:

defmodule Calculadora do
  def resta(a, b) do
    a * b  # Error intencionado
  end
end

defmodule CalculadoraTest do
  use ExUnit.Case

  test "resta dos números" do
    assert Calculadora.resta(3, 2) == 1
  end
end

Al correr mix test, veremos un error que nos indica que el resultado fue 6 en lugar de 1. Esto nos permite corregir rápidamente la función y asegurarnos de que el código cumple con la especificación.

La gran ventaja de tener una suite de tests es que podemos modificar nuestro código con confianza, sabiendo que si algo se rompe, los tests nos lo harán saber inmediatamente. Esto es especialmente útil cuando el proyecto crece y tiene cientos de funciones, ya que probarlas manualmente sería inviable.

En definitiva, ExUnit nos ofrece una forma rápida, segura y automatizada de mantener nuestro código en buen estado, detectando errores antes de que lleguen a producción y facilitando el desarrollo de software de calidad.

Lista de reproducción
  1. 1
    mix
    10 minutos
  2. 2
    Documentando código: comentarios, docs y moduledocs
    10 minutos
  3. 3
    Atributos de módulo
    9 minutos
  4. 4
    Dependencias
    12 minutos
  5. 5
    Un ejemplo práctico de módulo útil
    13 minutos
  6. 6
    Alias e import
    10 minutos
  7. 7
    Sobre las macros, require y use
    11 minutos
  8. 8
    Typespecs (parte 1, usando tipos básicos)
    10 minutos
  9. 9
    Typespecs (parte 2, tipos propios y t())
    11 minutos
  10. 10
    Comportamientos
    11 minutos
  11. 11
    Tratamiento de errores con rescue
    8 minutos
  12. 12
    Elevando errores con raise
    8 minutos
  13. 13
    with
    14 minutos
  14. 14
    Sigilos
    8 minutos
  15. 15
    Tests con ExUnit
    12 minutos
  16. 16
    Más particularidades de ExUnit
    13 minutos
  17. 17
    Microservicios en Elixir con Plug
    11 minutos
  18. 18
    Cómo Plug.Router te ayuda a escribir microservicios en Elixir
    14 minutos
  19. 19
    ¿Cómo hacer rutas dinámicas en Phoenix y Plug?
    13 minutos