PHPUnit

> Temas > PHPUnit
Editar

PHPUnit es el framework de pruebas más extendido para PHP. Es una biblioteca de software que nos permite implementar los test unitarios de las aplicaciones de una manera sencilla y avanzada, para el lenguaje PHP.

PHPUnit es un framework de pruebas. Esto quiere decir, un marco de trabajo para todas las actividades relacionadas con el testing de las aplicaciones. Forma parte de la familia de X-Unit, en este caso construido para las pruebas en PHP.

Con PHPUnit puedes desarrollar de una manera cómoda y avanzada las pruebas de tus aplicaciones desarrolladas con PHP, con lo que puedes conseguir software más robusto y confiable. Está orientado principalmente a lo que son las pruebas unitarias, pero también nos ofrece muchas funcionalidades para soportar las pruebas funcionales o el test de integración.

Dentro de los frameworks de pruebas para PHP, PHPUnit es el más tradicional y el más extendido. Existe una alternativa que es Pest, más nueva aunque todavía con una comunidad bastante menor.

Más información:

PHPUnit
Sitio oficial: https://phpunit.de
Nombres alternativos: PHP Unit Año de lanzamiento: 2001 Autor/es: Sebastian Bergmann Lenguaje desarrollo: PHP Licencia: BSD-3-Clause Plataforma/s: PHP Paradigmas: Pruebas del software, Programación Orientada a Objetos

Cómo instalar PHPUnit

Existen diversos medios para instalar PHPUnit y puedes elegir el que prefieras. La primera opción que ofrecen en su sitio web es instalarlo vía la descarga del archivo ejecutable de PHP (PHAR):

wget -O phpunit https://phar.phpunit.de/phpunit-11.phar

Luego debemos darle permisos de ejecución al ejecutable:

chmod +x phpunit

Y con ello ya podemos invocar a PHPUnit, de este modo:

./phpunit --version

Instalar vía Composer

Sin embargo, aunque esa sea una vía posible, la manera más frecuente de instalar PHPUnit es mediante Composer, en el proyecto donde lo quieras usar. Esto te obliga a usar Composer, pero realmente los proyectos de PHP modernos lo requieren sí o sí.

composer require --dev phpunit/phpunit

El flag --dev es importante porque define que esta es una dependencia de desarrollo. Con lo que no se instalará en el entorno de producción, algo esencial porque la ejecución de las pruebas no se realiza en el ambiente de producción.

Luego puedes lanzar el comando de ejecución de PHP desde la ruta donde Composer lo ha instalado, a nivel de proyecto:

./vendor/bin/phpunit --version

Ese comando lo lanzarás desde la raíz de tu proyecto, donde encuentras el archivo composer.json. Con esto ya puedes comenzar a trabajar con PHPUnit en tu aplicación, creando tus archivos de test unitarios y ejecutándolos para probar tu software.

Editar

Cómo organizar el proyecto para alojar tus archivos de pruebas

Si estás comenzando con PHPUnit te preguntarás ¿Dónde coloco los archivos de pruebas? ¿Cómo organizo mi proyecto para distinguir el código de mi aplicación y el código de pruebas?

Esto lo podrías hacer de muchas maneras, aunque existen unas convenciones bastante extendidas en el mundo de desarrollo de proyectos y el test. Así que vamos a ver cuál sería esta forma.

Primero vamos a crear archivo de composer.json. (Si ya lo tienes no necesitas hacer este paso) Para eso vamos a usar el comando siguiente:

composer init

Nos hará una serie de preguntas sobre nuestro proyecto que tendremos que responder. Aunque si no sabes algún dato puedes dejar simplemente los valores que te propone como predeterminados, sabiendo que más adelante podrás cambiar perfectamente estos datos editando el archivo composer.json.

Separar los archivos de test y los archivos de tu aplicación

Los archivos de test de un proyecto deben estar siempre separados a los archivos propios de la aplicación, en carpetas totalmente independientes.

  • Generalmente los archivos de test los colocarás en la carpeta tests
  • Los archivos de tu aplicación los puedes poner en cualquier otra carpeta donde te venga bien. Mucha gente usa la carpeta app, src, o incluso pueden separar los archivos de la aplicación en varias carpetas.

Lo importante es que tengas claro dónde vas a colocar tus archivos de cada ámbito y los mantengas separados.

Configurar del sistema de autoload de Composer

El siguiente paso es configurar del sistema de autoload que viene con Composer, lo que te permitirá tener una experiencia de desarrollo más adecuada, ya que no necesitarás hacer el include de cada archivo donde hayas programado cada clase, ni para el código de tu aplicación ni para el código de pruebas.

Composer viene con un archivo llamado vendor/autoload.php, que se genera cuando instalas dependencias haces el composer init. En el archivo composer.json defines reglas de autoload de las clases. Esto se declara mediante la definición de los namespaces de tu proyecto, que generalmente tendrán mucho que ver con la estructura de carpetas que hayas creado.

Dada la estructura que hemos sugerido para nuestro proyecto (nos vamos a centrar en una carpeta tests para las pruebas y src para las clases del proyecto), la configuración que tenemos que colocar en el composer.json es la siguiente:

