Symfony2 - Jobeet - Jour 08 - Les tests unitaires

1 1 1 1 1 1 1 1 1 1 Rating 0.00 (0 Votes)
Submit to DeliciousSubmit to DiggSubmit to FacebookSubmit to Google PlusSubmit to StumbleuponSubmit to TechnoratiSubmit to TwitterSubmit to LinkedIn

Les tests dans Symfony

Il existe deux types de tests automatisés dans Symfony : les tests unitaires et les tests fonctionnels. Les tests unitaires vérifient que chaque méthode et fonction fonctionne correctement. Chaque test doit être aussi indépendant que possible des autres. D'autre part, les tests fonctionnels vérifient que l'application résultante se comporte correctement dans son ensemble.

Les tests unitaires seront couverts ce jour, alors que demain sera consacré aux tests fonctionnels.

Symfony2 s'intègre à une bibliothèque indépendante, PHPUnit, pour vous donner un framework de tests riche. Pour exécuter des tests, vous devrez installer PHPUnit 3.5.11 ou une version ultérieure.

Si vous n'avez pas PHPUnit d'installé, exécutez les commandes suivantes :

su
apt-get install phpunit
pear channel-discover pear.phpunit.de
pear channel-discover pear.symfony-project.com
pear channel-discover components.ez.no
pear channel-discover pear.symfony.com
pear update-channels
pear upgrade-all
pear install pear.symfony.com/Yaml
pear install --alldeps phpunit/PHPUnit
pear install --force --alldeps phpunit/PHPUnit
exit

Chaque test - qu'il s'agisse d'un test unitaire ou un test fonctionnel - est une classe PHP qui doit se situer dans un sous-répertoire Tests/ de vos paquets. Si vous suivez cette règle, vous pouvez exécuter tous les tests de votre application avec la commande suivante :

phpunit -c app/

L'option -c indique à PHPUnit de chercher un fichier de configuration dans le répertoire app/. Si vous êtes curieux de connaître les options de PHPUnit, consultez le fichier app/phpunit.xml.dist.

Un test unitaire est généralement un test contre une classe PHP spécifique. Commençons par écrire des tests pour la méthode Jobeet::slugify().

Créez un nouveau fichier, JobeetTest.php, dans le répertoire src/Erlem/JobeetBundle/Tests/Utils. Par convention, le sous-répertoire Tests/ doit répliquer le répertoire de votre paquet. Donc, quand nous testons une classe dans le répertoire Utils/ de notre paquet, nous avons mis le test dans le répertoire Tests/Utils/ :

  • src/Erlem/JobeetBundle/Tests/Utils/JobeetTest.php
<?php

namespace Erlem\JobeetBundle\Tests\Utils;
 
use Erlem\JobeetBundle\Utils\Jobeet;
 
class JobeetTest extends \PHPUnit_Framework_TestCase
{
    public function testSlugify()
    {
        $this->assertEquals('sensio', Jobeet::slugify('Sensio'));
        $this->assertEquals('sensio-labs', Jobeet::slugify('sensio labs'));
        $this->assertEquals('sensio-labs', Jobeet::slugify('sensio labs'));
        $this->assertEquals('paris-france', Jobeet::slugify('paris,france'));
        $this->assertEquals('sensio', Jobeet::slugify(' sensio'));
        $this->assertEquals('sensio', Jobeet::slugify('sensio '));
    }
}

Pour exécuter ce test, vous pouvez utiliser la commande suivante :

phpunit -c app/ src/Erlem/JobeetBundle/Tests/Utils/JobeetTest

Comme tout devrait fonctionner correctement, vous devriez obtenir le résultat suivant :

PHPUnit 4.0.17 by Sebastian Bergmann.

Configuration read from /home/debian/www/jobeet/app/phpunit.xml.dist

.

Time: 225 ms, Memory: 2.75Mb

OK (1 test, 6 assertions)

Pour une liste complète des assertions, vous pouvez consulter la documentation de PHPUnit.

