vendredi 25 septembre 2026

À propos

Contact

Tests

Brain Monkey : tester la logique métier d’un plugin sans charger WordPress

Charger tout le cœur WordPress pour tester une simple fonction est lent et souvent inutile. Brain Monkey permet de simuler hooks et fonctions WordPress en tests unitaires purs.

Par Clément Hadrot • 25 septembre 2026 • 5 min de lecture • Aucun commentaire
Brain Monkey : tester la logique métier d'un plugin sans charger WordPress

La suite WP_UnitTestCase est indispensable dès qu’un test touche réellement la base de données, la boucle WordPress ou le système de permissions. Mais une grande partie du code d’un plugin n’a rien à voir avec cela : des fonctions de calcul, de formatage, de validation, qui se contentent d’appeler apply_filters() ou get_option() en passant. Faire démarrer tout WordPress pour tester ce genre de logique est un gaspillage de temps, à raison de plusieurs secondes par exécution de suite.

Le paquet Brain Monkey, construit au-dessus de Mockery, résout ce problème en simulant les fonctions et hooks WordPress sans jamais charger le cœur. Voici comment l’intégrer à une suite PHPUnit existante et écrire des tests réellement isolés.

Pourquoi séparer logique métier et tests d’intégration

Un plugin bien structuré sépare généralement deux types de code : les fonctions qui orchestrent WordPress (enregistrement de hooks, requêtes WP_Query, écriture en base) et les fonctions qui contiennent la logique pure (calculs, transformations de données, règles métier). Les premières ont besoin d’un environnement WordPress réel pour être testées correctement, avec WP_UnitTestCase. Les secondes n’ont besoin que d’isoler les quelques appels WordPress qu’elles font, et Brain Monkey excelle précisément à cela.

Cette séparation, en plus d’accélérer les tests, pousse naturellement vers un code plus découplé : une fonction difficile à tester avec Brain Monkey parce qu’elle mélange trop d’appels WordPress et de logique est souvent une fonction qui gagnerait à être découpée.

Installer Brain Monkey

Le paquet s’installe via Composer, en dépendance de développement :

composer require --dev brain/monkey

Il embarque Mockery, la bibliothèque de mocks la plus utilisée en PHP, et fournit une API dédiée aux spécificités de WordPress : hooks, filtres, fonctions globales comme wp_die() ou __().

L'essentiel à retenir : Des tests qui s'exécutent sans base de données ni bootstrap WordPress ; Des hooks et filtres simulés avec Functions\when() ; Une suite jusqu'à dix fois plus rapide sur la logique pure

Configurer un TestCase dédié

Contrairement à WP_UnitTestCase, Brain Monkey s’utilise avec la classe PHPUnit\Framework\TestCase standard. Il faut initialiser et nettoyer son environnement dans setUp() et tearDown() :

use Brain\Monkey;
use PHPUnit\Framework\TestCase;

class Test_Calcul_Remise extends TestCase {

    protected function setUp(): void {
        parent::setUp();
        Monkey\setUp();
    }

    protected function tearDown(): void {
        Monkey\tearDown();
        parent::tearDown();
    }
}

Beaucoup d’équipes créent une classe abstraite Brain_Monkey_TestCase qui centralise ce setUp()/tearDown(), pour ne pas le répéter dans chaque classe de test.

Simuler une fonction WordPress avec Functions\when()

Supposons une fonction qui applique une remise et loggue le résultat via apply_filters() :

function mon_plugin_calcule_remise( $prix, $pourcentage ) {
    $remise = $prix * ( $pourcentage / 100 );
    return apply_filters( 'mon_plugin_remise_calculee', $prix - $remise, $prix, $pourcentage );
}

Pour tester cette fonction sans charger WordPress, Brain Monkey permet de définir ce que apply_filters() doit retourner :

use Brain\Monkey\Functions;

public function test_applique_la_remise_sans_filtre_actif() {
    Functions\when( 'apply_filters' )->returnArg( 1 );

    $resultat = mon_plugin_calcule_remise( 100, 10 );

    $this->assertEquals( 90.0, $resultat );
}

Functions\when() convient pour les cas simples où l’on veut juste que la fonction WordPress se comporte de façon prévisible. Pour vérifier qu’une fonction WordPress est appelée avec des arguments précis, Functions\expect() est plus adapté.

Vérifier des appels avec Functions\expect()

public function test_declenche_le_filtre_avec_les_bons_arguments() {
    Functions\expect( 'apply_filters' )
        ->once()
        ->with( 'mon_plugin_remise_calculee', 90.0, 100, 10 )
        ->andReturn( 90.0 );

    $resultat = mon_plugin_calcule_remise( 100, 10 );

    $this->assertEquals( 90.0, $resultat );
}

Ce test échoue si apply_filters() n’est pas appelé exactement une fois, avec exactement ces arguments, ce qui en fait un excellent outil pour documenter et verrouiller le contrat d’une fonction.

Tester hooks et actions

Brain Monkey propose aussi des espaces de noms dédiés aux actions et filtres pour tester qu’une fonction les enregistre correctement :

  • Actions\expectAdded( 'init' ) : vérifie qu’un hook est bien accroché à l’action init.
  • Filters\expectApplied( 'the_content' ) : vérifie qu’un filtre donné est bien appliqué.
  • Actions\expectDone( 'save_post' ) : vérifie qu’une action a bien été déclenchée.
use Brain\Monkey\Actions;

public function test_enregistre_le_hook_init() {
    Actions\expectAdded( 'init' )->once();

    mon_plugin_enregistrer_hooks();
}

Les limites de l’approche

Brain Monkey ne remplace pas WP_UnitTestCase : il ne simule pas la base de données, ne recrée pas d’objets WP_Post réels, et ne convient pas pour tester une requête WP_Query complète. Utilisé à mauvais escient, il pousse aussi à écrire des tests qui vérifient l’implémentation plutôt que le comportement, en sur-spécifiant chaque appel de fonction.

Sur nos projets, nous réservons Brain Monkey aux classes de service et aux fonctions de calcul, et nous gardons WP_UnitTestCase pour tout ce qui touche réellement à la persistance des données. Mélanger les deux approches dans une même classe de test crée en général plus de confusion que de clarté.

En résumé

Brain Monkey comble un vide entre les tests unitaires PHP classiques et les tests d’intégration lourds de WP_UnitTestCase : il permet d’isoler la logique métier d’un plugin des appels WordPress environnants, avec des suites nettement plus rapides à l’exécution. Combiné avec une architecture qui sépare clairement orchestration et logique pure, c’est l’un des meilleurs investissements pour garder une suite de tests agréable à faire tourner au quotidien.

Partager :

À propos de l'auteur

Clément Hadrot

Développeur WordPress, passionné par Elementor, le FSE et l’automatisation par IA.

Voir tous ses articles

Dans la même veine

À lire aussi