{
    "autoload": {
        "psr-4": {
            "App\\": "src/"
        }
    },
    "autoload-dev": {
        "psr-4": {
            "Tests\\": "tests/"
        }
    }
}
  • Como ves, App\\ define que el namespace App corresponde a la carpeta src.
  • Por otra parte tenemos Tests\\ que define que el namespace Tests corresponde a la carpeta tests.

Fíjate además que tenemos el psr-4 del namespace Tests en el bloque autoload-dev. Esto se hace así para dependencias y clases que solo se usan en desarrollo, como las pruebas.

Una vez defido el composer.json, o cada vez que cambies las configuraciones del sistema de autoload, debes ejecutar un comando que sirve para generar los archivos de autoload.

composer dump-autoload

Ahora puedes usar clases automáticamente sin necesidad de require o include de cada cosa que quieras traerte.

Archivo vendor/autoload.php

Solo un detalle más y es con respecto al archivo vendor/autoload.php. Este es un archivo esencial para que puedas usar el autoload de Composer. Este archivo es el que permite que Composer registre automáticamente las clases y dependencias definidas en tu proyecto, cargándolas cuando las necesites.

Si estás ejecutando las pruebas PHPUnit este archivo ya se carga por si solo, por lo que no necesitas incluirlo en tu código de test.

Si estás escribiendo un script o archivo PHP que será el punto de entrada de tu aplicación (por ejemplo, index.php o bootstrap.php). generalmente harás el include o require de vendor/autoload.php al principio.

<?php

require __DIR__ . '/vendor/autoload.php'; // Carga el autoloader de Composer

use App\Example;

$example = new Example();
echo $example->oneMethod();

Editar

Cómo es el código de una prueba con PHPUnit

Una vez que ya tienes organizado tu proyecto para comenzar con las pruebas, puedes empezar a desarrollar tu código de tests unitarios con PHPUnit. Pero antes de comenzar puede que te preguntes ¿Qué son los test unitarios?

Cómo es el código de una prueba con PHPUnit

Tests unitarios

Los tests unitarios son uno de los tipos de prueba de software. Se centran en verificar el funcionamiento de las unidades más pequeñas y aisladas de un sistema, generalmente funciones, métodos o clases. Los tests se realizan de forma aislada e independiente, de modo que si un test falla es muy fácil entender qué parte concreta de nuestro software está presentando un problema.

Su objetivo principal es asegurarse de que cada unidad de código funcione según lo esperado bajo diferentes condiciones, validando tanto las entradas como las salidas que son esperadas en cada escenario. De esta manera podemos identificar errores en las etapas tempranas del desarrollo, antes de desplegar los proyectos.

Es muy importante entender que un test unitario no debería depender de otras partes del sistema, como bases de datos, APIs externas o servicios secundarios. Para lograr esto, se suelen utilizar técnicas como mocks o stubs (donde por supuesto PHPUnit también nos ayudará mucho).

Partes de un test

Todo test tiene tres partes fundamentales que debemos entender. Cada una de estas partes estará dentro de cada uno de los métodos de test:

  • Configuración: Es la etapa donde se preparan las condiciones necesarias para ejecutar el test. Aquí se inicializan las variables con datos, se instancian los objetos necesarios y se configuran las dependencias que serán utilizadas durante la prueba.
  • Ejecución: En esta fase, se invoca el código que se desea probar, generalmente un método específico de una clase, que alimentamos con los datos de configuración anteriores como entrada.
  • Aserción: o afirmación, en la que se verifica si el resultado obtenido a raíz de la ejecución cumple con las expectativas predefinidas. Esto se hace comparando los valores reales devueltos por el código con los valores esperados utilizando métodos de afirmación que ofrece el framework de pruebas PHPUint.

A veces alguna de esas partes podría estar implícita en otros pasos, por lo que no siempre se verán de forma clara, aunque en el fondo siempre estarán ahí.

Estas tres etapas tienen varios nombres. Hay personas que se refieren a ellas con las famosas "Tres A": Arrange, Act, Assert. Otros que se referen con los términos: Given-When-Then. En realidad es todo lo mismo, puedes llamarle como quieras pero siempre será así, en cualquier framework de testing y en cualquier tipo de pruebas que estés desarrollando.

Ejemplo de test unitario

Ahora vamos a ver un ejemplo de test unitario creado con PHPUnit, simplemente testimonial, donde podamos ver cómo se aterriza a código. Hemos escrito un código bien sencillo donde esas partes son bien visibles. No siempre es así.

<?php

namespace Tests;

use PHPUnit\Framework\TestCase;
use App\Calculator;

class CalculatorTest extends TestCase
{
    public function testAdd()
    {
        // Arrange / Given: Configurar los datos y la instancia necesaria
        $calculator = new Calculator();
        $a = 2;
        $b = 3;

        // Act / When: Ejecutar el método que se está probando
        $result = $calculator->add($a, $b);

        // Assert / Then: Verificar que el resultado es el esperado
        $this->assertEquals(5, $result);
    }
}

Editar

¿Quieres añadir algo sobre PHPUnit?

Crea artículos, recursos o comparte información sobre PHPUnit

Crear un bloque

Temas relacionados

Preguntas y respuestas de PHPUnit

Se han recibido 0 faqs en PHPUnit

Hacer una pregunta