Ajout de tests pour de nouvelles fonctionnalités

Le jeton pour une chaîne vide est une chaîne vide. Vous pouvez le tester, ça va marcher. Mais une chaîne vide dans une URL n'est pas une bonne idée. Nous allons changer la méthode slugify() de sorte qu'elle retourne la chaîne "n-a" dans le cas d'une chaîne vide.

Vous pouvez écrire le premier test, puis mettre à jour la méthode, ou l'inverse. C'est vraiment une question de goût mais l'écriture du test en premier vous donne l'assurance que votre code implémente réellement ce que vous avez prévu:

  •  src/Erlem/JobeetBundle/Tests/Utils/JobeetTest.php
// ...

$this->assertEquals('n-a', Jobeet::slugify(''));

// ...

 Maintenant, si nous réexécutons le test :

phpunit -c app/ src/Erlem/JobeetBundle/Tests/Utils/JobeetTest

Nous aurons un échec :

PHPUnit 4.0.17 by Sebastian Bergmann.

Configuration read from /home/debian/www/jobeet/app/phpunit.xml.dist

Time: 91 ms, Memory: 3.00Mb

There was 1 failure:

1) Erlem\JobeetBundle\Tests\Utils\JobeetTest::testSlugify
Failed asserting that two strings are equal.
--- Expected
+++ Actual
@@ @@
-'n-a'
+''

/home/debian/www/jobeet/src/Erlem/JobeetBundle/Tests/Utils/JobeetTest.php:17
                                     
FAILURES!                            
Tests: 1, Assertions: 7, Failures: 1.

Maintenant, modifiez la classe Jobeet et ajoutez la condition suivante au début :

  • src/Erlem/JobeetBundle/Utils/Jobeet.php
// ...

    static public function slugify($text)
    {
        if (empty($text)) {
            return 'n-a';
        }

        // ...
    }

Le test ne génére pas d'erreur :

phpunit -c app/ src/Erlem/JobeetBundle/Tests/Utils/JobeetTest

Le résultat :

PHPUnit 4.0.17 by Sebastian Bergmann.

Configuration read from /home/debian/www/jobeet/app/phpunit.xml.dist

.

Time: 88 ms, Memory: 2.75Mb

OK (1 test, 7 assertions)

Ajout de tests à cause d'un bug

Disons que le temps a passé et l'un de vos utilisateurs vous rapporte un bug bizarre : certains liens des offres pointent vers une page d'erreur 404. Après quelques recherches, vous trouverez que, pour une raison quelconque, ces offres ont un jeton société, intitulé ou lieu vide.

Comment est-ce possible?

Vous regardez à travers les enregistrements de la BDD et les colonnes ne sont absolument pas vide. Vous y réfléchissez un moment, et hop, vous trouvez la cause. Lorsqu'une chaîne ne contient que des caractères non-ASCII, la méthode slugify() la convertit en une chaîne vide. Je suis si heureux d'avoir trouvé la cause, vous ouvrez la classe Jobeet et corrigez le problème tout de suite. C'est une mauvaise idée. Tout d'abord, nous allons ajouter un test :

  • src/Erlem/JobeetBundle/Tests/Utils/JobeetTest.php
$this->assertEquals('n-a', Jobeet::slugify(' - '));

Après avoir vérifié que le test ne passe pas, modifiez la classe Jobeet et déplacez la vérification de la chaîne vide à la fin de la méthode :

  •  src/Erlem/JobeetBundle/Utils/Jobeet.php
static public function slugify($text)
{
    // ...

    if (empty($text))
    {
        return 'n-a';
    }

    return $text;
}

Le nouveau test passe désormais, comme tous les autres. La méthode slugify() a eu un bug en dépit de notre couverture à 100%.

Vous ne pouvez pas penser à tous les cas lors de l'écriture des tests, et c'est très bien. Mais quand vous en découvrez un, vous devez écrire un test avant de corriger votre code. Cela signifie également que votre code va s'améliorer au fil du temps, ce qui est toujours une bonne chose.

