Si vous ne l’avez pas encore lu, allez lire l’article Tester ses modules Drupal 7.

Les tests fonctionnels via Simpletest sont gérés par la class DrupalUnitTestCase qu’il faut ensuite étendre dans son module.

Drupal va exécuter chaque fonction commençant par test définie dans la class.

Contrairement aux tests fonctionnels, Drupal ne va pas reconstruire d’environnement pour lancer ce type de tests. Il va se contenter de charger les modules spécifiés dans l’initialisation et lancer les fonctions donner avec les bons paramètres.

Les fonctions testées ne doivent donc pas dépendre de données récupérées en base. C’est le retour de la fonction qui sera ensuite vérifié.

Mise en place des tests

Comme pour les tests fonctionnels il faut étendre une class de base de Drupal : DrupalUnitTestCase

<?php

class MyModuleUnitTestCase extends DrupalUnitTestCase {}

On va également déclarer la méthode getInfo().

<?php

public static function getInfo() {
  // Note: getInfo() strings should not be translated.
  return array(
    'name' => 'My module unit tests',
    'description' => 'Test that utilities functions used in my_module modules work fine.',
    'group' => 'My module group',
  );

}

Déclaration les modules dont on va charger le code via la méthode setUp()

<?php

/**
 * Set up the test environment.
 *
 * Note that we use drupal_load() instead of passing our module dependency
 * to parent::setUp(). That's because we're using DrupalUnitTestCase, and
 * thus we don't want to install the module, only load it's code.
 *
 * Also, DrupalUnitTestCase can't actually install modules. This is by
 * design.
 */
public function setUp() {
  drupal_load('module', 'my_module');
  parent::setUp();
}

et enfin déclarer nos fonction de test qui doivent commencer par le mot clé test.

<?php

/**
 * Test my_module_check_login().
 *
 * Note that no environment is provided; we're just testing the correct
 * behavior of a function when passed specific arguments.
 */
public function testMyModuleCheckLoginFunction() {
  // Your tests
}

Exemple

On souhaite pouvoir tester le retour de la fonction suivante :

<?php

/**
 * Check the user login match the regex.
 *
 * @return
 */
function my_module_check_login($login) {
  // Extract all regex defined.
  $regex_list = explode(';', '/^[0-9]{7}[A-Z]$/i;/^(P|A|Z|F|E|S)[A-Z]{3}[0-9]{5}$/i;/^.*domain\.fr$/i');

  // Check if the login verify at least one regex.
  foreach ($regex_list as $regex) {

    // If there is one result.
    if (preg_match($regex, $login)) {
      return TRUE;
    }
  }
  return FALSE;
}

ce qui pourrait donner un test comme ceci :

<?php

/**
 * Test my_module_check_login().
 *
 * Note that no environment is provided; we're just testing the correct
 * behavior of a function when passed specific arguments.
 */
public function testMyModuleCheckLoginFunction() {
  $result = my_module_check_login(NULL);
  // Note that test assertion messages should never be translated, so
  // this string is not wrapped in t().
  $message = 'A NULL value should return FALSE.';
  $this->assertFalse($result, $message);

  $result = my_module_check_login('');
  $message = 'An empty string should return FALSE.';
  $this->assertFalse($result, $message);

  $result = my_module_check_login('[email protected]');
  $message = 'An string with @domain.fr should return TRUE.';
  $this->assertTrue($result, $message);

  $result = store_user_check_login('@domain.fr');
  $message = 'An string with @domain.fr should return TRUE.';
  $this->assertTrue($result, $message);

  $result = my_module_check_login('AZER01234');
  $message = 'A string that looks like a CP code should return TRUE.';
  $this->assertTrue($result, $message);

}