Doctrine est un ORM php (mapping Objet/Relationnel). Les ORM consistent à réaliser la correspondance entre le modèle de données relationnel et le modèle objets de la façon la plus aisée et efficace possible. Un outil d'ORM propose un certain nombre de fonctionnalités parmi lesquelles :
Cette étape consiste à indiquer au projet l'adresse de la base de données, son nom, et le login/mot de passe du compte permettant de s'y connecter. Pour cela, vérifier votre fichier de configuration .env (dans c:\wamp64\www\webstudent\ ou à la racine du projet)
#DATABASE_URL=mysql://db_user:db_password@127.0.0.1:3306/db_name
Exemple :
DATABASE_URL="mysql://root:@127.0.0.1:3307/webstudent?serverVersion=mariadb-10.10.2"
Cette configuration permet de se connecter à une base de données mariadb nommée webstudent, située sur le poste local. Le compte de connexion est root, sans mot de passe.
Si vous n'avez pas encore créé la base de données sous mariadb ou mysql, la console permet de créer la base de données en exécutant la commande ci-dessous :
> php bin/console doctrine:database:create
Dans symfony, les classes métiers se nomment des entités. Elles peuvent être créées avec la console :
> php bin/console make:entity
Le système nous invite alors à saisir l'ensemble des propriétés de l'entité. Pour chaque propriété, nous devons préciser son type, si cette propriété sera nullable
en bdd ou pas.
Dans l'exemple ci-dessous, nous créons l'entité Etudiant
avec la propriété nom
de type string
de 50 caractères. Vous créerez les propriétés nom, prenom, dateNaiss (type date), ville.
Un fichier nommé Etudiant.php a alors été créé dans le dossier …/src/Entity. Il s'agit d'une classe métier classique avec ses propriétés. Les getters et les setters ont été générés automatiquement. Une propriété supplémentaire id de type int a été ajoutée. Elle est utilisée pour faire le mapping de la clé primaire de la table qui sera un numérique auto-incrémenté.
Il est alors possible de créer la table correspondant à l'entité.
> php bin/console make:migration
Cette instruction créé à chaque fois un fichier dans le dossier src/migration avec les instructions sql à exécuter.
Pour exécuter les instructions sql, lancer la commande suivante :
> php bin/console doctrine:migrations:migrate
On voit alors l'instruction sql exécutée. Vérifiez en base l'existence de la table. A chaque propriété de l'entité correspond un champ de la table. Celle ci a pour clé primaire Id.
Il s'agit ici de créer un objet et de rendre ses données persistantes en base de données. Pour cela, nous allons créer une nouvelle url qui exécutera une méthode du contrôleur créant un objet et insérant un enregistrement en base. Le contrôleur redirigera vers une page de consultation de l'enregistrement créé.
Dans le fichier des routes, ajouter :
etudiantAjouter: path: /etudiant/ajouter controller: App\Controller\EtudiantController::ajouter
Ajout de la méthode ajouterEtudiant dans EtudiantController
public function ajouter(ManagerRegistry $doctrine){ // récupère le manager d'entités $entityManager = $doctrine->getManager(); // instanciation d'un objet Etudiant $etudiant = new Etudiant(); $etudiant->setNom('Potter'); $etudiant->setPrenom('Harry'); $etudiant->setDateNaiss(new \DateTime(date('1980-07-31'))); $etudiant->setVille('Surrey'); // Indique à Doctrine de persister l'objet $entityManager->persist($etudiant); // Exécue l'instruction sql permettant de persister lobjet, ici un INSERT INTO $entityManager->flush(); // renvoie vers la vue de consultation de l'étudiant en passant l'objet etudiant en paramètre return $this->render('etudiant/consulter.html.twig', [ 'etudiant' => $etudiant,]); }
une erreur apparaitra car la classe métier (l'entité) Etudiant n'est pas connue de EtudiantController. Il faut donc l'importer en ajoutant la ligne ci-dessous au niveau des use (imports) ainsi que le manager d'entités.
use App\Entity\Etudiant; use Doctrine\Persistence\ManagerRegistry;
Dans le dossier templates/etudiant, créer le fichier ci-dessous, nommé consulter.html.twig
<!DOCTYPE html> <html> <head> </head> <body> <h5>PAGE DE CONSULTATION D'UN ETUDIANT</h5> <p> <table > <tr><td>Id : </td><td>{{etudiant.id}} </td></tr> <tr><td>Nom : </td><td>{{etudiant.nom}}</td> <td rowspan="8" class="imgEtu"> {% set photo = 'img/etudiant/'~ etudiant.id ~'.jpg' %} <span class="zoom"><img src="{{ asset(photo | trans )}}" title="{{ etudiant.prenom ~ " " ~ etudiant.nom }}" alt="{{ etudiant.prenom ~ " " ~ etudiant.nom }}"/></span></td></tr> </td> <tr><td>Prénom : </td><td>{{etudiant.prenom}}</td></tr></tr> <tr><td>Date de naissance : </td><td>{{etudiant.dateNaiss|date("d/m/Y")}}</td></tr> <tr><td>rue : </td><td>{{etudiant.numrue}} {{etudiant.rue}}</td></tr> <tr><td>code postal : </td><td>{{etudiant.copos}}</td></tr> <tr><td>ville : </td><td>{{etudiant.ville}}</td></tr> <tr><td>Surnom : </td><td>{{etudiant.surnom}}</td></tr> </table> </body> </html>
Note : dans la vue ci-dessus,, des propriétés supplémentaires ont été ajoutées. Ajoutez les dans votre entité étudiant et faites le mapping avec la base de données.
public function consulterEtudiant(ManagerRegistry $doctrine, int $id){ $etudiant= $doctrine->getRepository(Etudiant::class)->find($id); if (!$etudiant) { throw $this->createNotFoundException( 'Aucun etudiant trouvé avec le numéro '.$id ); } //return new Response('Etudiant : '.$etudiant->getNom()); return $this->render('etudiant/consulter.html.twig', [ 'etudiant' => $etudiant,]); }
La méthode prend en paramètre l'id de l'étudiant permettant la recherche en bdd de l'étudiant selon son id. Il faut donc indiquer dans l'url l'id de l'étudiant. Dans le fichier de routes, il faut donc ajouter le paramètre :
etudiantConsulter: path: /etudiant/consulter/{id} controller: App\Controller\EtudiantController::consulterEtudiant
EtudiantController, méthode permettant de lister les étudiants
public function listerEtudiant(ManagerRegistry $doctrine){ $repository = $doctrine->getRepository(Etudiant::class); $etudiants= $repository->findAll(); return $this->render('etudiant/lister.html.twig', [ 'pEtudiants' => $etudiants,]); }
Vue Twig listant les étudiants
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>{% block title %}Welcome!{% endblock %}</title> {% block stylesheets %}{% endblock %} </head> <body> {% block body %}{% endblock %} {% block javascripts %}{% endblock %} LISTE DES ETUDIANTS</br> <table> {% for e in pEtudiants %} <tr> <td><a href="{{ path('etudiantConsulter', { 'id': e.id }) }}">{{ e.nom }}</a></td> <td>{{ e.prenom }}</a></td> <td>{{ e.dateNaiss|date('d/m/Y') }}</td> <td>{{ e.ville}}</td> {% else %} <tr> <td>Aucun etudiant n'a été trouvé.</td> </tr> {% endfor %} </table> </body> </html>