Vers une meilleure méthode slugify()

Vous savez probablement que Symfony a été créé par des français, nous allons donc ajouter un test avec un mot français qui contient un accent :

  •  src/Erlem/JobeetBundle/Tests/Utils/JobeetTest.php
$this->assertEquals('developpeur-web', Jobeet::slugify('Développeur Web'));

Le test doit échouer. Au lieu de remplacer é par e, la méthode slugify() l'a remplacé par un tiret (-). C'est un problème compliqué, appelé translittération. Heureusement, la bibliothèque iconv, si elle est installée, va faire le travail pour nous. Remplacez le code de la méthode slugify() par ce qui suit :

  •  src/Erlem/JobeetBundle/Utils/Jobeet.php
static public function slugify($text)
{
    // replace non letter or digits by -
    $text = preg_replace('#[^\\pL\d]+#u', '-', $text);

    // trim
    $text = trim($text, '-');

    // transliterate
    if (function_exists('iconv'))
    {
        $text = iconv('utf-8', 'us-ascii//TRANSLIT', $text);
    }

    // lowercase
    $text = strtolower($text);

    // remove unwanted characters
    $text = preg_replace('#[^-\w]+#', '', $text);

    if (empty($text))
    {
        return 'n-a';
    }

    return $text;
}

N'oubliez pas de sauvegarder tous vos fichiers PHP avec l'encodage UTF-8, car c'est l'encodage par défaut de Symfony, et celui utilisé par iconv pour faire la translitération.

Modifiez également le fichier de test pour n'exécuter le test que si iconv est disponible:

  •  src/Erlem/JobeetBundle/Tests/Utils/JobeetTest.php
if (function_exists('iconv')) {
    $this->assertEquals('developpeur-web', Jobeet::slugify('Développeur Web'));
}

Couverture de code

Lorsque vous écrivez des tests, il est facile d'oublier une partie du code. Si vous ajoutez une nouvelle fonctionnalité ou si vous voulez juste pour vérifier vos statistiques de couverture de code, tout ce que vous devez faire est de vérifier la couverture de code en utilisant l'option --coverage-html :

La couverture de code ne fonctionne que si vous avez XDebug permis et toutes les dépendances installées :

apt-get install php5-xdebug

Puis exécutez la commande ci-dessous :

phpunit --coverage-html=web/cov/ -c app/

Vérifiez la couverture de code en ouvrant la page générée http://jobeet.local/cov/index.html dans votre navigateur.

01-107-symfony2-jobeet-jour-08-les-tests-unitaires

Tests unitaires de Doctrine

Les tests unitaires d'une classe modèle Doctrine est un peu plus complexe, car elle nécessite une connexion à la base de données. Vous avez déjà celle que vous utilisez pour votre développement, mais c'est une bonne habitude de créer une base de données dédiée pour des tests.

Au début de ce tutoriel, nous avons introduit les environnements comme un moyen de faire varier les paramètres d'une application. Par défaut, tous les tests de symfony sont lancées dans l'environnement de test, donc nous allons configurer une base de données différente pour l'environnement de test.

Accédez à votre app/config et de créer une copie du dossier parameters.yml, appelé parameters_test.yml. Ouvrir parameters_test.yml et changer le nom de votre base de données à jobeet_test. Pour que cela soit importé, il faut ajouter dans le fichier config_test.yml :

  •  app/config/config_test.yml
imports:
    - { resource: config_dev.yml }
    - { resource: parameters_test.yml }
// ...

Test de l'Entité Job

Tout d'abord, nous devons créer le fichier JobTest.php dans le dossier Tests/Entity.

La fonction setUp sera lancée à chaque fois que vous exécutez le test. Dans un premier temps, elle fera tomber votre base de données, elle sera re-créée et les données seront rechargées. Cela vous aidera à avoir les mêmes données initiales dans la base de données que vous avez créée pour l'environnement de test avant de lancer les tests.

  •  src/Erlem/JobeetBundle/Tests/Entity/JobTest.php
