Archives Wild Code School
Symfony

12 - Symfony : Fabriquer ses jeux de données avec FakerPHP

Quête 15 sur 35

Objectifs

  • ✅ Installer la librairie FakerPHP
  • ✅ Fabriquer un jeu de données consistant et testable

Pré-requis

​ Avoir terminé la quête

Quêtes liées
title-book
Introduction

Dans la quête précédente, tu as créé les entités Season et Episode afin de parfaire ton Wild-Séries. Parfait 🤩!

Et maintenant que tu as ces deux nouvelles entités, tu te tournes vers ton nouvel outil préféré pour créer un jeu de données que tu pourrais facilement manipuler et maintenir : les Fixtures 😎.

Tu vas donc pouvoir créer toutes les saisons et les épisodes de tes séries préférées. Mais avant ça, réalisons un rapide calcul 🤔 : si j'ai 5 séries, que chacune a en moyenne 8 saisons et que chaque saison possède une vingtaine d'épisodes... 😑

😒 5 x 8 x 20 = 800 ! 😱

😰 Hé bien il ne te reste qu'à créer 840 objets (saisons + épisodes) à la main dans tes fixtures ... Bon courage 💪!

Sommaire

FakerPHP

Ah ! tu es toujours là ... 😌 Bon effectivement il y a un moyen de s'épargner la création manuelle d'un jeu de données complet.

La solution : FakerPHP

↗
Fake data generator

La documentation officielle de la bibliothèque FakerPHP.

fakerphp.github.io

FakerPHP est une bibliothèque PHP qui nous permet de génerer des données aléatoirement en fonction de certains critères.

Important

Avant toute chose clarifions certains points :

  • Si les données sont générées aléatoirement, alors ce ne sont pas de vraies données. En effet, l'objectif n'est pas d'avoir un jeu de données réel, mais plutôt de remplir sa base de données avec des objets vraisemblables et aléatoirement générés.
  • Avec cette méthode, à chaque rechargement des fixtures, tu vas perdre toutes les données générées par FakerPhp qui seront remplacées par des nouvelles. Oui, et c'est exactement ce que l'on cherche à faire ! Rien n'est plus mauvais que de constamment travailler avec les mêmes données, cela empêche de voir certains problèmes. FakerPhp nous assure des données toujours renouvelées, imprévisibles et donc parfaites pour nos tests !

Très bien mais comment ca marche 🤓?

Installation du Composant FakerPhp/Faker

Pour ajouter FakerPhp à la racine de ton projet, passe la commande :

sh
composer require fakerphp/faker

Cela viendra ajouter la bibliothèque à ton projet.

Utilisation

FakerPhp prend tout son sens lors de l'élaboration de fixtures, car il vient nous fournir des données générées là où il nous faudrait mettre une valeur pertinente (prénom, date, prix, email, téléphone, description, etc).

Prenons l'exemple de la création de fixtures de Category :

php
<?php

namespace App\DataFixtures;

use App\Entity\Category;
use Doctrine\Bundle\FixturesBundle\Fixture;
use Doctrine\Persistence\ObjectManager;

//Tout d'abord nous ajoutons la classe Factory de FakerPhp
use Faker\Factory;

class CategoryFixtures extends Fixture
{
    public function load(ObjectManager $manager): void
    {
        //Puis ici nous demandons à la Factory de nous fournir un Faker
        $faker = Factory::create();

        /**
        * L'objet $faker que tu récupères est l'outil qui va te permettre 
        * de te générer toutes les données que tu souhaites
        */
        for($i = 1; $i <= 5; $i++) {
            $category = new Category();
            //Ce Faker va nous permettre d'alimenter l'instance de Category que l'on souhaite ajouter en base
            $category->setName($faker->word());

            $manager->persist($category);
            // Ici, on crée une référence à l'objet $category sous la forme 'category_1', 'category_2'...
            $this->addReference('category_' . $i, $category);
        }

        $manager->flush();
    }
}

Dans cet exemple, tu remarqueras que nous utilisons une fonction de notre Faker pour avoir un résultat approprié au champ que nous alimentons :

  • word() => permet de récupérer un mot pour représenter le nom d'une catégorie
↗
FakerPHP word

La documentation officielle sur la fonction word().

fakerphp.github.io
Important

Attention ! Si tu recharges tes fixtures maintenant, un message d'erreur t'informant qu'une référence n'existe pas s'affichera : il va falloir que tu adaptes les fixtures que tu as déjà créées en fonction des références choisies. Commençons avec la classe ProgramFixtures :

php
<?php

namespace App\DataFixtures;

use App\Entity\Program;
use Doctrine\Bundle\FixturesBundle\Fixture;
use Doctrine\Common\DataFixtures\DependentFixtureInterface;
use Doctrine\Persistence\ObjectManager;

use Faker\Factory;

class ProgramFixtures extends Fixture implements DependentFixtureInterface
{
    public function load(ObjectManager $manager): void
    {
        $faker = Factory::create();

        // L'objectif est de créer 10 séries qui appartiendront à une catégorie au hasard
        for($i = 1; $i <= 10; $i++) {
            $program = new Program();
            $program->setTitle($faker->words(3, true));
            $program->setSynopsis($faker->paragraphs(2, true));
            $program->setCategory($this->getReference('category_' . $faker->numberBetween(1, 5)));

            $manager->persist($program);
            $this->addReference('program_' . $i, $program);
        }

        $manager->flush();
    }

    public function getDependencies()
    {
        return [
            CategoryFixtures::class,
        ];
    }
}

Cette fois-ci, on utilise d'autres fonctions mises à disposition par Faker :

  • words() => permet de récupérer une chaîne de caractères de plusieurs mots pour représenter le titre d'une série.
↗
FakerPHP words

La documentation officielle sur la fonction words().

fakerphp.github.io
  • numberBetween() => permet de récupérer un chiffre compris dans un interval, ici entre 1 et 5, ce qui correspond aux références créées pour les catégories.
↗
FakerPHP numberBetween

La documentation officielle sur la fonction numberBetween().

fakerphp.github.io
  • paragraph() => permet de générer plusieurs paragraphes de texte.
↗
FakerPHP paragraphs

La documentation officielle sur la fonction paragraphs().

fakerphp.github.io

Mais il faut savoir que FakerPhp est capable de créer de la même manière des données de toute sorte :

  • firstName() => permet de générer un prénom
  • lastName() => permet de générer un nom de famille
  • city() => permet de générer une ville
  • email() => permet de générer une adresse email
  • password() => permet de générer un mot de passe
  • et encore beaucoup d'autres que tu pourras découvrir en parcourant la doc 😎. Tu peux aussi ajouter un paramètre pour gérer la langue, et ainsi générer des fixtures adaptées à chaque pays.

💪 Challenge

Alimente encore ton Wild Séries

Sers toi maintenant de FakerPHP afin de créer un jeu données adapté pour :

  • Les saisons (5 par série)
  • Les épisodes (10 par saison)

Tu seras très certainement amené à utiliser des boucles imbriquées, pour que chaque série possède plusieurs saisons, et que chaque saison possède plusieurs épisodes.

🧐 Critères de validation

  • Lorsque symfony console doctrine:fixtures:load est exécuté, il n y a pas de message d'erreur.
  • La navigation montre que toutes les données ont bien été insérées et qu'elles sont correctement associées (les séries ont bien des saisons, les saisons ont bien des épisodes).
  • Le code est disponible sur un repository GitHub, avec une branche correspondant à cette quête.