<?php

namespace Erlem\JobeetBundle\Entity;

use Symfony\Bundle\FrameworkBundle\Test\WebTestCase;
use Erlem\JobeetBundle\Utils\Jobeet as Jobeet;
use Symfony\Bundle\FrameworkBundle\Console\Application;
use Symfony\Component\Console\Output\NullOutput;
use Symfony\Component\Console\Input\ArrayInput;
use Doctrine\Bundle\DoctrineBundle\Command\DropDatabaseDoctrineCommand;
use Doctrine\Bundle\DoctrineBundle\Command\CreateDatabaseDoctrineCommand;
use Doctrine\Bundle\DoctrineBundle\Command\Proxy\CreateSchemaDoctrineCommand;

class JobTest extends WebTestCase
{
    private $em;
    private $application;

    public function setUp()
    {
        static::$kernel = static::createKernel();
        static::$kernel->boot();

        $this->application = new Application(static::$kernel);

        // drop the database
        $command = new DropDatabaseDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:database:drop',
            '--force' => true
        ));
        $command->run($input, new NullOutput());

        // we have to close the connection after dropping the database so we don't get "No database selected" error
        $connection = $this->application->getKernel()->getContainer()->get('doctrine')->getConnection();
        if ($connection->isConnected()) {
            $connection->close();
        }

        // create the database
        $command = new CreateDatabaseDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:database:create',
        ));
        $command->run($input, new NullOutput());

        // create schema
        $command = new CreateSchemaDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:schema:create',
        ));
        $command->run($input, new NullOutput());

        // get the Entity Manager
        $this->em = static::$kernel->getContainer()
            ->get('doctrine')
            ->getManager();

        // load fixtures
        $client = static::createClient();
        $loader = new \Symfony\Bridge\Doctrine\DataFixtures\ContainerAwareLoader($client->getContainer());
        $loader->loadFromDirectory(static::$kernel->locateResource('@ErlemJobeetBundle/DataFixtures/ORM'));
        $purger = new \Doctrine\Common\DataFixtures\Purger\ORMPurger($this->em);
        $executor = new \Doctrine\Common\DataFixtures\Executor\ORMExecutor($this->em, $purger);
        $executor->execute($loader->getFixtures());
    }

    public function testGetCompanySlug()
    {
        $job = $this->em->createQuery('SELECT j FROM ErlemJobeetBundle:Job j ')
            ->setMaxResults(1)
            ->getSingleResult();

        $this->assertEquals($job->getCompanySlug(), Jobeet::slugify($job->getCompany()));
    }

    public function testGetPositionSlug()
    {
        $job = $this->em->createQuery('SELECT j FROM ErlemJobeetBundle:Job j ')
            ->setMaxResults(1)
            ->getSingleResult();

        $this->assertEquals($job->getPositionSlug(), Jobeet::slugify($job->getPosition()));
    }

    public function testGetLocationSlug()
    {
        $job = $this->em->createQuery('SELECT j FROM ErlemJobeetBundle:Job j ')
            ->setMaxResults(1)
            ->getSingleResult();

        $this->assertEquals($job->getLocationSlug(), Jobeet::slugify($job->getLocation()));
    }

    public function testSetExpiresAtValue()
    {
        $job = new Job();
        $job->setExpiresAtValue();

        $this->assertEquals(time() + 86400 * 30, $job->getExpiresAt()->format('U'));
    }

    protected function tearDown()
    {
        parent::tearDown();
        $this->em->close();
    }
}

Tester les classes repository

Maintenant, nous allons écrire des tests pour la classe JobRepository, pour voir si les fonctions que nous avons créés dans les jours précédents nous fournissent les bonnes valeurs :

  • src/Erlem/JobeetBundle/Tests/Repository/JobRepositoryTest.php
<?php

namespace Erlem\JobeetBundle\Tests\Repository;

use Symfony\Bundle\FrameworkBundle\Test\WebTestCase;
use Symfony\Bundle\FrameworkBundle\Console\Application;
use Symfony\Component\Console\Output\NullOutput;
use Symfony\Component\Console\Input\ArrayInput;
use Doctrine\Bundle\DoctrineBundle\Command\DropDatabaseDoctrineCommand;
use Doctrine\Bundle\DoctrineBundle\Command\CreateDatabaseDoctrineCommand;
use Doctrine\Bundle\DoctrineBundle\Command\Proxy\CreateSchemaDoctrineCommand;

class JobRepositoryTest extends WebTestCase
{
    private $em;
    private $application;

    public function setUp()
    {
        static::$kernel = static::createKernel();
        static::$kernel->boot();

        $this->application = new Application(static::$kernel);

        // drop the database
        $command = new DropDatabaseDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:database:drop',
            '--force' => true
        ));
        $command->run($input, new NullOutput());

        // we have to close the connection after dropping the database so we don't get "No database selected" error
        $connection = $this->application->getKernel()->getContainer()->get('doctrine')->getConnection();
        if ($connection->isConnected()) {
            $connection->close();
        }

        // create the database
        $command = new CreateDatabaseDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:database:create',
        ));
        $command->run($input, new NullOutput());

        // create schema
        $command = new CreateSchemaDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:schema:create',
        ));
        $command->run($input, new NullOutput());

        // get the Entity Manager
        $this->em = static::$kernel->getContainer()
            ->get('doctrine')
            ->getManager();

        // load fixtures
        $client = static::createClient();
        $loader = new \Symfony\Bridge\Doctrine\DataFixtures\ContainerAwareLoader($client->getContainer());
        $loader->loadFromDirectory(static::$kernel->locateResource('@ErlemJobeetBundle/DataFixtures/ORM'));
        $purger = new \Doctrine\Common\DataFixtures\Purger\ORMPurger($this->em);
        $executor = new \Doctrine\Common\DataFixtures\Executor\ORMExecutor($this->em, $purger);
        $executor->execute($loader->getFixtures());
    }

    public function testCountActiveJobs()
    {
        $query = $this->em->createQuery('SELECT c FROM ErlemJobeetBundle:Category c');
        $categories = $query->getResult();

        foreach($categories as $category) {
            $query = $this->em->createQuery('SELECT COUNT(j.id) FROM ErlemJobeetBundle:Job j WHERE j.category = :category AND j.expires_at > :date');
            $query->setParameter('category', $category->getId());
            $query->setParameter('date', date('Y-m-d H:i:s', time()));
            $jobs_db = $query->getSingleScalarResult();

            $jobs_rep = $this->em->getRepository('ErlemJobeetBundle:Job')->countActiveJobs($category->getId());
            // This test will verify if the value returned by the countActiveJobs() function
            // coincides with the number of active jobs for a given category from the database
            $this->assertEquals($jobs_rep, $jobs_db);
        }
    }

    public function testGetActiveJobs()
    {
        $query = $this->em->createQuery('SELECT c from ErlemJobeetBundle:Category c');
        $categories = $query->getResult();

        foreach ($categories as $category) {
            $query = $this->em->createQuery('SELECT COUNT(j.id) from ErlemJobeetBundle:Job j WHERE j.expires_at > :date AND j.category = :category');
            $query->setParameter('date', date('Y-m-d H:i:s', time()));
            $query->setParameter('category', $category->getId());
            $jobs_db = $query->getSingleScalarResult();

            $jobs_rep = $this->em->getRepository('ErlemJobeetBundle:Job')->getActiveJobs($category->getId(), null, null);
            // This test tells if the number of active jobs for a given category from
            // the database is the same as the value returned by the function
            $this->assertEquals($jobs_db, count($jobs_rep));
        }
    }

    public function testGetActiveJob()
    {
        $query = $this->em->createQuery('SELECT j FROM ErlemJobeetBundle:Job j WHERE j.expires_at > :date');
        $query->setParameter('date', date('Y-m-d H:i:s', time()));
        $query->setMaxResults(1);
        $job_db = $query->getSingleResult();

        $job_rep = $this->em->getRepository('ErlemJobeetBundle:Job')->getActiveJob($job_db->getId());
        // If the job is active, the getActiveJob() method should return a non-null value
        $this->assertNotNull($job_rep);

        $query = $this->em->createQuery('SELECT j FROM ErlemJobeetBundle:Job j WHERE j.expires_at < :date');         $query->setParameter('date', date('Y-m-d H:i:s', time()));
        $query->setMaxResults(1);
        $job_expired = $query->getSingleResult();

        $job_rep = $this->em->getRepository('ErlemJobeetBundle:Job')->getActiveJob($job_expired->getId());
        // If the job is expired, the getActiveJob() method should return a null value
        $this->assertNull($job_rep);
    }

    protected function tearDown()
    {
        parent::tearDown();
        $this->em->close();
    }
}

Nous ferons la même chose pour la classe CategoryRepository :

  • src/Erlem/JobeetBundle/Tests/Repository/CategoryRepositoryTest.php
<?php

namespace Erlem\JobeetBundle\Tests\Repository;

use Symfony\Bundle\FrameworkBundle\Test\WebTestCase;
use Symfony\Bundle\FrameworkBundle\Console\Application;
use Symfony\Component\Console\Output\NullOutput;
use Symfony\Component\Console\Input\ArrayInput;
use Doctrine\Bundle\DoctrineBundle\Command\DropDatabaseDoctrineCommand;
use Doctrine\Bundle\DoctrineBundle\Command\CreateDatabaseDoctrineCommand;
use Doctrine\Bundle\DoctrineBundle\Command\Proxy\CreateSchemaDoctrineCommand;

class CategoryRepositoryTest extends WebTestCase
{
    private $em;
    private $application;

    public function setUp()
    {
        static::$kernel = static::createKernel();
        static::$kernel->boot();

        $this->application = new Application(static::$kernel);

        // drop the database
        $command = new DropDatabaseDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:database:drop',
            '--force' => true
        ));
        $command->run($input, new NullOutput());

        // we have to close the connection after dropping the database so we don't get "No database selected" error
        $connection = $this->application->getKernel()->getContainer()->get('doctrine')->getConnection();
        if ($connection->isConnected()) {
            $connection->close();
        }

        // create the database
        $command = new CreateDatabaseDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:database:create',
        ));
        $command->run($input, new NullOutput());

        // create schema
        $command = new CreateSchemaDoctrineCommand();
        $this->application->add($command);
        $input = new ArrayInput(array(
            'command' => 'doctrine:schema:create',
        ));
        $command->run($input, new NullOutput());

        // get the Entity Manager
        $this->em = static::$kernel->getContainer()
            ->get('doctrine')
            ->getManager();

        // load fixtures
        $client = static::createClient();
        $loader = new \Symfony\Bridge\Doctrine\DataFixtures\ContainerAwareLoader($client->getContainer());
        $loader->loadFromDirectory(static::$kernel->locateResource('@ErlemJobeetBundle/DataFixtures/ORM'));
        $purger = new \Doctrine\Common\DataFixtures\Purger\ORMPurger($this->em);
        $executor = new \Doctrine\Common\DataFixtures\Executor\ORMExecutor($this->em, $purger);
        $executor->execute($loader->getFixtures());
    }

    public function testGetWithJobs()
    {
        $query = $this->em->createQuery('SELECT c FROM ErlemJobeetBundle:Category c LEFT JOIN c.jobs j WHERE j.expires_at > :date');
        $query->setParameter('date', date('Y-m-d H:i:s', time()));
        $categories_db = $query->getResult();

        $categories_rep = $this->em->getRepository('ErlemJobeetBundle:Category')->getWithJobs();
        // This test verifies if the number of categories having active jobs, returned
        // by the getWithJobs() function equals the number of categories having active jobs from database
        $this->assertEquals(count($categories_rep), count($categories_db));
    }

    protected function tearDown()
    {
        parent::tearDown();
        $this->em->close();
    }
}

Après avoir terminé l'écriture des tests, les exécuter avec la commande suivante, afin de générer le pourcentage de couverture de code pour les fonctions :

phpunit --coverage-html=web/cov/ -c app src/Erlem/JobeetBundle/Tests/Repository/

Maintenant, si vous allez à l'adresse http://jobeet.local/cov/Repository/index.html vous verrez que la couverture de code pour les tests Repository n'est pas complète à 100%.

02-107-symfony2-jobeet-jour-08-les-tests-unitaires

Ajoutons quelques tests pour la JobRepository pour atteindre une couverture de code à 100%. À l'heure actuelle, dans notre base de données, nous avons deux catégories d'emplois ayant 0 emploi actif et une catégorie d'emplois ayant un seul emploi actif. C'est pourquoi, quand nous allons tester les paramètres $max et $offset, nous allons exécuter les tests suivants seulement sur les catégories avec au moins 3 emplois actifs. De ce fait, ajoutez cela à l'intérieur de votre instruction foreach, de votre fonction testGetActiveJobs() :

  •  src/Erlem/JobeetBundle/Tests/Repository/JobRepositoryTest.php
// ...
foreach ($categories as $category) {
    // ...

    // If there are at least 3 active jobs in the selected category, we will
    // test the getActiveJobs() method using the limit and offset parameters too
    // to get 100% code coverage
    if($jobs_db > 2 ) {
        $jobs_rep = $this->em->getRepository('ErlemJobeetBundle:Job')->getActiveJobs($category->getId(), 2);
        // This test tells if the number of returned active jobs is the one $max parameter requires
        $this->assertEquals(2, count($jobs_rep));

        $jobs_rep = $this->em->getRepository('ErlemJobeetBundle:Job')->getActiveJobs($category->getId(), 2, 1);
        // We set the limit to 2 results, starting from the second job and test if the result is as expected
        $this->assertEquals(2, count($jobs_rep));
    }
}
// ...

 Exécutez de nouveau la commande de couverture de code :

phpunit --coverage-html=web/cov/ -c app src/Erlem/JobeetBundle/Tests/Repository/

Cette fois, si vous vérifiez votre couverture de code, vous verrez qu'elle est à 100% : http://jobeet.local/cov/Repository/index.html

03-107-symfony2-jobeet-jour-08-les-tests-unitaires

C'est fini pour aujourd'hui ! Rendez-vous demain, quand nous allons parler de tests fonctionnels.

Code source

Le code source est sur GitHub. Vous pouvez le télécharger en exécutant les commandes ci-dessous (prérequis Symfony2 - Jobeet - Jour 01 - Démarrage du projet) :

su
cd /var/www/
git clone https://github.com/erlem/jobeet.git
cd jobeet/
git checkout tags/v0.8.0
 
composer update
 
php app/console doctrine:database:create
php app/console doctrine:schema:update --force
php app/console doctrine:fixtures:load
 
php app/console assets:install web

chmod 777 -R app/cache/
chmod 777 -R app/logs/

Vous pouvez maintenant tester l'application dans un navigateur: http://jobeet.local/ ou dans l'environnement de développement, http://jobeet.local/app_dev.php.


Symfony2 - Jour 07 - Jouons avec la page Catégorie
[Sommaire] Symfony2 - Jour 09 - Les tests fonctionnels >


Pour ce tutoriel, je me suis inspiré du tutoriel Symfony2 Jobeet du site IntelligentBee

Submit to DeliciousSubmit to DiggSubmit to FacebookSubmit to Google PlusSubmit to StumbleuponSubmit to TechnoratiSubmit to TwitterSubmit to LinkedIn