Introduction à Laravel - Installation, MVC, Exemples et Structure du Projet

Laravel est un framework PHP open-source utilisé pour le développement d'applications web. Il suit le modèle architectural MVC (Modèle-Vue-Contrôleur) et offre une syntaxe élégante et expressive. Ce tutoriel vous guidera pas à pas pour comprendre les bases de Laravel, installer le framework, explorer la structure MVC avec des exemples concrets, et comprendre la structure d'un projet Laravel.


1. Introduction à Laravel

Qu'est-ce que Laravel ?

Pourquoi utiliser Laravel ?


2. Installation de Laravel

Prérequis

Avant d'installer Laravel, assurez-vous que votre environnement satisfait les conditions suivantes :

flowchart TD A[Installation de Laravel]:::laravel --> B(Conditions préalables):::conditions B --> C(PHP >= 8.1):::php B --> D(Composer):::composer B --> E(Serveur web):::server E --> E1(Apache):::apache E --> E2(Nginx):::nginx E --> E3(Serveur intégré de PHP):::phpbuiltin B --> F(Base de données):::database F --> F1(MySQL):::mysql F --> F2(PostgreSQL):::postgres F --> F3(SQLite):::sqlite F --> F4(Autres SGBD):::others classDef laravel fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff classDef conditions fill:#f7b267,stroke:#333,stroke-width:2px,color:#000 classDef php fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff classDef composer fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff classDef server fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff classDef apache fill:#d32f2f,stroke:#333,stroke-width:2px,color:#fff classDef nginx fill:#009688,stroke:#333,stroke-width:2px,color:#fff classDef phpbuiltin fill:#ff9800,stroke:#333,stroke-width:2px,color:#fff classDef database fill:#673ab7,stroke:#333,stroke-width:2px,color:#fff classDef mysql fill:#e91e63,stroke:#333,stroke-width:2px,color:#fff classDef postgres fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff classDef sqlite fill:#00bcd4,stroke:#333,stroke-width:2px,color:#fff classDef others fill:#ffc107,stroke:#333,stroke-width:2px,color:#000

Étape 1 : Installer Composer

Composer est essentiel pour gérer les dépendances de Laravel. Si vous ne l'avez pas encore installé, suivez ces étapes :

  1. Téléchargez Composer depuis https://getcomposer.org/download/.
  2. Installez-le en suivant les instructions pour votre système d'exploitation.

Étape 2 : Créer un nouveau projet Laravel

Ouvrez votre terminal et exécutez la commande suivante pour créer un nouveau projet Laravel :

composer create-project laravel/laravel nom-du-projet

Remplacez nom-du-projet par le nom que vous souhaitez donner à votre application.

Étape 3 : Démarrer le serveur local

Accédez au répertoire de votre projet :

cd nom-du-projet

Démarrez le serveur local intégré de Laravel :

php artisan serve

Vous devriez voir un message indiquant que le serveur est en cours d'exécution. Par défaut, il est accessible à l'adresse suivante :
http://127.0.0.1:8000


3. Comprendre le Modèle MVC dans Laravel

Qu'est-ce que le MVC ?

Le modèle MVC divise une application en trois composants principaux :

  1. Modèle (Model) : Gère les données et la logique métier. Il interagit avec la base de données.
  2. Vue (View) : Représente l'interface utilisateur. C'est ce que l'utilisateur voit.
  3. Contrôleur (Controller) : Agit comme un intermédiaire entre le Modèle et la Vue. Il traite les requêtes des utilisateurs et renvoie des réponses.
flowchart TD A[Modèle MVC]:::mvc --> B(Modèle Model):::model A --> C(Vue View):::view A --> D(Contrôleur Controller):::controller B --> B1(Gère les données):::data B --> B2(Logique métier):::logic B --> B3(Interagit avec la base de données):::db C --> C1(Interface utilisateur):::ui C --> C2(Ce que l'utilisateur voit):::user D --> D1(Intermédiaire entre Modèle et Vue):::intermediate D --> D2(Traite les requêtes des utilisateurs):::requests D --> D3(Retourne des réponses):::responses classDef mvc fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff classDef model fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff classDef view fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff classDef controller fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff classDef data fill:#8bc34a,stroke:#333,stroke-width:2px,color:#000 classDef logic fill:#cddc39,stroke:#333,stroke-width:2px,color:#000 classDef db fill:#ff9800,stroke:#333,stroke-width:2px,color:#000 classDef ui fill:#00bcd4,stroke:#333,stroke-width:2px,color:#000 classDef user fill:#009688,stroke:#333,stroke-width:2px,color:#fff classDef intermediate fill:#ffc107,stroke:#333,stroke-width:2px,color:#000 classDef requests fill:#ff5722,stroke:#333,stroke-width:2px,color:#fff classDef responses fill:#795548,stroke:#333,stroke-width:2px,color:#fff


les interactions entre les différentes couches du modèle MVC (Modèle, Vue, Contrôleur)


flowchart TD User((Utilisateur)) -->|Envoie une requête| Controller(Contrôleur) Controller -->|Traite la requête| Model(Modèle) Model -->|Interagit avec la base de données| Database(Base de données) Database -->|Retourne les données| Model Model -->|Retourne les données traitées| Controller Controller -->|Prépare la réponse| View(Vue) View -->|Affiche l'interface utilisateur| User style User fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff style Controller fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff style Model fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff style Database fill:#ff9800,stroke:#333,stroke-width:2px,color:#fff style View fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff

Exemple Simple : Créer une Application "Liste de Tâches"

Étape 1 : Créer une Migration

Les migrations permettent de définir la structure de la base de données. Créez une migration pour une table tasks :

flowchart TD A[Création d'une migration] --> B(Écrire le code de la migration) B --> C(Exécuter la commande de migration) C --> D(Base de données mise à jour) D --> E(Versionnage de la structure) E --> F(Rollback possible) subgraph Migration_Process["Processus des migrations"] B -->|Code de création/modification| C C -->|Applique les changements| D D -->|Enregistre l'état| E E -->|Permet de revenir en arrière| F end style A fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff style B fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff style C fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff style D fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff style E fill:#ffc107,stroke:#333,stroke-width:2px,color:#000 style F fill:#ff5722,stroke:#333,stroke-width:2px,color:#fff
  1. Création d'une migration :

    • Une migration est créée via une commande CLI (par exemple, php artisan make:migration dans Laravel).
    • Elle génère un fichier contenant deux méthodes principales : up() et down().
  2. Écrire le code de la migration :

    • Dans la méthode up(), vous définissez les modifications à apporter à la base de données (par exemple, créer une table ou ajouter une colonne).
    • Dans la méthode down(), vous définissez comment annuler ces modifications (par exemple, supprimer une table ou une colonne).
  3. Exécuter la commande de migration :

    • Vous exécutez la commande php artisan migrate pour appliquer les migrations.
    • Cette commande lit les fichiers de migration et met à jour la base de données en conséquence.
  4. Base de données mise à jour :

    • La structure de la base de données est modifiée selon le code écrit dans la méthode up().
  5. Versionnage de la structure :

    • Chaque migration est enregistrée dans une table spéciale (migrations) pour suivre son état.
    • Cela permet de garder une trace des modifications apportées à la base de données.
  6. Rollback possible :

    • Si nécessaire, vous pouvez annuler les migrations avec la commande php artisan migrate:rollback.
    • Cela exécute la méthode down() pour inverser les changements.
php artisan make:migration create_tasks_table

Ouvrez le fichier généré dans le dossier database/migrations et modifiez-le comme suit :

public function up()
{
    Schema::create('tasks', function (Blueprint $table) {
        $table->id();
        $table->string('title');
        $table->boolean('completed')->default(false);
        $table->timestamps();
    });
}

Exécutez la migration :

php artisan migrate

Étape 2 : Créer un Modèle

flowchart TD A[Migration] -->|Defines table structure| B(Database Table) B -->|Mapped to| C(Model) C -->|Interacts with| B subgraph Migration_Process["Migration Process"] A -->|Creates/Modifies| B end subgraph Model_Process["Model Process"] C -->|Queries/Manipulates| B end style A fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff style B fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff style C fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff

Créez un modèle Task pour interagir avec la table tasks :

php artisan make:model Task

Étape 3 : Créer un Contrôleur

Générez un contrôleur pour gérer les actions liées aux tâches :

flowchart TD A[Migration] -->|Defines table structure| B(Database Table) B -->|Mapped to| C(Model) C -->|Fetches/Manipulates data| B User((User)) -->|Sends request| Controller(Controller) Controller -->|Queries data from| C Controller -->|Passes data to| D(View) D -->|Displays data to| User subgraph Migration_Process["Migration Process"] A -->|Creates/Modifies| B end subgraph Model_Process["Model Process"] C -->|Queries/Manipulates| B end subgraph Controller_Process["Controller Process"] Controller -->|Handles request| C Controller -->|Prepares response| D end subgraph View_Process["View Process"] D -->|Renders UI| User end style A fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff style B fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff style C fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff style Controller fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff style D fill:#ffc107,stroke:#333,stroke-width:2px,color:#000 style User fill:#795548,stroke:#333,stroke-width:2px,color:#fff
php artisan make:controller TaskController --resource

Le flag --resource crée un contrôleur avec des méthodes CRUD prédéfinies.

Ouvrez le fichier TaskController.php et ajoutez la logique suivante :

use App\Models\Task;

public function index()
{
    $tasks = Task::all();
    return view('tasks.index', compact('tasks'));
}

public function store(Request $request)
{
    $task = new Task();
    $task->title = $request->input('title');
    $task->save();
    return redirect()->route('tasks.index');
}

Étape 4 : Créer une Vue

flowchart TD User((User)) -->|Sends request| Route(Route) Route -->|Calls| Controller(Controller Function) Controller -->|Queries| Model(Model) Model -->|Interacts with| Database(Database Table) Database -->|Returns data to| Model Model -->|Passes data to| Controller Controller -->|Passes data to| View(View) View -->|Displays data to| User subgraph Request_Flow["Request Flow"] User --> Route Route --> Controller end subgraph Data_Flow["Data Flow"] Controller --> Model Model --> Database Database --> Model Model --> Controller end subgraph Response_Flow["Response Flow"] Controller --> View View --> User end style User fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff style Route fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff style Controller fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff style Model fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff style Database fill:#ff9800,stroke:#333,stroke-width:2px,color:#fff style View fill:#ffc107,stroke:#333,stroke-width:2px,color:#000

Créez un fichier index.blade.php dans le dossier resources/views/tasks :

<!DOCTYPE html>
<html>
<head>
    <title>Liste de Tâches</title>
</head>
<body>
    <h1>Liste de Tâches</h1>
    <ul>
        @foreach ($tasks as $task)
            <li>{{ $task->title }}</li>
        @endforeach
    </ul>

    <form action="{{ route('tasks.store') }}" method="POST">
        @csrf
        <input type="text" name="title" placeholder="Ajouter une tâche">
        <button type="submit">Ajouter</button>
    </form>
</body>
</html>

Étape 5 : Définir les Routes

Ouvrez le fichier routes/web.php et ajoutez les routes suivantes :

use App\Http\Controllers\TaskController;

Route::get('/tasks', [TaskController::class, 'index'])->name('tasks.index');
Route::post('/tasks', [TaskController::class, 'store'])->name('tasks.store');

4. Structure d'un Projet Laravel

Voici une vue d'ensemble des principaux dossiers et fichiers dans un projet Laravel :

Dossier app

Dossier config

Dossier database

Dossier public

Dossier resources

Dossier routes

Fichier .env

flowchart LR Root[Projet Laravel] --> App[app/] Root --> Routes[routes/] Root --> Database[database/] Root --> Resources[resources/] Root --> Public[public/] Root --> Config[config/] Root --> Storage[storage/] Root --> Tests[tests/] Root --> Files[Fichiers racine] subgraph App_Folder["app/"] App --> Models[Models/] App --> Controllers[Http/Controllers/] App --> Middleware[Http/Middleware/] App --> Events[Events/] App --> Jobs[Jobs/] end subgraph Routes_Folder["routes/"] Routes --> Web[web.php] Routes --> Api[api.php] Routes --> Console[console.php] Routes --> Channels[channels.php] end subgraph Database_Folder["database/"] Database --> Migrations[Migrations/] Database --> Seeders[Seeders/] Database --> Factories[Factories/] end subgraph Resources_Folder["resources/"] Resources --> Views[Views/] Resources --> Js[Js/] Resources --> Css[Css/] Resources --> Lang[Lang/] end subgraph Public_Folder["public/"] Public --> Index[index.php] Public --> Assets[Assets/] end subgraph Config_Folder["config/"] Config --> AppConfig[app.php] Config --> DbConfig[database.php] end subgraph Storage_Folder["storage/"] Storage --> Logs[Logs/] Storage --> AppFiles[App/] Storage --> Sessions[Sessions/] end subgraph Tests_Folder["tests/"] Tests --> Unit[Unit/] Tests --> Feature[Feature/] end subgraph Root_Files["Fichiers racine"] Files --> Env[.env] Files --> Composer[composer.json] Files --> Artisan[artisan] end style Root fill:#ff6f61,stroke:#333,stroke-width:2px,color:#fff style App fill:#4caf50,stroke:#333,stroke-width:2px,color:#fff style Routes fill:#9c27b0,stroke:#333,stroke-width:2px,color:#fff style Database fill:#03a9f4,stroke:#333,stroke-width:2px,color:#fff style Resources fill:#ffc107,stroke:#333,stroke-width:2px,color:#000 style Public fill:#ff9800,stroke:#333,stroke-width:2px,color:#fff style Config fill:#8bc34a,stroke:#333,stroke-width:2px,color:#000 style Storage fill:#00bcd4,stroke:#333,stroke-width:2px,color:#fff style Tests fill:#795548,stroke:#333,stroke-width:2px,color:#fff style Files fill:#e91e63,stroke:#333,stroke-width:2px,color:#fff
yyy

5. Conclusion

Ce tutoriel vous a introduit aux bases de Laravel, y compris son installation, la structure MVC et la création d'une application simple. Vous avez également appris à naviguer dans la structure d'un projet Laravel. À partir de là, vous pouvez approfondir vos connaissances en explorant des fonctionnalités avancées comme l'authentification, les relations Eloquent, et les API RESTful.

Si vous avez des questions ou besoin d'aide supplémentaire, n'hésitez pas à consulter la documentation officielle de Laravel.

créer un tutoriel bien detaillé sur "laravel:model et migration en incluant toutes les relations possible:belongsto,hasmany,haseone,table pivot , belongstomany,....

Laravel - Exemple 2

Voici l'exemple adapté pour le modèle Client (idClient, nom, prenom, email), en suivant la même structure.


📌 Création d'une Application de Gestion des Clients avec Laravel

Ce guide vous montrera comment créer une application Laravel permettant de gérer une liste de clients. Nous allons :
✅ Créer une migration pour la table clients
✅ Définir un modèle Client
✅ Mettre en place un contrôleur ClientController
✅ Créer une vue pour afficher et ajouter des clients
✅ Définir les routes correspondantes


🔹 Étape 1 : Créer une Migration

Générez une migration pour la table clients :

php artisan make:migration create_clients_table

Ouvrez le fichier généré dans database/migrations/ et modifiez-le comme suit :

public function up() { Schema::create('clients', function (Blueprint $table) { $table->id('idClient'); // Clé primaire personnalisée $table->string('nom'); $table->string('prenom'); $table->string('email')->unique(); $table->timestamps(); }); }

Exécutez la migration :

php artisan migrate

🔹 Étape 2 : Créer un Modèle

Créez un modèle Client pour interagir avec la table clients :

php artisan make:model Client

Modifiez le fichier app/Models/Client.php :

namespace App\Models; use Illuminate\Database\Eloquent\Factories\HasFactory; use Illuminate\Database\Eloquent\Model; class Client extends Model { use HasFactory; protected $table = 'clients'; protected $primaryKey = 'idClient'; protected $fillable = ['nom', 'prenom', 'email']; }

🔹 Étape 3 : Créer un Contrôleur

Générez un contrôleur ClientController :

php artisan make:controller ClientController --resource

Modifiez app/Http/Controllers/ClientController.php :

namespace App\Http\Controllers; use Illuminate\Http\Request; use App\Models\Client; class ClientController extends Controller { public function index() { $clients = Client::all(); return view('clients.index', compact('clients')); } public function store(Request $request) { $request->validate([ 'nom' => 'required|string|max:255', 'prenom' => 'required|string|max:255', 'email' => 'required|email|unique:clients,email', ]); Client::create($request->all()); return redirect()->route('clients.index'); } }

🔹 Étape 4 : Créer une Vue

Créez le fichier resources/views/clients/index.blade.php :

<!DOCTYPE html> <html lang="fr"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Liste des Clients</title> </head> <body> <h1>Liste des Clients</h1> <ul> @foreach ($clients as $client) <li>{{ $client->nom }} {{ $client->prenom }} - {{ $client->email }}</li> @endforeach </ul> <h2>Ajouter un Client</h2> <form action="{{ route('clients.store') }}" method="POST"> @csrf <input type="text" name="nom" placeholder="Nom" required> <input type="text" name="prenom" placeholder="Prénom" required> <input type="email" name="email" placeholder="Email" required> <button type="submit">Ajouter</button> </form> </body> </html>

🔹 Étape 5 : Définir les Routes

Ajoutez ces routes dans routes/web.php :

En utilisant ressource

Parceque le controller Client est créer avec ClientController --resource

use App\Http\Controllers\ClientController;

Route::resource('clients', ClientController::class);

Ou

use App\Http\Controllers\ClientController; Route::get('/clients', [ClientController::class, 'index'])->name('clients.index'); Route::post('/clients', [ClientController::class, 'store'])->name('clients.store');

🎯 Test de l'Application

1️⃣ Démarrez le serveur Laravel :

php artisan serve

2️⃣ Accédez à http://127.0.0.1:8000/clients pour voir la liste des clients et ajouter un nouvel enregistrement.


✅ Conclusion

Vous avez maintenant une application Laravel simple qui permet d'afficher et d'ajouter des clients dans une base de données. 🎉

Besoin d'une gestion plus avancée ? Vous pouvez ajouter des fonctionnalités comme l'édition et la suppression des clients. 🚀

Laravel - Modèles et Migrations avec Toutes les Relations Possibles

Dans ce tutoriel, nous allons explorer en détail comment utiliser les modèles et les migrations dans Laravel. Nous couvrirons également toutes les relations possibles entre les modèles, y compris belongsTo, hasMany, hasOne, belongsToMany (avec une table pivot), et bien d'autres.


1. Introduction aux Modèles et Migrations

Qu'est-ce qu'un Modèle ?

  • Un modèle dans Laravel représente une entité ou une table dans la base de données.
  • Il est utilisé pour interagir avec la base de données via l'ORM Eloquent.
  • Par exemple, un modèle User correspond à la table users dans la base de données.

Qu'est-ce qu'une Migration ?

  • Une migration est un fichier PHP qui définit la structure d'une table dans la base de données.
  • Les migrations permettent de gérer facilement la création, la modification et la suppression des tables sans toucher directement à la base de données.

2. Création d'un Modèle et d'une Migration

Étape 1 : Créer un Modèle avec une Migration

Pour créer un modèle et sa migration associée, utilisez la commande suivante :

php artisan make:model NomDuModele -m

Le flag -m génère automatiquement une migration associée au modèle.

Par exemple, pour créer un modèle Post :

php artisan make:model Post -m

Cela générera :

  • Un fichier Post.php dans le dossier app/Models.
  • Un fichier de migration dans le dossier database/migrations.

Étape 2 : Définir la Structure de la Table dans la Migration

Ouvrez le fichier de migration généré dans database/migrations. Voici un exemple pour une table posts :

public function up()
{
    Schema::create('posts', function (Blueprint $table) {
    $table->id('idpost'); // Custom primary key: 'idpost' instead of default 'id'
    $table->string('title');
    $table->text('content');
    $table->timestamps();
});
}

Exécutez la migration pour créer la table dans la base de données :

php artisan migrate

3. Relations entre les Modèles

Laravel Eloquent prend en charge plusieurs types de relations entre les modèles. Voici une explication détaillée de chaque relation avec des exemples.


Relation belongsTo

La relation belongsTo est utilisée lorsqu'une entité "appartient" à une autre. Par exemple, un Comment appartient à un Post.

Exemple : Comment Appartient à Post

  1. Créer les Modèles et Migrations

    • Créez un modèle Comment avec une migration :

      php artisan make:model Comment -m
      
    • Dans la migration comments, ajoutez une colonne post_id pour établir la relation :

      public function up()
      {
          Schema::create('comments', function (Blueprint $table) {
              $table->id('idcomment'); // Custom primary key for comments
              $table->unsignedBigInteger('post_id'); // Foreign key column
              $table->foreign('post_id')->references('idpost')->on('posts')->onDelete('cascade'); // Correct foreign key setup
              $table->text('content'); // Comment content
              $table->timestamps();
          });
      }
      
  2. Définir la Relation dans les Modèles

    • Dans le modèle Comment :

      class Comment extends Model
      {
          use HasFactory;
      
          protected $table = 'comments'; // Explicitly define the table name
      
          protected $primaryKey = 'idcomment'; // Define the custom primary key
      
          protected $fillable = ['post_id', 'content']; // Define fillable fields for mass assignment
      
          public function post()
          {
              return $this->belongsTo(Post::class, 'post_id', 'idpost');
          }
      }
      
    • Dans le modèle Post :

      class Post extends Model
      {
          use HasFactory;
      
          protected $table = 'posts'; // Explicitly define the table name
      
          protected $primaryKey = 'idpost'; // Define the custom primary key
      
          protected $fillable = ['title', 'content']; // Define fillable fields for mass assignment
      
          public function comments()
          {
              return $this->hasMany(Comment::class, 'post_id', 'idpost');
          }
      }
      
  3. Utiliser la Relation

    • Récupérez tous les commentaires d'un post :

      $post = Post::find(1);
      $comments = $post->comments;
      

Relation hasMany

La relation hasMany est utilisée lorsqu'une entité "a plusieurs" autres entités. Par exemple, un Post a plusieurs Comments.

Exemple : Post a Plusieurs Comments

(Voir l'exemple précédent.)


Relation hasOne

La relation hasOne est utilisée lorsqu'une entité "a une seule" autre entité. Par exemple, un User a un Profile.

Exemple : User a un Profile

  1. Créer les Modèles et Migrations

    • Créez un modèle Profile avec une migration :

      php artisan make:model Profile -m
      
    • Dans la migration profiles, ajoutez une colonne user_id :

      public function up()
      {
          Schema::create('profiles', function (Blueprint $table) {
              $table->id('idprofile'); // Define a custom primary key (if needed)
              $table->unsignedBigInteger('user_id'); // Define the foreign key column
              $table->string('bio');
              $table->timestamps();
      
              // Set up the foreign key constraint manually
              $table->foreign('user_id')->references('iduser')->on('users')->onDelete('cascade');
          });
      }
      
  2. Définir la Relation dans les Modèles

    • Dans le modèle User :

      class User extends Model
      {
          use HasFactory;
      
          protected $table = 'users'; // Explicitly define the table name
      
          protected $primaryKey = 'iduser'; // Define the custom primary key
      
          protected $fillable = ['name', 'email', 'password']; // Define fillable fields for mass assignment
      
          public function profile()
          {
              return $this->hasOne(Profile::class, 'user_id', 'iduser');
          }
      }
      
    • Dans le modèle Profile :

      class Profile extends Model
      {
          use HasFactory;
      
          protected $table = 'profiles'; // Explicitly define the table name
      
          protected $primaryKey = 'idprofile'; // Define the custom primary key
      
          protected $fillable = ['user_id', 'bio']; // Define fillable fields for mass assignment
      
          public function user()
          {
              return $this->belongsTo(User::class, 'user_id', 'iduser');
          }
      }
      
  3. Utiliser la Relation

    • Récupérez le profil d'un utilisateur :

      $user = User::find(1);
      $profile = $user->profile;
      

Relation belongsToMany (Table Pivot)

La relation belongsToMany est utilisée pour une relation "many-to-many". Elle nécessite une table pivot pour établir la connexion. Par exemple, un User peut avoir plusieurs Roles, et un Role peut être attribué à plusieurs Users.

Exemple : User et Role

  1. Créer les Modèles et Migrations

    • Créez les modèles User et Role :

      php artisan make:model Role -m
      
    • Créez une migration pour la table pivot role_user :

      php artisan make:migration create_role_user_table
      
    • Dans la migration role_user :

      public function up()
      {
          Schema::create('role_user', function (Blueprint $table) {
              $table->unsignedBigInteger('user_id'); // Define the user foreign key column
              $table->unsignedBigInteger('role_id'); // Define the role foreign key column
      
              // Define foreign key constraints manually
              $table->foreign('user_id')->references('iduser')->on('users')->onDelete('cascade');
              $table->foreign('role_id')->references('idrole')->on('roles')->onDelete('cascade');
      
              // Define composite primary key
              $table->primary(['user_id', 'role_id']);
          });
      }
      
      
  2. Définir la Relation dans les Modèles

    • Dans le modèle User :

      class User extends Model
      {
          use HasFactory;
      
          protected $table = 'users'; // Explicitly define the table name
      
          protected $primaryKey = 'iduser'; // Define the custom primary key
      
          protected $fillable = ['name', 'email', 'password']; // Define fillable fields for mass assignment
      
          public function roles()
          {
              return $this->belongsToMany(Role::class, 'role_user', 'user_id', 'role_id');
          }
      }
      
    • Dans le modèle Role :

      class Role extends Model
      {
          use HasFactory;
      
          protected $table = 'roles'; // Explicitly define the table name
      
          protected $primaryKey = 'idrole'; // Define the custom primary key
      
          protected $fillable = ['name', 'description']; // Define fillable fields for mass assignment
      
          public function users()
          {
              return $this->belongsToMany(User::class, 'role_user', 'role_id', 'user_id');
          }
      }
      
  3. Utiliser la Relation

    • Attribuez un rôle à un utilisateur :

      $user = User::find(1);
      $role = Role::find(1);
      $user->roles()->attach($role);
      
    • Récupérez les rôles d'un utilisateur :

      $roles = $user->roles;
      

Relation hasOneThrough

La relation hasOneThrough est utilisée pour accéder à une entité via une autre entité intermédiaire. Par exemple, un Country a un Post via un User.

Exemple : Country -> User -> Post

  1. Définir la Relation

    • Dans le modèle Country :

      class Country extends Model
      {
          use HasFactory;
      
          protected $table = 'countries'; // Explicitly define the table name
      
          protected $primaryKey = 'idcountry'; // Define the custom primary key
      
          protected $fillable = ['name']; // Define fillable fields for mass assignment
      
          public function post()
          {
              return $this->hasOneThrough(
                  Post::class,  // Final target model
                  User::class,  // Intermediate model
                  'country_id', // Foreign key on the users table
                  'user_id',    // Foreign key on the posts table
                  'idcountry',  // Local primary key in the countries table
                  'iduser'      // Local primary key in the users table
              );
          }
      }
      
  2. Utiliser la Relation

    • Récupérez le post d'un pays :

      $country = Country::find(1);
      $post = $country->post;
      

Relation hasManyThrough

La relation hasManyThrough est similaire à hasOneThrough, mais elle retourne plusieurs résultats. Par exemple, un Country a plusieurs Posts via des Users.

Exemple : Country -> Users -> Posts

  1. Définir la Relation

    • Dans le modèle Country :

      class Country extends Model
      {
          use HasFactory;
      
          protected $table = 'countries'; // Explicitly define the table name
      
          protected $primaryKey = 'idcountry'; // Define the custom primary key
      
          protected $fillable = ['name']; // Define fillable fields for mass assignment
      
          public function posts()
          {
              return $this->hasManyThrough(
                  Post::class,  // Final target model
                  User::class,  // Intermediate model
                  'country_id', // Foreign key on the users table
                  'user_id',    // Foreign key on the posts table
                  'idcountry',  // Local primary key in the countries table
                  'iduser'      // Local primary key in the users table
              );
          }
      }
      
  2. Utiliser la Relation

    • Récupérez les posts d'un pays :

      $country = Country::find(1);
      $posts = $country->posts;
      

Exemple 2

Schéma MLD en Notation Inline

User(idUser, name, email, email_verified_at, password, remember_token, created_at, updated_at)

Vehicle(idVehicle, make, model, year, #idUser, created_at, updated_at)

Trip(idTrip, #idVehicle, start_time, end_time, price, created_at, updated_at)

Reservation(idReservation, #idTrip, #idUser, reservation_date, created_at, updated_at)

Review(idReview, #idTrip, #idUser, comment, rating, created_at, updated_at)

Étape 1: Création des Migrations

Nous allons commencer par créer les migrations pour chaque table.

1. Migration pour la Table users

php artisan make:migration create_users_table --create=users
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_users_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateUsersTable extends Migration
{
    public function up()
    {
        Schema::create('users', function (Blueprint $table) {
            $table->id('idUser');
            $table->string('name');
            $table->string('email')->unique();
            $table->timestamp('email_verified_at')->nullable();
            $table->string('password');
            $table->rememberToken();
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('users');
    }
}

2. Migration pour la Table vehicles

php artisan make:migration create_vehicles_table --create=vehicles
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_vehicles_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateVehiclesTable extends Migration
{
    public function up()
    {
        Schema::create('vehicles', function (Blueprint $table) {
            $table->id('idVehicle');
            $table->string('make');
            $table->string('model');
            $table->integer('year');
            $table->unsignedBigInteger('idUser');
            $table->foreign('idUser')->references('idUser')->on('users')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('vehicles');
    }
}

3. Migration pour la Table trips

php artisan make:migration create_trips_table --create=trips
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_trips_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateTripsTable extends Migration
{
    public function up()
    {
        Schema::create('trips', function (Blueprint $table) {
            $table->id('idTrip');
            $table->unsignedBigInteger('idVehicle');
            $table->foreign('idVehicle')->references('idVehicle')->on('vehicles')->onDelete('cascade');
            $table->dateTime('start_time');
            $table->dateTime('end_time');
            $table->decimal('price', 8, 2);
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('trips');
    }
}

4. Migration pour la Table reservations

php artisan make:migration create_reservations_table --create=reservations
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_reservations_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateReservationsTable extends Migration
{
    public function up()
    {
        Schema::create('reservations', function (Blueprint $table) {
            $table->id('idReservation');
            $table->unsignedBigInteger('idTrip');
            $table->foreign('idTrip')->references('idTrip')->on('trips')->onDelete('cascade');
            $table->unsignedBigInteger('idUser');
            $table->foreign('idUser')->references('idUser')->on('users')->onDelete('cascade');
            $table->dateTime('reservation_date');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('reservations');
    }
}

5. Migration pour la Table reviews

php artisan make:migration create_reviews_table --create=reviews
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_reviews_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateReviewsTable extends Migration
{
    public function up()
    {
        Schema::create('reviews', function (Blueprint $table) {
            $table->id('idReview');
            $table->unsignedBigInteger('idTrip');
            $table->foreign('idTrip')->references('idTrip')->on('trips')->onDelete('cascade');
            $table->unsignedBigInteger('idUser');
            $table->foreign('idUser')->references('idUser')->on('users')->onDelete('cascade');
            $table->text('comment');
            $table->integer('rating');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('reviews');
    }
}

Étape 2: Exécution des Migrations

Exécutez les migrations pour créer les tables dans la base de données:
php artisan migrate
Étape 3: Création des Modèles

1. Modèle User

php artisan make:model User
Modifier le fichier généré (app/Models/User.php):
namespace App\Models;

use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;

class User extends Authenticatable
{
    use Notifiable;

    protected $table = 'users';
    protected $primaryKey = 'idUser';
    protected $fillable = ['name', 'email', 'email_verified_at', 'password', 'remember_token'];

    public function vehicles()
    {
        return $this->hasMany(Vehicle::class, 'idUser');
    }

    public function reservations()
    {
        return $this->hasMany(Reservation::class, 'idUser');
    }

    public function reviews()
    {
        return $this->hasMany(Review::class, 'idUser');
    }
}

2. Modèle Vehicle

php artisan make:model Vehicle
Modifier le fichier généré (app/Models/Vehicle.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Vehicle extends Model
{
    use HasFactory;

    protected $table = 'vehicles';
    protected $primaryKey = 'idVehicle';
    protected $fillable = ['make', 'model', 'year', 'idUser'];

    public function user()
    {
        return $this->belongsTo(User::class, 'idUser');
    }

    public function trips()
    {
        return $this->hasMany(Trip::class, 'idVehicle');
    }
}

3. Modèle Trip

php artisan make:model Trip
Modifier le fichier généré (app/Models/Trip.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Trip extends Model
{
    use HasFactory;

    protected $table = 'trips';
    protected $primaryKey = 'idTrip';
    protected $fillable = ['idVehicle', 'start_time', 'end_time', 'price'];

    public function vehicle()
    {
        return $this->belongsTo(Vehicle::class, 'idVehicle');
    }

    public function reservations()
    {
        return $this->hasMany(Reservation::class, 'idTrip');
    }

    public function reviews()
    {
        return $this->hasMany(Review::class, 'idTrip');
    }
}

4. Modèle Reservation

php artisan make:model Reservation
Modifier le fichier généré (app/Models/Reservation.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Reservation extends Model
{
    use HasFactory;

    protected $table = 'reservations';
    protected $primaryKey = 'idReservation';
    protected $fillable = ['idTrip', 'idUser', 'reservation_date'];

    public function trip()
    {
        return $this->belongsTo(Trip::class, 'idTrip');
    }

    public function user()
    {
        return $this->belongsTo(User::class, 'idUser');
    }
}

5. Modèle Review

php artisan make:model Review
Modifier le fichier généré (app/Models/Review.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Review extends Model
{
    use HasFactory;

    protected $table = 'reviews';
    protected $primaryKey = 'idReview';
    protected $fillable = ['idTrip', 'idUser', 'comment', 'rating'];

    public function trip()
    {
        return $this->belongsTo(Trip::class, 'idTrip');
    }

    public function user()
    {
        return $this->belongsTo(User::class, 'idUser');
    }
}

Exercice Créer les migrations et les modèles

Schéma MLD en Notation Inline
User(idUser, name, email, email_verified_at, password, remember_token, created_at, updated_at)

Team(idTeam, name, coach, stadium, created_at, updated_at)

Player(idPlayer, name, position, date_of_birth, #idTeam, created_at, updated_at)

Match(idMatch, #idHomeTeam, #idAwayTeam, match_date, location, created_at, updated_at)

Goal(idGoal, #idMatch, #idPlayer, minute, created_at, updated_at)

Comment(idComment, #idMatch, #idUser, content, created_at, updated_at)
  1. User -> Comment (One-to-Many)

    • Un utilisateur peut écrire plusieurs commentaires.
    • La clé étrangère idUser est présente dans la table Comment.
  2. Team -> Player (One-to-Many)

    • Une équipe peut avoir plusieurs joueurs.
    • La clé étrangère idTeam est présente dans la table Player.
  3. Team -> Match (One-to-Many)

    • Une équipe peut jouer dans plusieurs matchs (en tant qu'équipe à domicile ou équipe visiteuse).
    • La clé étrangère idHomeTeam et idAwayTeam sont présentes dans la table Match.
  4. Match -> Goal (One-to-Many)

    • Un match peut avoir plusieurs buts marqués.
    • La clé étrangère idMatch est présente dans la table Goal.
  5. Player -> Goal (One-to-Many)

    • Un joueur peut marquer plusieurs buts.
    • La clé étrangère idPlayer est présente dans la table Goal.
  6. Match -> Comment (One-to-Many)

    • Un match peut avoir plusieurs commentaires.
    • La clé étrangère idMatch est présente dans la table Comment.

Exemple3 Créer les migrations et les modèles

Schéma MLD en Notation Inline
User(idUser, name, email, email_verified_at, password, remember_token, created_at, updated_at)

Team(idTeam, name, coach, #idStadium, created_at, updated_at)

Player(idPlayer, name, position, date_of_birth, #idTeam, created_at, updated_at)

Match(idMatch, #idHomeTeam, #idAwayTeam, match_date, #idLeague, location, created_at, updated_at)

Goal(idGoal, #idMatch, #idPlayer, minute, created_at, updated_at)

Comment(idComment, #idMatch, #idUser, content, created_at, updated_at)

Stadium(idStadium, name, capacity, location, created_at, updated_at)

League(idLeague, name, country, created_at, updated_at)

PlayerMatch(idPlayerMatch, #idPlayer, #idMatch, minutes_played, created_at, updated_at)
  1. User -> Comment (One-to-Many)

    • Un utilisateur peut écrire plusieurs commentaires.
    • La clé étrangère idUser est présente dans la table Comment.
  2. Team -> Player (One-to-Many)

    • Une équipe peut avoir plusieurs joueurs.
    • La clé étrangère idTeam est présente dans la table Player.
  3. Stadium -> Team (One-to-Many)

    • Un stade peut accueillir plusieurs équipes.
    • La clé étrangère idStadium est présente dans la table Team.
  4. League -> Match (One-to-Many)

    • Une ligue peut avoir plusieurs matchs.
    • La clé étrangère idLeague est présente dans la table Match.
  5. Match -> Goal (One-to-Many)

    • Un match peut avoir plusieurs buts marqués.
    • La clé étrangère idMatch est présente dans la table Goal.
  6. Player -> Goal (One-to-Many)

    • Un joueur peut marquer plusieurs buts.
    • La clé étrangère idPlayer est présente dans la table Goal.
  7. Match -> Comment (One-to-Many)

    • Un match peut avoir plusieurs commentaires.
    • La clé étrangère idMatch est présente dans la table Comment.
  8. Team -> Match (Many-to-One)

    • Un match peut impliquer une équipe à domicile et une équipe visiteuse.
    • Les clés étrangères idHomeTeam et idAwayTeam sont présentes dans la table Match.
  9. Player <-> Match (Many-to-Many) via PlayerMatch

    • Un joueur peut participer à plusieurs matchs, et un match peut avoir plusieurs joueurs.
    • La table pivot PlayerMatch relie Player et Match avec des attributs supplémentaires comme minutes_played.
Étape 1: Création des Migrations
php artisan make:migration create_users_table --create=users
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_users_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateUsersTable extends Migration
{
    public function up()
    {
        Schema::create('users', function (Blueprint $table) {
            $table->id('idUser');
            $table->string('name');
            $table->string('email')->unique();
            $table->timestamp('email_verified_at')->nullable();
            $table->string('password');
            $table->rememberToken();
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('users');
    }
}
2. Migration pour la Table stadiums
php artisan make:migration create_stadiums_table --create=stadiums
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_stadiums_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateStadiumsTable extends Migration
{
    public function up()
    {
        Schema::create('stadiums', function (Blueprint $table) {
            $table->id('idStadium');
            $table->string('name');
            $table->integer('capacity');
            $table->string('location');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('stadiums');
    }
}
3. Migration pour la Table leagues
php artisan make:migration create_leagues_table --create=leagues
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_leagues_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateLeaguesTable extends Migration
{
    public function up()
    {
        Schema::create('leagues', function (Blueprint $table) {
            $table->id('idLeague');
            $table->string('name');
            $table->string('country');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('leagues');
    }
}
4. Migration pour la Table teams
php artisan make:migration create_teams_table --create=teams
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_teams_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateTeamsTable extends Migration
{
    public function up()
    {
        Schema::create('teams', function (Blueprint $table) {
            $table->id('idTeam');
            $table->string('name');
            $table->string('coach');
            $table->unsignedBigInteger('idStadium');
            $table->foreign('idStadium')->references('idStadium')->on('stadiums')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('teams');
    }
}
5. Migration pour la Table players
php artisan make:migration create_players_table --create=players
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_players_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreatePlayersTable extends Migration
{
    public function up()
    {
        Schema::create('players', function (Blueprint $table) {
            $table->id('idPlayer');
            $table->string('name');
            $table->string('position');
            $table->date('date_of_birth');
            $table->unsignedBigInteger('idTeam');
            $table->foreign('idTeam')->references('idTeam')->on('teams')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('players');
    }
}
6. Migration pour la Table matches
php artisan make:migration create_matches_table --create=matches
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_matches_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateMatchesTable extends Migration
{
    public function up()
    {
        Schema::create('matches', function (Blueprint $table) {
            $table->id('idMatch');
            $table->unsignedBigInteger('idHomeTeam');
            $table->unsignedBigInteger('idAwayTeam');
            $table->unsignedBigInteger('idLeague');
            $table->dateTime('match_date');
            $table->string('location');
            $table->foreign('idHomeTeam')->references('idTeam')->on('teams')->onDelete('cascade');
            $table->foreign('idAwayTeam')->references('idTeam')->on('teams')->onDelete('cascade');
            $table->foreign('idLeague')->references('idLeague')->on('leagues')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('matches');
    }
}
7. Migration pour la Table goals
php artisan make:migration create_goals_table --create=goals
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_goals_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateGoalsTable extends Migration
{
    public function up()
    {
        Schema::create('goals', function (Blueprint $table) {
            $table->id('idGoal');
            $table->unsignedBigInteger('idMatch');
            $table->unsignedBigInteger('idPlayer');
            $table->integer('minute');
            $table->foreign('idMatch')->references('idMatch')->on('matches')->onDelete('cascade');
            $table->foreign('idPlayer')->references('idPlayer')->on('players')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('goals');
    }
}
8. Migration pour la Table comments
php artisan make:migration create_comments_table --create=comments
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_comments_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateCommentsTable extends Migration
{
    public function up()
    {
        Schema::create('comments', function (Blueprint $table) {
            $table->id('idComment');
            $table->unsignedBigInteger('idMatch');
            $table->unsignedBigInteger('idUser');
            $table->text('content');
            $table->foreign('idMatch')->references('idMatch')->on('matches')->onDelete('cascade');
            $table->foreign('idUser')->references('idUser')->on('users')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('comments');
    }
}
9. Migration pour la Table player_match
php artisan make:migration create_player_match_table --create=player_match
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_player_match_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreatePlayerMatchTable extends Migration
{
    public function up()
    {
        Schema::create('player_match', function (Blueprint $table) {
            $table->id('idPlayerMatch');
            $table->unsignedBigInteger('idPlayer');
            $table->unsignedBigInteger('idMatch');
            $table->integer('minutes_played');
            $table->foreign('idPlayer')->references('idPlayer')->on('players')->onDelete('cascade');
            $table->foreign('idMatch')->references('idMatch')->on('matches')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('player_match');
    }
}
Étape 2: Exécution des Migrations
php artisan migrate
Étape 3: Création des Modèles Maintenant, créons les modèles pour chaque table en incluant les propriétés $table et $fillable. 1. Modèle User
php artisan make:model User
Modifier le fichier généré (app/Models/User.php):
namespace App\Models;

use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;

class User extends Authenticatable
{
    use Notifiable;

    protected $table = 'users';
    protected $primaryKey = 'idUser';
    protected $fillable = ['name', 'email', 'email_verified_at', 'password', 'remember_token'];

    public function comments()
    {
        return $this->hasMany(Comment::class, 'idUser');
    }
}
2. Modèle Stadium
php artisan make:model Stadium
Modifier le fichier généré (app/Models/Stadium.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Stadium extends Model
{
    use HasFactory;

    protected $table = 'stadiums';
    protected $primaryKey = 'idStadium';
    protected $fillable = ['name', 'capacity', 'location'];

    public function teams()
    {
        return $this->hasMany(Team::class, 'idStadium');
    }
}
3. Modèle League
php artisan make:model League
Modifier le fichier généré (app/Models/League.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class League extends Model
{
    use HasFactory;

    protected $table = 'leagues';
    protected $primaryKey = 'idLeague';
    protected $fillable = ['name', 'country'];

    public function matches()
    {
        return $this->hasMany(Match::class, 'idLeague');
    }
}
4. Modèle Team
php artisan make:model Team
Modifier le fichier généré (app/Models/Team.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Team extends Model
{
    use HasFactory;

    protected $table = 'teams';
    protected $primaryKey = 'idTeam';
    protected $fillable = ['name', 'coach', 'idStadium'];

    public function stadium()
    {
        return $this->belongsTo(Stadium::class, 'idStadium');
    }

    public function players()
    {
        return $this->hasMany(Player::class, 'idTeam');
    }

    public function homeMatches()
    {
        return $this->hasMany(Match::class, 'idHomeTeam');
    }

    public function awayMatches()
    {
        return $this->hasMany(Match::class, 'idAwayTeam');
    }
}
5. Modèle Player
php artisan make:model Player
Modifier le fichier généré (app/Models/Player.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Player extends Model
{
    use HasFactory;

    protected $table = 'players';
    protected $primaryKey = 'idPlayer';
    protected $fillable = ['name', 'position', 'date_of_birth', 'idTeam'];

    public function team()
    {
        return $this->belongsTo(Team::class, 'idTeam');
    }

    public function goals()
    {
        return $this->hasMany(Goal::class, 'idPlayer');
    }

    public function matches()
    {
        return $this->belongsToMany(Match::class, 'player_match', 'idPlayer', 'idMatch')->withPivot('minutes_played');
    }
}
6. Modèle Match
php artisan make:model Match
Modifier le fichier généré (app/Models/Match.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Match extends Model
{
    use HasFactory;

    protected $table = 'matches';
    protected $primaryKey = 'idMatch';
    protected $fillable = ['idHomeTeam', 'idAwayTeam', 'idLeague', 'match_date', 'location'];

    public function league()
    {
        return $this->belongsTo(League::class, 'idLeague');
    }

    public function homeTeam()
    {
        return $this->belongsTo(Team::class, 'idHomeTeam');
    }

    public function awayTeam()
    {
        return $this->belongsTo(Team::class, 'idAwayTeam');
    }

    public function goals()
    {
        return $this->hasMany(Goal::class, 'idMatch');
    }

    public function comments()
    {
        return $this->hasMany(Comment::class, 'idMatch');
    }

    public function players()
    {
        return $this->belongsToMany(Player::class, 'player_match', 'idMatch', 'idPlayer')->withPivot('minutes_played');
    }
}
7. Modèle Goal
php artisan make:model Goal
Modifier le fichier généré (app/Models/Goal.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Goal extends Model
{
    use HasFactory;

    protected $table = 'goals';
    protected $primaryKey = 'idGoal';
    protected $fillable = ['idMatch', 'idPlayer', 'minute'];

    public function match()
    {
        return $this->belongsTo(Match::class, 'idMatch');
    }

    public function player()
    {
        return $this->belongsTo(Player::class, 'idPlayer');
    }
}
8. Modèle Comment
php artisan make:model Comment
Modifier le fichier généré (app/Models/Comment.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Comment extends Model
{
    use HasFactory;

    protected $table = 'comments';
    protected $primaryKey = 'idComment';
    protected $fillable = ['idMatch', 'idUser', 'content'];

    public function match()
    {
        return $this->belongsTo(Match::class, 'idMatch');
    }

    public function user()
    {
        return $this->belongsTo(User::class, 'idUser');
    }
}

CRUD avec un Contrôleur de Ressource pour la Table client

Dans ce tutoriel, nous allons créer une application complète pour gérer les opérations CRUD (Create, Read, Update, Delete) sur une table client en utilisant un contrôleur de ressource dans Laravel. Nous couvrirons le modèle, la migration, le contrôleur, les routes (web.php) et les vues.


1. Étape 1 : Créer le Modèle et la Migration

Créer le Modèle et la Migration

Exécutez la commande suivante pour générer un modèle Client et sa migration associée :

php artisan make:model Client -m

Cela générera :

  • Un fichier Client.php dans le dossier app/Models.
  • Un fichier de migration dans le dossier database/migrations.

Modifier la Migration

Ouvrez le fichier de migration généré dans database/migrations et définissez la structure de la table clients :

 public function up()
    {
        Schema::create('clients', function (Blueprint $table) {
            $table->id('idclient'); // Clé primaire auto-incrémentée avec un nom personnalisé
            $table->string('nom'); // Colonne pour le nom du client
            $table->string('prenom'); // Colonne pour le prénom du client
            $table->timestamps(); // Colonnes created_at et updated_at
        });
    }

Exécutez la migration pour créer la table dans la base de données :

php artisan migrate

2. Étape 2 : Créer un Contrôleur de Ressource

Générer un Contrôleur de Ressource

Un contrôleur de ressource contient des méthodes prédéfinies pour les opérations CRUD. Créez un contrôleur ClientController :

php artisan make:controller ClientController --resource

Cela générera un fichier ClientController.php dans le dossier app/Http/Controllers. Le flag --resource crée automatiquement les méthodes suivantes :

  • index(): Liste tous les clients.
  • create(): Affiche le formulaire de création.
  • store(): Enregistre un nouveau client.
  • show(): Affiche un client spécifique.
  • edit(): Affiche le formulaire d'édition.
  • update(): Met à jour un client existant.
  • destroy(): Supprime un client.

Implémenter les Méthodes du Contrôleur

Ouvrez le fichier ClientController.php et ajoutez le code suivant :

namespace App\Http\Controllers;

use App\Models\Client;
use Illuminate\Http\Request;

class ClientController extends Controller
{
    // Liste tous les clients
    public function index()
    {
        $clients = Client::all();
        return view('clients.index', compact('clients'));
    }

    // Affiche le formulaire de création
    public function create()
    {
        return view('clients.create');
    }

    // Enregistre un nouveau client
    public function store(Request $request)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'prenom' => 'required|string|max:255',
        ]);

        Client::create($request->all());
        return redirect()->route('clients.index')->with('success', 'Client créé avec succès.');
    }

    // Affiche un client spécifique
    public function show(Client $client)
    {
        return view('clients.show', compact('client'));
    }

    // Affiche le formulaire d'édition
    public function edit(Client $client)
    {
        return view('clients.edit', compact('client'));
    }

    // Met à jour un client existant
    public function update(Request $request, Client $client)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'prenom' => 'required|string|max:255',
        ]);

        $client->update($request->all());
        return redirect()->route('clients.index')->with('success', 'Client mis à jour avec succès.');
    }

    // Supprime un client
    public function destroy(Client $client)
    {
        $client->delete();
        return redirect()->route('clients.index')->with('success', 'Client supprimé avec succès.');
    }
}

3. Étape 3 : Définir les Routes

Ajouter les Routes dans web.php

Ouvrez le fichier routes/web.php et ajoutez les routes pour le contrôleur de ressource :

use App\Http\Controllers\ClientController;

Route::resource('clients', ClientController::class);

Cela créera automatiquement les routes suivantes :

  • GET /clientsindex()
  • GET /clients/createcreate()
  • POST /clientsstore()
  • GET /clients/{client}show()
  • GET /clients/{client}/editedit()
  • PUT/PATCH /clients/{client}update()
  • DELETE /clients/{client}destroy()

4. Étape 4 : Créer les Vues

Structure des Dossiers

Créez un dossier clients dans resources/views pour organiser les vues.

Vue index.blade.php

Cette vue affiche la liste des clients et inclut des liens pour créer, éditer ou supprimer un client.

<!-- resources/views/clients/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Liste des Clients</title>
</head>
<body>
    <h1>Liste des Clients</h1>

    @if(session('success'))
        <div>{{ session('success') }}</div>
    @endif

    <a href="{{ route('clients.create') }}">Ajouter un Client</a>

    <ul>
        @foreach ($clients as $client)
            <li>
                {{ $client->nom }} {{ $client->prenom }}
                <a href="{{ route('clients.edit', $client->idclient) }}">Éditer</a>
                <form action="{{ route('clients.destroy', $client->idclient) }}" method="POST" style="display:inline;">
                    @csrf
                    @method('DELETE')
                    <button type="submit">Supprimer</button>
                </form>
            </li>
        @endforeach
    </ul>
</body>
</html>

Vue create.blade.php

Cette vue affiche un formulaire pour créer un nouveau client.

<!-- resources/views/clients/create.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Créer un Client</title>
</head>
<body>
    <h1>Créer un Client</h1>

    <form action="{{ route('clients.store') }}" method="POST">
        @csrf
        <label for="nom">Nom :</label>
        <input type="text" name="nom" id="nom" required><br>

        <label for="prenom">Prénom :</label>
        <input type="text" name="prenom" id="prenom" required><br>

        <button type="submit">Enregistrer</button>
    </form>

    <a href="{{ route('clients.index') }}">Retour à la liste</a>
</body>
</html>

Vue edit.blade.php

Cette vue affiche un formulaire pour éditer un client existant.

<!-- resources/views/clients/edit.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Éditer un Client</title>
</head>
<body>
    <h1>Éditer un Client</h1>

    <form action="{{ route('clients.update', $client->idclient) }}" method="POST">
        @csrf
        @method('PUT')
        <label for="nom">Nom :</label>
        <input type="text" name="nom" id="nom" value="{{ $client->nom }}" required><br>

        <label for="prenom">Prénom :</label>
        <input type="text" name="prenom" id="prenom" value="{{ $client->prenom }}" required><br>

        <button type="submit">Mettre à jour</button>
    </form>

    <a href="{{ route('clients.index') }}">Retour à la liste</a>
</body>
</html>

Vue show.blade.php

Cette vue affiche les détails d'un client spécifique.

<!-- resources/views/clients/show.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Détails du Client</title>
</head>
<body>
    <h1>Détails du Client</h1>

    <p>Nom : {{ $client->nom }}</p>
    <p>Prénom : {{ $client->prenom }}</p>

    <a href="{{ route('clients.index') }}">Retour à la liste</a>
</body>
</html>

5. Conclusion

Vous avez maintenant une application complète pour gérer les opérations CRUD sur la table client en utilisant un contrôleur de ressource dans Laravel. Voici un résumé des étapes que nous avons suivies :

  1. Création du modèle et de la migration.
  2. Génération et implémentation d'un contrôleur de ressource.
  3. Définition des routes dans web.php.
  4. Création des vues pour interagir avec l'utilisateur.

Pour tester l'application, démarrez le serveur local :

php artisan serve

Accédez à l'application via http://127.0.0.1:8000/clients.

Avec ces bases, vous pouvez maintenant personnaliser et étendre cette application pour répondre à vos besoins spécifiques. Bon développement !

CRUD sans Contrôleur de Ressource pour la Table client

Dans ce tutoriel, nous allons créer une application complète pour gérer les opérations CRUD (Create, Read, Update, Delete) sur une table client en utilisant des fonctions personnalisées dans un contrôleur standard. Nous ne utiliserons pas un contrôleur de ressource (--resource), mais plutôt des méthodes spécifiques comme ajouter, afficher, modifier, et supprimer.


1. Étape 1 : Créer le Modèle et la Migration

Créer le Modèle et la Migration

Exécutez la commande suivante pour générer un modèle Client et sa migration associée :

php artisan make:model Client -m

Cela générera :

  • Un fichier Client.php dans le dossier app/Models.
  • Un fichier de migration dans le dossier database/migrations.

Modifier la Migration

Ouvrez le fichier de migration généré dans database/migrations et définissez la structure de la table clients :

public function up()
    {
        Schema::create('clients', function (Blueprint $table) {
            $table->id('idclient'); // Clé primaire auto-incrémentée avec un nom personnalisé
            $table->string('nom'); // Colonne pour le nom du client
            $table->string('prenom'); // Colonne pour le prénom du client
            $table->timestamps(); // Colonnes created_at et updated_at
        });
    }

Exécutez la migration pour créer la table dans la base de données :

php artisan migrate

2. Étape 2 : Créer un Contrôleur Standard

Générer un Contrôleur Standard

Créez un contrôleur ClientController sans utiliser le flag --resource :

php artisan make:controller ClientController

Cela générera un fichier ClientController.php dans le dossier app/Http/Controllers. Vous devrez implémenter manuellement les méthodes pour les opérations CRUD.

Implémenter les Méthodes du Contrôleur

Ouvrez le fichier ClientController.php et ajoutez les méthodes suivantes :

namespace App\Http\Controllers;

use App\Models\Client;
use Illuminate\Http\Request;

class ClientController extends Controller
{
    // Liste tous les clients
    public function afficher()
    {
        $clients = Client::all();
        return view('clients.afficher', compact('clients'));
    }

    // Affiche le formulaire d'ajout
    public function creer()
    {
        return view('clients.creer');
    }

    // Enregistre un nouveau client
    public function ajouter(Request $request)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'prenom' => 'required|string|max:255',
        ]);

        Client::create($request->all());
        return redirect()->route('clients.afficher')->with('success', 'Client créé avec succès.');
    }

    // Affiche un client spécifique
    public function voir($id)
    {
        $client = Client::findOrFail($id);
        return view('clients.voir', compact('client'));
    }

    // Affiche le formulaire d'édition
    public function editer($id)
    {
        $client = Client::findOrFail($id);
        return view('clients.editer', compact('client'));
    }

    // Met à jour un client existant
    public function modifier(Request $request, $id)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'prenom' => 'required|string|max:255',
        ]);

        $client = Client::findOrFail($id);
        $client->update($request->all());
        return redirect()->route('clients.afficher')->with('success', 'Client mis à jour avec succès.');
    }

    // Supprime un client
    public function supprimer($id)
    {
        $client = Client::findOrFail($id);
        $client->delete();
        return redirect()->route('clients.afficher')->with('success', 'Client supprimé avec succès.');
    }
}

3. Étape 3 : Définir les Routes

Ajouter les Routes dans web.php

Ouvrez le fichier routes/web.php et ajoutez les routes pour chaque méthode du contrôleur :

use App\Http\Controllers\ClientController;

Route::get('/clients', [ClientController::class, 'afficher'])->name('clients.afficher');
Route::get('/clients/creer', [ClientController::class, 'creer'])->name('clients.creer');
Route::post('/clients/ajouter', [ClientController::class, 'ajouter'])->name('clients.ajouter');
Route::get('/clients/{id}', [ClientController::class, 'voir'])->name('clients.voir');
Route::get('/clients/{id}/editer', [ClientController::class, 'editer'])->name('clients.editer');
Route::put('/clients/{id}/modifier', [ClientController::class, 'modifier'])->name('clients.modifier');
Route::delete('/clients/{id}/supprimer', [ClientController::class, 'supprimer'])->name('clients.supprimer');

4. Étape 4 : Créer les Vues

Structure des Dossiers

Créez un dossier clients dans resources/views pour organiser les vues.

Vue afficher.blade.php

Cette vue affiche la liste des clients et inclut des liens pour créer, éditer ou supprimer un client.

<!-- resources/views/clients/afficher.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Liste des Clients</title>
</head>
<body>
    <h1>Liste des Clients</h1>

    @if(session('success'))
        <div>{{ session('success') }}</div>
    @endif

    <a href="{{ route('clients.creer') }}">Ajouter un Client</a>

    <ul>
        @foreach ($clients as $client)
            <li>
                {{ $client->nom }} {{ $client->prenom }}
                <a href="{{ route('clients.voir', $client->idclient) }}">Voir</a>
                <a href="{{ route('clients.editer', $client->idclient) }}">Éditer</a>
                <form action="{{ route('clients.supprimer', $client->idclient) }}" method="POST" style="display:inline;">
                    @csrf
                    @method('DELETE')
                    <button type="submit">Supprimer</button>
                </form>
            </li>
        @endforeach
    </ul>
</body>
</html>

Vue creer.blade.php

Cette vue affiche un formulaire pour créer un nouveau client.

<!-- resources/views/clients/creer.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Créer un Client</title>
</head>
<body>
    <h1>Créer un Client</h1>

    <form action="{{ route('clients.ajouter') }}" method="POST">
        @csrf
        <label for="nom">Nom :</label>
        <input type="text" name="nom" id="nom" required><br>

        <label for="prenom">Prénom :</label>
        <input type="text" name="prenom" id="prenom" required><br>

        <button type="submit">Enregistrer</button>
    </form>

    <a href="{{ route('clients.afficher') }}">Retour à la liste</a>
</body>
</html>

Vue editer.blade.php

Cette vue affiche un formulaire pour éditer un client existant.

<!-- resources/views/clients/editer.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Éditer un Client</title>
</head>
<body>
    <h1>Éditer un Client</h1>

    <form action="{{ route('clients.modifier', $client->idclient) }}" method="POST">
        @csrf
        @method('PUT')
        <label for="nom">Nom :</label>
        <input type="text" name="nom" id="nom" value="{{ $client->nom }}" required><br>

        <label for="prenom">Prénom :</label>
        <input type="text" name="prenom" id="prenom" value="{{ $client->prenom }}" required><br>

        <button type="submit">Mettre à jour</button>
    </form>

    <a href="{{ route('clients.afficher') }}">Retour à la liste</a>
</body>
</html>

Vue voir.blade.php

Cette vue affiche les détails d'un client spécifique.

<!-- resources/views/clients/voir.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Détails du Client</title>
</head>
<body>
    <h1>Détails du Client</h1>

    <p>Nom : {{ $client->nom }}</p>
    <p>Prénom : {{ $client->prenom }}</p>

    <a href="{{ route('clients.afficher') }}">Retour à la liste</a>
</body>
</html>

5. Conclusion

Vous avez maintenant une application complète pour gérer les opérations CRUD sur la table client en utilisant des fonctions personnalisées dans un contrôleur standard. Voici un résumé des étapes que nous avons suivies :

  1. Création du modèle et de la migration.
  2. Génération et implémentation d'un contrôleur standard avec des méthodes spécifiques (afficher, creer, ajouter, voir, editer, modifier, supprimer).
  3. Définition des routes dans web.php.
  4. Création des vues pour interagir avec l'utilisateur.

Pour tester l'application, démarrez le serveur local :

php artisan serve

Accédez à l'application via http://127.0.0.1:8000/clients.

Avec ces bases, vous pouvez maintenant personnaliser et étendre cette application pour répondre à vos besoins spécifiques. Bon développement !

Création d'une Application CRUD pour les Modèles Categorie et Produit

Dans ce tutoriel, nous allons créer une application complète pour gérer les opérations CRUD (Create, Read, Update, Delete) pour deux modèles : Categorie et Produit. Nous inclurons également la relation entre ces deux modèles (Produit appartient à une Categorie). Voici le code complet pour les migrations, modèles, relations, contrôleurs et vues.


1. Étape 1 : Créer les Migrations

Créer la Migration pour Categorie

Exécutez la commande suivante pour générer une migration pour la table categories :

php artisan make:migration create_categories_table

Ouvrez le fichier de migration généré dans database/migrations et définissez la structure de la table categories :

 public function up()
    {
        Schema::create('categories', function (Blueprint $table) {
            $table->id('idcategorie'); // Clé primaire auto-incrémentée avec un nom personnalisé
            $table->string('nom'); // Nom de la catégorie
            $table->text('description')->nullable(); // Description de la catégorie (peut être null)
            $table->timestamps(); // Colonnes created_at et updated_at
        });
    }

Créer la Migration pour Produit

Exécutez la commande suivante pour générer une migration pour la table produits :

php artisan make:migration create_produits_table

Ouvrez le fichier de migration généré dans database/migrations et définissez la structure de la table produits :

public function up()
    {
        Schema::create('produits', function (Blueprint $table) {
            $table->id('idproduit'); // Clé primaire auto-incrémentée avec un nom personnalisé
            $table->string('nom'); // Nom du produit
            $table->decimal('prix', 8, 2); // Prix du produit avec 8 chiffres au total et 2 décimales
            $table->foreignId('categorie_id')
                  ->constrained('categories') // Spécifie explicitement la table référencée
                  ->onDelete('cascade'); // Suppression en cascade si la catégorie est supprimée
            $table->timestamps(); // Colonnes created_at et updated_at
        });
    }

Exécuter les Migrations

Exécutez les migrations pour créer les tables dans la base de données :

php artisan migrate

2. Étape 2 : Créer les Modèles et Définir les Relations

Modèle Categorie

Créez un modèle Categorie :

php artisan make:model Categorie

Ajoutez la relation hasMany dans le modèle Categorie :

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Categorie extends Model
{
    use HasFactory;

    protected $table = 'categories'; // Nom explicite de la table
    protected $primaryKey = 'idcategorie'; // Clé primaire personnalisée

    protected $fillable = ['nom', 'description']; // Champs modifiables en masse

    // Une catégorie a plusieurs produits
    public function produits()
    {
        return $this->hasMany(Produit::class, 'categorie_id', 'idcategorie');
    }
}

Modèle Produit

Créez un modèle Produit :

php artisan make:model Produit

Ajoutez la relation belongsTo dans le modèle Produit :

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Produit extends Model
{
    use HasFactory;

    protected $table = 'produits'; // Nom explicite de la table
    protected $primaryKey = 'idproduit'; // Clé primaire personnalisée

    protected $fillable = ['nom', 'prix', 'categorie_id']; // Champs modifiables en masse

    // Un produit appartient à une catégorie
    public function categorie()
    {
        return $this->belongsTo(Categorie::class, 'categorie_id', 'idcategorie');
    }
}


3. Étape 3 : Créer les Contrôleurs

Contrôleur CategorieController

Créez un contrôleur CategorieController :

php artisan make:controller CategorieController

Implémentez les méthodes CRUD dans le contrôleur :

namespace App\Http\Controllers;

use App\Models\Categorie;
use Illuminate\Http\Request;

class CategorieController extends Controller
{
    // Liste toutes les catégories
    public function index()
    {
        $categories = Categorie::all();
        return view('categories.index', compact('categories'));
    }

    // Affiche le formulaire de création
    public function create()
    {
        return view('categories.create');
    }

    // Enregistre une nouvelle catégorie
    public function store(Request $request)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'description' => 'nullable|string',
        ]);

        Categorie::create($request->all());
        return redirect()->route('categories.index')->with('success', 'Catégorie créée avec succès.');
    }

    // Affiche une catégorie spécifique
    public function show(Categorie $categorie)
    {
        return view('categories.show', compact('categorie'));
    }

    // Affiche le formulaire d'édition
    public function edit(Categorie $categorie)
    {
        return view('categories.edit', compact('categorie'));
    }

    // Met à jour une catégorie existante
    public function update(Request $request, Categorie $categorie)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'description' => 'nullable|string',
        ]);

        $categorie->update($request->all());
        return redirect()->route('categories.index')->with('success', 'Catégorie mise à jour avec succès.');
    }

    // Supprime une catégorie
    public function destroy(Categorie $categorie)
    {
        $categorie->delete();
        return redirect()->route('categories.index')->with('success', 'Catégorie supprimée avec succès.');
    }
}

Contrôleur ProduitController

Créez un contrôleur ProduitController :

php artisan make:controller ProduitController

Implémentez les méthodes CRUD dans le contrôleur :

namespace App\Http\Controllers;

use App\Models\Produit;
use App\Models\Categorie;
use Illuminate\Http\Request;

class ProduitController extends Controller
{
    // Liste tous les produits
    public function index()
    {
        $produits = Produit::with('categorie')->get();
        return view('produits.index', compact('produits'));
    }

    // Affiche le formulaire de création
    public function create()
    {
        $categories = Categorie::all();
        return view('produits.create', compact('categories'));
    }

    // Enregistre un nouveau produit
    public function store(Request $request)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'prix' => 'required|numeric|min:0',
            'categorie_id' => 'required|exists:categories,id',
        ]);

        Produit::create($request->all());
        return redirect()->route('produits.index')->with('success', 'Produit créé avec succès.');
    }

    // Affiche un produit spécifique
    public function show(Produit $produit)
    {
        return view('produits.show', compact('produit'));
    }

    // Affiche le formulaire d'édition
    public function edit(Produit $produit)
    {
        $categories = Categorie::all();
        return view('produits.edit', compact('produit', 'categories'));
    }

    // Met à jour un produit existant
    public function update(Request $request, Produit $produit)
    {
        $request->validate([
            'nom' => 'required|string|max:255',
            'prix' => 'required|numeric|min:0',
            'categorie_id' => 'required|exists:categories,id',
        ]);

        $produit->update($request->all());
        return redirect()->route('produits.index')->with('success', 'Produit mis à jour avec succès.');
    }

    // Supprime un produit
    public function destroy(Produit $produit)
    {
        $produit->delete();
        return redirect()->route('produits.index')->with('success', 'Produit supprimé avec succès.');
    }
}

4. Étape 4 : Définir les Routes

Ajoutez les routes dans routes/web.php :

use App\Http\Controllers\CategorieController;
use App\Http\Controllers\ProduitController;

// Routes pour Catégorie
Route::get('/categories', [CategorieController::class, 'index'])->name('categories.index');
Route::get('/categories/create', [CategorieController::class, 'create'])->name('categories.create');
Route::post('/categories', [CategorieController::class, 'store'])->name('categories.store');
Route::get('/categories/{categorie}', [CategorieController::class, 'show'])->name('categories.show');
Route::get('/categories/{categorie}/edit', [CategorieController::class, 'edit'])->name('categories.edit');
Route::put('/categories/{categorie}', [CategorieController::class, 'update'])->name('categories.update');
Route::delete('/categories/{categorie}', [CategorieController::class, 'destroy'])->name('categories.destroy');

// Routes pour Produit
Route::get('/produits', [ProduitController::class, 'index'])->name('produits.index');
Route::get('/produits/create', [ProduitController::class, 'create'])->name('produits.create');
Route::post('/produits', [ProduitController::class, 'store'])->name('produits.store');
Route::get('/produits/{produit}', [ProduitController::class, 'show'])->name('produits.show');
Route::get('/produits/{produit}/edit', [ProduitController::class, 'edit'])->name('produits.edit');
Route::put('/produits/{produit}', [ProduitController::class, 'update'])->name('produits.update');
Route::delete('/produits/{produit}', [ProduitController::class, 'destroy'])->name('produits.destroy');

5. Étape 5 : Créer les Vues

Vue categories/index.blade.php

<!-- resources/views/categories/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Liste des Catégories</title>
</head>
<body>
    <h1>Liste des Catégories</h1>

    @if(session('success'))
        <div>{{ session('success') }}</div>
    @endif

    <a href="{{ route('categories.create') }}">Ajouter une Catégorie</a>

    <ul>
        @foreach ($categories as $categorie)
            <li>
                {{ $categorie->nom }} - {{ $categorie->description }}
                <a href="{{ route('categories.edit', $categorie->idcategorie) }}">Éditer</a>
                <form action="{{ route('categories.destroy', $categorie->idcategorie) }}" method="POST" style="display:inline;">
                    @csrf
                    @method('DELETE')
                    <button type="submit">Supprimer</button>
                </form>
            </li>
        @endforeach
    </ul>
</body>
</html>

Vue produits/index.blade.php

<!-- resources/views/produits/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Liste des Produits</title>
</head>
<body>
    <h1>Liste des Produits</h1>

    @if(session('success'))
        <div>{{ session('success') }}</div>
    @endif

    <a href="{{ route('produits.create') }}">Ajouter un Produit</a>

    <ul>
        @foreach ($produits as $produit)
            <li>
                {{ $produit->nom }} - {{ $produit->prix }} € ({{ $produit->categorie->nom }})
                <a href="{{ route('produits.edit', $produit->idproduit) }}">Éditer</a>
                <form action="{{ route('produits.destroy', $produit->idproduit) }}" method="POST" style="display:inline;">
                    @csrf
                    @method('DELETE')
                    <button type="submit">Supprimer</button>
                </form>
            </li>
        @endforeach
    </ul>
</body>
</html>

Les autres vues (create, edit, show) peuvent être créées en suivant le même principe que les exemples précédents.


6. Conclusion

Vous avez maintenant une application complète pour gérer les opérations CRUD pour les modèles Categorie et Produit, avec une relation belongsTo et hasMany. Vous pouvez tester l'application en démarrant le serveur local :

php artisan serve

Accédez aux routes via :

Bon développement !

Ajouter des Fonctions de Recherche, Filtrage et Calcul dans une Application Laravel

Dans ce tutoriel, nous allons ajouter des fonctionnalités avancées à notre application existante pour les modèles Categorie et Produit. Nous inclurons des fonctions pour rechercher un produit par nom, filtrer les produits par catégorie, et effectuer des calculs (par exemple, calculer le prix total des produits). Ces fonctionnalités seront ajoutées dans les contrôleurs, vues et routes.


1. Étape 1 : Ajouter des Fonctions dans les Contrôleurs

Ajouter la Fonction rechercherProduitParNom

Cette fonction permettra de rechercher des produits en fonction de leur nom.

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function rechercher(Request $request)
{
    $query = $request->input('query'); // Récupérer le terme de recherche depuis la requête

    // Rechercher les produits dont le nom contient le terme de recherche
    $produits = Produit::where('nom', 'like', '%' . $query . '%')->get();

    return view('produits.index', compact('produits'));
}

Ajouter la Fonction filterProduitParCategory

Cette fonction permettra de filtrer les produits par catégorie.

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function filterParCategorie($id)
{
    // Récupérer la catégorie spécifique
    $categorie = Categorie::findOrFail($id);

    // Filtrer les produits appartenant à cette catégorie
    $produits = $categorie->produits;

    return view('produits.index', compact('produits', 'categorie'));
}

Ajouter la Fonction de Calcul (Prix Total des Produits)

Cette fonction calculera le prix total de tous les produits ou d'une catégorie spécifique.

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function calculerPrixTotal()
{
    // Calculer le prix total de tous les produits
    $prixTotal = Produit::sum('prix');

    return view('produits.prix_total', compact('prixTotal'));
}

public function calculerPrixTotalParCategorie($id)
{
    // Récupérer la catégorie spécifique
    $categorie = Categorie::findOrFail($id);

    // Calculer le prix total des produits de cette catégorie
    $prixTotal = $categorie->produits()->sum('prix');

    return view('produits.prix_total', compact('prixTotal', 'categorie'));
}

2. Étape 2 : Ajouter des Routes

Ajoutez les nouvelles routes dans routes/web.php pour accéder aux fonctionnalités de recherche, filtrage et calcul :

// Route pour rechercher des produits par nom
Route::get('/produits/rechercher', [ProduitController::class, 'rechercher'])->name('produits.rechercher');

// Route pour filtrer les produits par catégorie
Route::get('/produits/filter/{id}', [ProduitController::class, 'filterParCategorie'])->name('produits.filter');

// Route pour calculer le prix total de tous les produits
Route::get('/produits/prix-total', [ProduitController::class, 'calculerPrixTotal'])->name('produits.prix_total');

// Route pour calculer le prix total des produits d'une catégorie spécifique
Route::get('/produits/prix-total/{id}', [ProduitController::class, 'calculerPrixTotalParCategorie'])->name('produits.prix_total_par_categorie');

3. Étape 3 : Mettre à Jour les Vues

Vue produits/index.blade.php

Ajoutez un formulaire de recherche et des liens pour filtrer les produits par catégorie :

<!-- resources/views/produits/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Liste des Produits</title>
</head>
<body>
    <h1>Liste des Produits</h1>

    @if(session('success'))
        <div>{{ session('success') }}</div>
    @endif

    <!-- Formulaire de Recherche -->
    <form action="{{ route('produits.rechercher') }}" method="GET">
        <input type="text" name="query" placeholder="Rechercher un produit...">
        <button type="submit">Rechercher</button>
    </form>

    <!-- Lien pour Afficher Tous les Produits -->
    <a href="{{ route('produits.index') }}">Afficher Tous les Produits</a>

    <!-- Filtrer par Catégorie -->
    <h2>Filtrer par Catégorie</h2>
    <ul>
        @foreach ($categories as $categorie)
            <li>
                <a href="{{ route('produits.filter', $categorie->id) }}">{{ $categorie->nom }}</a>
            </li>
        @endforeach
    </ul>

    <!-- Liste des Produits -->
    <ul>
        @foreach ($produits as $produit)
            <li>
                {{ $produit->nom }} - {{ $produit->prix }} € ({{ $produit->categorie->nom }})
                <a href="{{ route('produits.edit', $produit->id) }}">Éditer</a>
                <form action="{{ route('produits.destroy', $produit->id) }}" method="POST" style="display:inline;">
                    @csrf
                    @method('DELETE')
                    <button type="submit">Supprimer</button>
                </form>
            </li>
        @endforeach
    </ul>

    <!-- Liens pour Calculer le Prix Total -->
    <h2>Calculs</h2>
    <a href="{{ route('produits.prix_total') }}">Calculer le Prix Total de Tous les Produits</a>
    @if(isset($categorie))
        <a href="{{ route('produits.prix_total_par_categorie', $categorie->id) }}">Calculer le Prix Total de la Catégorie "{{ $categorie->nom }}"</a>
    @endif
</body>
</html>

Vue produits/prix_total.blade.php

Créez une nouvelle vue pour afficher le résultat des calculs :

<!-- resources/views/produits/prix_total.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Prix Total des Produits</title>
</head>
<body>
    <h1>Prix Total des Produits</h1>

    @if(isset($categorie))
        <p>Prix total des produits de la catégorie "{{ $categorie->nom }}" : {{ $prixTotal }} €</p>
    @else
        <p>Prix total de tous les produits : {{ $prixTotal }} €</p>
    @endif

    <a href="{{ route('produits.index') }}">Retour à la liste des produits</a>
</body>
</html>

4. Étape 4 : Tester les Fonctionnalités

Rechercher un Produit

Accédez à la page /produits et utilisez le formulaire de recherche pour trouver des produits par nom.

Filtrer les Produits par Catégorie

Cliquez sur une catégorie dans la liste pour filtrer les produits appartenant à cette catégorie.

Calculer le Prix Total

  • Accédez à /produits/prix-total pour calculer le prix total de tous les produits.
  • Accédez à /produits/prix-total/{id} pour calculer le prix total des produits d'une catégorie spécifique.

5. Conclusion

Vous avez maintenant une application complète avec des fonctionnalités avancées :

  • Recherche : Rechercher des produits par nom.
  • Filtrage : Filtrer les produits par catégorie.
  • Calcul : Calculer le prix total des produits (globalement ou par catégorie).

Ces fonctionnalités peuvent être facilement étendues pour inclure d'autres critères de recherche ou de filtrage. Bon développement !

Ajouter des Fonctionnalités Avancées pour Recherche, Filtrage, Groupage, Calcul et Tri

Dans ce tutoriel, nous allons ajouter encore plus de fonctionnalités avancées à notre application Laravel. Nous inclurons des fonctions pour :

  1. Rechercher avec plusieurs critères (nom, prix, catégorie).
  2. Filtrer avec plusieurs filtres (par exemple, par plage de prix ou par statut).
  3. Grouper les produits (par catégorie ou autre critère).
  4. Calculs avancés (moyenne des prix, nombre total de produits par catégorie).
  5. Trier les produits (par nom, prix, date de création).

1. Étape 1 : Ajouter des Fonctions dans les Contrôleurs

Ajouter la Fonction rechercherProduitAvecCritères

Cette fonction permettra de rechercher des produits en utilisant plusieurs critères (nom, prix, catégorie).

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function rechercher(Request $request)
{
    // Initialiser une requête Eloquent
    $query = Produit::query();

    // Filtrer par nom si fourni
    if ($request->has('nom')) {
        $query->where('nom', 'like', '%' . $request->input('nom') . '%');
    }

    // Filtrer par prix minimum si fourni
    if ($request->has('prix_min')) {
        $query->where('prix', '>=', $request->input('prix_min'));
    }

    // Filtrer par prix maximum si fourni
    if ($request->has('prix_max')) {
        $query->where('prix', '<=', $request->input('prix_max'));
    }

    // Filtrer par catégorie si fourni
    if ($request->has('categorie_id')) {
        $query->where('categorie_id', $request->input('categorie_id'));
    }

    // Récupérer les résultats
    $produits = $query->get();

    // Passer les catégories pour le formulaire de recherche
    $categories = Categorie::all();

    return view('produits.index', compact('produits', 'categories'));
}

Ajouter la Fonction grouperProduitsParCategorie

Cette fonction regroupera les produits par catégorie.

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function grouperParCategorie()
{
    // Grouper les produits par catégorie
    $groupedProducts = Produit::with('categorie')->get()->groupBy('categorie.nom');

    return view('produits.groupe_par_categorie', compact('groupedProducts'));
}

Ajouter la Fonction calculerStatistiques

Cette fonction calculera des statistiques avancées comme la moyenne des prix et le nombre total de produits par catégorie.

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function calculerStatistiques()
{
    // Calculer la moyenne des prix de tous les produits
    $prixMoyen = Produit::avg('prix');

    // Calculer le nombre total de produits par catégorie
    $nombreProduitsParCategorie = Categorie::withCount('produits')->get();

    return view('produits.statistiques', compact('prixMoyen', 'nombreProduitsParCategorie'));
}

Ajouter la Fonction trierProduits

Cette fonction triera les produits par nom, prix ou date de création.

Mise à Jour du Contrôleur ProduitController

Ajoutez la méthode suivante dans le contrôleur ProduitController :

public function trier(Request $request)
{
    // Définir l'ordre de tri par défaut
    $orderBy = $request->input('order_by', 'nom'); // Par défaut, trier par nom
    $orderDirection = $request->input('order_direction', 'asc'); // Par défaut, ordre ascendant

    // Trier les produits
    $produits = Produit::orderBy($orderBy, $orderDirection)->get();

    return view('produits.index', compact('produits'));
}

2. Étape 2 : Ajouter des Routes

Ajoutez les nouvelles routes dans routes/web.php pour accéder aux fonctionnalités avancées :

// Route pour rechercher des produits avec plusieurs critères
Route::get('/produits/rechercher', [ProduitController::class, 'rechercher'])->name('produits.rechercher');

// Route pour grouper les produits par catégorie
Route::get('/produits/grouper-par-categorie', [ProduitController::class, 'grouperParCategorie'])->name('produits.grouper_par_categorie');

// Route pour calculer des statistiques avancées
Route::get('/produits/statistiques', [ProduitController::class, 'calculerStatistiques'])->name('produits.statistiques');

// Route pour trier les produits
Route::get('/produits/trier', [ProduitController::class, 'trier'])->name('produits.trier');

3. Étape 3 : Mettre à Jour les Vues

Vue produits/index.blade.php

Ajoutez un formulaire de recherche avancée et des options de tri :

<!-- resources/views/produits/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Liste des Produits</title>
</head>
<body>
    <h1>Liste des Produits</h1>

    <!-- Formulaire de Recherche Avancée -->
    <form action="{{ route('produits.rechercher') }}" method="GET">
        <input type="text" name="nom" placeholder="Nom du produit...">
        <input type="number" name="prix_min" placeholder="Prix minimum...">
        <input type="number" name="prix_max" placeholder="Prix maximum...">

        <select name="categorie_id">
            <option value="">Toutes les catégories</option>
            @foreach ($categories as $categorie)
                <option value="{{ $categorie->id }}">{{ $categorie->nom }}</option>
            @endforeach
        </select>

        <button type="submit">Rechercher</button>
    </form>

    <!-- Options de Tri -->
    <form action="{{ route('produits.trier') }}" method="GET">
        <label for="order_by">Trier par :</label>
        <select name="order_by">
            <option value="nom">Nom</option>
            <option value="prix">Prix</option>
            <option value="created_at">Date de création</option>
        </select>

        <label for="order_direction">Ordre :</label>
        <select name="order_direction">
            <option value="asc">Croissant</option>
            <option value="desc">Décroissant</option>
        </select>

        <button type="submit">Trier</button>
    </form>

    <!-- Liste des Produits -->
    <ul>
        @foreach ($produits as $produit)
            <li>
                {{ $produit->nom }} - {{ $produit->prix }} € ({{ $produit->categorie->nom }})
                <a href="{{ route('produits.edit', $produit->id) }}">Éditer</a>
                <form action="{{ route('produits.destroy', $produit->id) }}" method="POST" style="display:inline;">
                    @csrf
                    @method('DELETE')
                    <button type="submit">Supprimer</button>
                </form>
            </li>
        @endforeach
    </ul>

    <!-- Liens pour Accéder aux Autres Fonctionnalités -->
    <h2>Autres Fonctionnalités</h2>
    <a href="{{ route('produits.grouper_par_categorie') }}">Grouper les Produits par Catégorie</a>
    <a href="{{ route('produits.statistiques') }}">Voir les Statistiques</a>
</body>
</html>

Vue produits/groupe_par_categorie.blade.php

Créez une nouvelle vue pour afficher les produits groupés par catégorie :

<!-- resources/views/produits/groupe_par_categorie.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Produits Groupés par Catégorie</title>
</head>
<body>
    <h1>Produits Groupés par Catégorie</h1>

    @foreach ($groupedProducts as $categorie => $produits)
        <h2>{{ $categorie }}</h2>
        <ul>
            @foreach ($produits as $produit)
                <li>{{ $produit->nom }} - {{ $produit->prix }} €</li>
            @endforeach
        </ul>
    @endforeach

    <a href="{{ route('produits.index') }}">Retour à la liste des produits</a>
</body>
</html>

Vue produits/statistiques.blade.php

Créez une nouvelle vue pour afficher les statistiques :

<!-- resources/views/produits/statistiques.blade.php -->
<!DOCTYPE html>
<html>
<head>
    <title>Statistiques des Produits</title>
</head>
<body>
    <h1>Statistiques des Produits</h1>

    <p>Prix moyen des produits : {{ $prixMoyen }} €</p>

    <h2>Nombre de Produits par Catégorie</h2>
    <ul>
        @foreach ($nombreProduitsParCategorie as $categorie)
            <li>{{ $categorie->nom }} : {{ $categorie->produits_count }} produits</li>
        @endforeach
    </ul>

    <a href="{{ route('produits.index') }}">Retour à la liste des produits</a>
</body>
</html>

4. Conclusion

Vous avez maintenant une application complète avec des fonctionnalités avancées :

  • Recherche avancée : Rechercher des produits avec plusieurs critères.
  • Filtrage avancé : Filtrer les produits par plage de prix ou par catégorie.
  • Groupage : Regrouper les produits par catégorie.
  • Calculs avancés : Calculer la moyenne des prix et le nombre total de produits par catégorie.
  • Tri : Trier les produits par nom, prix ou date de création.

Ces fonctionnalités peuvent être étendues davantage pour répondre à des besoins spécifiques. Bon développement !

Eloquent:

Tutoriel détaillé sur Laravel Eloquent

1. Introduction à Laravel Eloquent

Laravel Eloquent est un ORM (Object-Relational Mapping) inclus dans le framework Laravel. Il permet d'interagir avec la base de données en utilisant des objets PHP au lieu d'écrire des requêtes SQL directement. Cela simplifie grandement les opérations CRUD (Create, Read, Update, Delete).

1.1 Avantages d'Eloquent

  • Facilité d'utilisation : Les modèles Eloquent permettent de manipuler les données de manière intuitive.
  • Relations entre tables : Eloquent gère facilement les relations entre les tables (hasOne, hasMany, belongsTo, etc.).
  • Validation et événements : Eloquent offre des fonctionnalités avancées comme les événements de modèle et la validation des données.

2. Configuration initiale

Pour utiliser Eloquent, vous devez avoir un projet Laravel configuré avec une base de données. Assurez-vous que votre fichier .env contient les bonnes informations de connexion à la base de données :


DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=your_database_name
DB_USERNAME=your_username
DB_PASSWORD=your_password
    

3. Création d'un modèle Eloquent

Un modèle Eloquent représente une table dans la base de données. Chaque modèle est associé à une table spécifique.

3.1 Créer un modèle

Pour créer un modèle, utilisez la commande Artisan suivante :

php artisan make:model NomDuModele

Cela crée un fichier dans le dossier app/Models. Par exemple, si vous créez un modèle nommé Article, le fichier sera app/Models/Article.php.

3.2 Convention de nommage

Par défaut, Eloquent associe un modèle à une table dont le nom est le pluriel du nom du modèle en minuscules. Par exemple :

  • Modèle : Article
  • Table associée : articles

Si votre table a un nom différent, vous pouvez spécifier le nom de la table dans le modèle :


namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Article extends Model
{
    protected $table = 'custom_table_name';
}
    

4. Opérations CRUD avec Eloquent

Eloquent permet d'effectuer des opérations CRUD de manière simple et intuitive.

4.1 Créer un enregistrement (Create)

Pour insérer un nouvel enregistrement dans la table, utilisez la méthode create() :


use App\Models\Article;

$data = [
    'title' => 'Mon premier article',
    'content' => 'Ceci est le contenu de l\'article.',
];

$article = Article::create($data);
    

Assurez-vous que les colonnes sont remplies correctement et que les champs autorisés sont définis dans la propriété $fillable du modèle :


protected $fillable = ['title', 'content'];
    

4.2 Lire des enregistrements (Read)

Pour récupérer tous les enregistrements d'une table :

$articles = Article::all();

Pour récupérer un enregistrement par son ID :

$article = Article::find(1);

Pour récupérer un enregistrement avec des conditions spécifiques :

$article = Article::where('title', 'Mon premier article')->first();

4.3 Mettre à jour un enregistrement (Update)

Pour mettre à jour un enregistrement existant :


$article = Article::find(1);
$article->title = 'Nouveau titre';
$article->save();
    

Ou utilisez la méthode update() :


$article = Article::find(1);
$article->update(['title' => 'Nouveau titre']);
    

4.4 Supprimer un enregistrement (Delete)

Pour supprimer un enregistrement :


$article = Article::find(1);
$article->delete();
    

Ou utilisez la méthode destroy() pour supprimer par ID :

Article::destroy(1);

5. Relations entre modèles

Eloquent permet de définir des relations entre les modèles pour représenter les associations entre les tables.

5.1 Relation One-to-One (hasOne / belongsTo)

Exemple : Un utilisateur a un profil.

Dans le modèle User :


public function profile()
{
    return $this->hasOne(Profile::class);
}
    

Dans le modèle Profile :


public function user()
{
    return $this->belongsTo(User::class);
}
    

5.2 Relation One-to-Many (hasMany / belongsTo)

Exemple : Un utilisateur peut avoir plusieurs articles.

Dans le modèle User :


public function articles()
{
    return $this->hasMany(Article::class);
}
    

Dans le modèle Article :


public function user()
{
    return $this->belongsTo(User::class);
}
    

5.3 Relation Many-to-Many (belongsToMany)

Exemple : Un article peut avoir plusieurs tags, et un tag peut être associé à plusieurs articles.

Dans le modèle Article :


public function tags()
{
    return $this->belongsToMany(Tag::class);
}
    

Dans le modèle Tag :


public function articles()
{
    return $this->belongsToMany(Article::class);
}
    

6. Pagination

Pour paginer les résultats, utilisez la méthode paginate() :

$articles = Article::paginate(10);

Cela renvoie 10 enregistrements par page avec des liens pour naviguer entre les pages.

7. Événements de modèle

Eloquent déclenche des événements lors des opérations CRUD. Vous pouvez écouter ces événements pour exécuter du code personnalisé.

Exemple : Ajouter un timestamp lors de la création d'un enregistrement :


protected static function boot()
{
    parent::boot();

    static::creating(function ($model) {
        $model->created_at = now();
    });
}
    

Tutoriel détaillé sur les fonctions Eloquent

Introduction

Dans ce tutoriel, nous allons explorer les fonctions couramment utilisées dans Laravel Eloquent pour interagir avec la base de données. Chaque fonction sera expliquée avec des exemples concrets.

1. Récupérer tous les enregistrements : all()

La méthode all() permet de récupérer tous les enregistrements d'une table.


use App\Models\Article;

$articles = Article::all();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode renvoie une collection de tous les enregistrements de la table associée au modèle Article.

2. Trouver un enregistrement par ID : find($id)

La méthode find($id) permet de récupérer un enregistrement spécifique en utilisant son ID.


use App\Models\Article;

$article = Article::find(1);
if ($article) {
    echo $article->title;
} else {
    echo "Aucun article trouvé.";
}
    

Explication : Si aucun enregistrement n'est trouvé avec l'ID spécifié, la méthode renvoie null.

3. Trouver un enregistrement ou renvoyer une erreur 404 : findOrFail($id)

La méthode findOrFail($id) fonctionne comme find($id), mais elle renvoie une erreur 404 si aucun enregistrement n'est trouvé.


use App\Models\Article;

try {
    $article = Article::findOrFail(1);
    echo $article->title;
} catch (\Illuminate\Database\Eloquent\ModelNotFoundException $e) {
    echo "Article non trouvé.";
}
    

Explication : Cette méthode est utile lorsque vous voulez afficher une page d'erreur si l'enregistrement n'existe pas.

4. Récupérer le premier enregistrement : first()

La méthode first() permet de récupérer le premier enregistrement correspondant à une requête.


use App\Models\Article;

$article = Article::where('status', 'published')->first();
if ($article) {
    echo $article->title;
} else {
    echo "Aucun article publié trouvé.";
}
    

Explication : Si aucun enregistrement ne correspond, la méthode renvoie null.

5. Récupérer le premier enregistrement ou renvoyer une erreur 404 : firstOrFail()

La méthode firstOrFail() fonctionne comme first(), mais elle renvoie une erreur 404 si aucun enregistrement n'est trouvé.


use App\Models\Article;

try {
    $article = Article::where('status', 'published')->firstOrFail();
    echo $article->title;
} catch (\Illuminate\Database\Eloquent\ModelNotFoundException $e) {
    echo "Aucun article publié trouvé.";
}
    

Explication : Cette méthode est utile lorsque vous voulez garantir qu'un enregistrement existe avant de continuer.

6. Filtrer par une colonne : where('column', 'value')

La méthode where() permet de filtrer les résultats en fonction d'une condition.


use App\Models\Article;

$articles = Article::where('status', 'published')->get();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode filtre les articles dont le statut est "published".

7. Filtrer entre deux valeurs : whereBetween('column', [$min, $max])

La méthode whereBetween() permet de filtrer les résultats compris entre deux valeurs.


use App\Models\Article;

$articles = Article::whereBetween('price', [50, 100])->get();
foreach ($articles as $article) {
    echo $article->title . " - " . $article->price;
}
    

Explication : Cette méthode filtre les articles dont le prix est compris entre 50 et 100.

8. Vérifier si une valeur est dans une liste : whereIn('column', [val1, val2])

La méthode whereIn() permet de vérifier si une colonne contient une valeur présente dans une liste.


use App\Models\Article;

$articles = Article::whereIn('category_id', [1, 2, 3])->get();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode filtre les articles dont la catégorie est 1, 2 ou 3.

9. Vérifier si une valeur n'est pas dans une liste : whereNotIn('column', [val1, val2])

La méthode whereNotIn() permet de vérifier si une colonne ne contient aucune des valeurs d'une liste.


use App\Models\Article;

$articles = Article::whereNotIn('category_id', [1, 2, 3])->get();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode filtre les articles dont la catégorie n'est ni 1, ni 2, ni 3.

10. Vérifier si une colonne est NULL : whereNull('column')

La méthode whereNull() permet de vérifier si une colonne est NULL.


use App\Models\Article;

$articles = Article::whereNull('published_at')->get();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode filtre les articles qui n'ont pas encore été publiés (colonne published_at est NULL).

11. Vérifier si une colonne n'est pas NULL : whereNotNull('column')

La méthode whereNotNull() permet de vérifier si une colonne n'est pas NULL.


use App\Models\Article;

$articles = Article::whereNotNull('published_at')->get();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode filtre les articles qui ont déjà été publiés (colonne published_at n'est pas NULL).

12. Trier les résultats : orderBy('column', 'desc')

La méthode orderBy() permet de trier les résultats par une colonne spécifique.


use App\Models\Article;

$articles = Article::orderBy('created_at', 'desc')->get();
foreach ($articles as $article) {
    echo $article->title;
}
    

Explication : Cette méthode trie les articles par date de création décroissante (du plus récent au plus ancien).

13. Grouper les résultats : groupBy('column')

La méthode groupBy() permet de regrouper les résultats par une colonne spécifique.


use App\Models\Article;

$articles = Article::select('category_id', \DB::raw('COUNT(*) as total'))
    ->groupBy('category_id')
    ->get();
foreach ($articles as $article) {
    echo "Catégorie ID: " . $article->category_id . ", Total: " . $article->total;
}
    

Explication : Cette méthode regroupe les articles par catégorie et compte le nombre d'articles dans chaque catégorie.

14. Sélectionner des valeurs distinctes : distinct()

La méthode distinct() permet de sélectionner des valeurs distinctes d'une colonne.


use App\Models\Article;

$categories = Article::distinct()->pluck('category_id');
foreach ($categories as $category) {
    echo $category;
}
    

Explication : Cette méthode renvoie une liste unique des IDs de catégorie sans doublons.

15. Sélectionner des colonnes spécifiques : select('column1', 'column2')

La méthode select() permet de sélectionner uniquement certaines colonnes.


use App\Models\Article;

$articles = Article::select('title', 'created_at')->get();
foreach ($articles as $article) {
    echo $article->title . " - " . $article->created_at;
}
    

Explication : Cette méthode récupère uniquement les colonnes title et created_at pour chaque article.

Tutoriel détaillé sur les fonctions Eloquent

Introduction

Dans ce tutoriel, nous allons explorer les fonctions Eloquent pour la création, la mise à jour, la suppression et les requêtes avancées. Chaque fonction sera expliquée avec des exemples concrets.

1. Création et mise à jour

1.1 Ajouter un enregistrement : create(['column' => 'value'])

La méthode create() permet d'ajouter un nouvel enregistrement dans la table associée au modèle.


use App\Models\Article;

$data = [
    'title' => 'Mon premier article',
    'content' => 'Ceci est le contenu de l\'article.',
];

$article = Article::create($data);
echo "Nouvel article créé avec l'ID : " . $article->id;
    

Explication : Cette méthode insère un nouvel enregistrement dans la base de données et renvoie une instance du modèle créé.

1.2 Mettre à jour un enregistrement : update(['column' => 'newValue'])

La méthode update() permet de mettre à jour un ou plusieurs enregistrements existants.


use App\Models\Article;

$article = Article::find(1);
if ($article) {
    $article->update(['title' => 'Nouveau titre']);
    echo "Article mis à jour.";
} else {
    echo "Article non trouvé.";
}
    

Explication : Cette méthode met à jour les colonnes spécifiées dans la table.

1.3 Sauvegarder un modèle après modification : save()

La méthode save() permet de sauvegarder les modifications apportées à un modèle existant.


use App\Models\Article;

$article = Article::find(1);
if ($article) {
    $article->title = 'Titre modifié';
    $article->save();
    echo "Article sauvegardé.";
} else {
    echo "Article non trouvé.";
}
    

Explication : Cette méthode sauvegarde les changements effectués sur un modèle directement dans la base de données.

1.4 Incrémenter une colonne : increment('column')

La méthode increment() permet d'incrémenter une colonne numérique.


use App\Models\Article;

$article = Article::find(1);
if ($article) {
    $article->increment('views');
    echo "Nombre de vues incrémenté.";
} else {
    echo "Article non trouvé.";
}
    

Explication : Cette méthode incrémente automatiquement la valeur d'une colonne (par exemple, le nombre de vues).

1.5 Décrémenter une colonne : decrement('column')

La méthode decrement() permet de décrémenter une colonne numérique.


use App\Models\Article;

$article = Article::find(1);
if ($article) {
    $article->decrement('stock');
    echo "Stock décrémenté.";
} else {
    echo "Article non trouvé.";
}
    

Explication : Cette méthode décrémente automatiquement la valeur d'une colonne (par exemple, le stock).

2. Suppression

2.1 Supprimer un enregistrement : delete()

La méthode delete() permet de supprimer un enregistrement spécifique.


use App\Models\Article;

$article = Article::find(1);
if ($article) {
    $article->delete();
    echo "Article supprimé.";
} else {
    echo "Article non trouvé.";
}
    

Explication : Cette méthode supprime l'enregistrement correspondant au modèle.

2.2 Supprimer un enregistrement par ID : destroy($id)

La méthode destroy() permet de supprimer un ou plusieurs enregistrements directement par leur ID.


use App\Models\Article;

Article::destroy(1); // Supprime l'article avec l'ID 1
Article::destroy([2, 3]); // Supprime les articles avec les IDs 2 et 3
    

Explication : Cette méthode supprime les enregistrements sans avoir besoin de récupérer le modèle au préalable.

2.3 Vider complètement une table : truncate()

La méthode truncate() permet de supprimer toutes les données d'une table.


use App\Models\Article;

Article::truncate();
echo "Tous les articles ont été supprimés.";
    

Explication : Cette méthode vide complètement la table associée au modèle.

3. Requêtes avancées

3.1 Compter les enregistrements : count()

La méthode count() permet de compter le nombre d'enregistrements correspondant à une requête.


use App\Models\Article;

$count = Article::where('status', 'published')->count();
echo "Nombre d'articles publiés : " . $count;
    

Explication : Cette méthode renvoie le nombre total d'enregistrements filtrés.

3.2 Calculer la somme d'une colonne : sum('column')

La méthode sum() permet de calculer la somme des valeurs d'une colonne.


use App\Models\Article;

$totalPrice = Article::sum('price');
echo "Prix total des articles : " . $totalPrice;
    

Explication : Cette méthode calcule la somme des valeurs d'une colonne numérique.

3.3 Calculer la moyenne d'une colonne : avg('column')

La méthode avg() permet de calculer la moyenne des valeurs d'une colonne.


use App\Models\Article;

$averagePrice = Article::avg('price');
echo "Prix moyen des articles : " . $averagePrice;
    

Explication : Cette méthode calcule la moyenne des valeurs d'une colonne numérique.

3.4 Trouver la plus petite valeur : min('column')

La méthode min() permet de trouver la plus petite valeur d'une colonne.


use App\Models\Article;

$lowestPrice = Article::min('price');
echo "Prix le plus bas : " . $lowestPrice;
    

Explication : Cette méthode renvoie la valeur minimale d'une colonne numérique.

3.5 Trouver la plus grande valeur : max('column')

La méthode max() permet de trouver la plus grande valeur d'une colonne.


use App\Models\Article;

$highestPrice = Article::max('price');
echo "Prix le plus élevé : " . $highestPrice;
    

Explication : Cette méthode renvoie la valeur maximale d'une colonne numérique.

3.6 Vérifier si des enregistrements existent : exists()

La méthode exists() permet de vérifier si des enregistrements existent pour une requête donnée.


use App\Models\Article;

if (Article::where('status', 'published')->exists()) {
    echo "Il y a des articles publiés.";
} else {
    echo "Aucun article publié trouvé.";
}
    

Explication : Cette méthode renvoie true si au moins un enregistrement correspond à la requête.

3.7 Vérifier si aucun enregistrement n'existe : doesntExist()

La méthode doesntExist() permet de vérifier si aucun enregistrement ne correspond à une requête donnée.


use App\Models\Article;

if (Article::where('status', 'draft')->doesntExist()) {
    echo "Aucun article en brouillon trouvé.";
} else {
    echo "Il y a des articles en brouillon.";
}
    

Explication : Cette méthode renvoie true si aucun enregistrement ne correspond à la requête.

Tutoriel détaillé sur Eloquent : DB::, Jointures et Fonctions d'agrégation

Introduction

Dans ce tutoriel, nous allons explorer l'utilisation de la classe DB:: pour exécuter des requêtes brutes, les jointures entre tables avec Eloquent, ainsi que les fonctions d'agrégation. Chaque concept sera expliqué avec des exemples concrets.

1. Utilisation de la classe DB::

La classe DB:: permet d'exécuter des requêtes SQL directement sans passer par les modèles Eloquent. Cela est utile pour des requêtes complexes ou personnalisées.

1.1 Exécuter une requête brute : DB::select()

La méthode DB::select() permet d'exécuter une requête SQL brute et de récupérer les résultats.


use Illuminate\Support\Facades\DB;

$results = DB::select('SELECT * FROM articles WHERE status = ?', ['published']);
foreach ($results as $article) {
    echo $article->title;
}
    

Explication : Cette méthode exécute une requête SQL brute et renvoie les résultats sous forme d'objets PHP.

1.2 Insérer des données : DB::insert()

La méthode DB::insert() permet d'insérer des données dans la base de données.


use Illuminate\Support\Facades\DB;

DB::insert('INSERT INTO articles (title, content) VALUES (?, ?)', ['Mon article', 'Ceci est le contenu']);
echo "Article inséré.";
    

Explication : Cette méthode exécute une requête SQL d'insertion.

1.3 Mettre à jour des données : DB::update()

La méthode DB::update() permet de mettre à jour des données existantes.


use Illuminate\Support\Facades\DB;

$affectedRows = DB::update('UPDATE articles SET title = ? WHERE id = ?', ['Nouveau titre', 1]);
echo "Nombre de lignes mises à jour : " . $affectedRows;
    

Explication : Cette méthode met à jour les enregistrements correspondants et renvoie le nombre de lignes affectées.

1.4 Supprimer des données : DB::delete()

La méthode DB::delete() permet de supprimer des enregistrements.


use Illuminate\Support\Facades\DB;

$deletedRows = DB::delete('DELETE FROM articles WHERE id = ?', [1]);
echo "Nombre de lignes supprimées : " . $deletedRows;
    

Explication : Cette méthode supprime les enregistrements correspondants et renvoie le nombre de lignes affectées.

2. Jointures avec Eloquent

Les jointures permettent de combiner des données provenant de plusieurs tables.

2.1 Jointure simple : join()

La méthode join() permet de faire une jointure entre deux tables.


use App\Models\Article;
use App\Models\Category;

$articles = Article::join('categories', 'articles.category_id', '=', 'categories.id')
    ->select('articles.title', 'categories.name as category_name')
    ->get();

foreach ($articles as $article) {
    echo "Titre : " . $article->title . ", Catégorie : " . $article->category_name;
}
    

Explication : Cette méthode combine les données des tables articles et categories en utilisant une clé étrangère.

2.2 Jointure avec condition : leftJoin()

La méthode leftJoin() permet de faire une jointure gauche (LEFT JOIN).


use App\Models\Article;
use App\Models\Category;

$articles = Article::leftJoin('categories', 'articles.category_id', '=', 'categories.id')
    ->select('articles.title', 'categories.name as category_name')
    ->get();

foreach ($articles as $article) {
    echo "Titre : " . $article->title . ", Catégorie : " . ($article->category_name ?? 'Aucune catégorie');
}
    

Explication : Cette méthode inclut tous les articles, même ceux qui n'ont pas de catégorie associée.

2.3 Jointure avec plusieurs conditions : join(...)->where()

Vous pouvez ajouter des conditions supplémentaires à une jointure.


use App\Models\Article;
use App\Models\Category;

$articles = Article::join('categories', function ($join) {
        $join->on('articles.category_id', '=', 'categories.id')
             ->where('categories.status', '=', 'active');
    })
    ->select('articles.title', 'categories.name as category_name')
    ->get();

foreach ($articles as $article) {
    echo "Titre : " . $article->title . ", Catégorie : " . $article->category_name;
}
    

Explication : Cette méthode ajoute une condition supplémentaire à la jointure.

3. Fonctions d'agrégation

Les fonctions d'agrégation permettent de calculer des valeurs globales sur un ensemble de données.

3.1 Compter les enregistrements : count()

La méthode count() permet de compter le nombre d'enregistrements.


use App\Models\Article;

$count = Article::count();
echo "Nombre total d'articles : " . $count;
    

Explication : Cette méthode renvoie le nombre total d'enregistrements dans la table.

3.2 Calculer la somme d'une colonne : sum()

La méthode sum() permet de calculer la somme des valeurs d'une colonne numérique.


use App\Models\Article;

$totalPrice = Article::sum('price');
echo "Prix total des articles : " . $totalPrice;
    

Explication : Cette méthode calcule la somme des valeurs d'une colonne spécifiée.

3.3 Calculer la moyenne d'une colonne : avg()

La méthode avg() permet de calculer la moyenne des valeurs d'une colonne numérique.


use App\Models\Article;

$averagePrice = Article::avg('price');
echo "Prix moyen des articles : " . $averagePrice;
    

Explication : Cette méthode calcule la moyenne des valeurs d'une colonne spécifiée.

3.4 Trouver la valeur minimale : min()

La méthode min() permet de trouver la plus petite valeur d'une colonne numérique.


use App\Models\Article;

$lowestPrice = Article::min('price');
echo "Prix le plus bas : " . $lowestPrice;
    

Explication : Cette méthode renvoie la valeur minimale d'une colonne spécifiée.

3.5 Trouver la valeur maximale : max()

La méthode max() permet de trouver la plus grande valeur d'une colonne numérique.


use App\Models\Article;

$highestPrice = Article::max('price');
echo "Prix le plus élevé : " . $highestPrice;
    

Explication : Cette méthode renvoie la valeur maximale d'une colonne spécifiée.

Tutoriel détaillé sur Eloquent : Relations et Fonctionnalités

Introduction

Dans ce tutoriel, nous allons explorer les relations Eloquent et leurs fonctionnalités en utilisant le schéma relationnel suivant :

  • Clients (idclient, nom, prenom)
  • Categories (idcategorie, nom, description)
  • Produits (idproduit, idcategorie, nom, prix, quantiteStock, marque)
  • Vente (idvente, idclient, idproduit, quantite, datevente)

Nous expliquerons chaque fonctionnalité avec des exemples concrets.

1. Définition des relations dans les modèles

1.1 Relation One-to-One : hasOne()

Exemple : Un client peut avoir une seule vente préférée.


namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Client extends Model
{
    public function ventePreferee()
    {
        return $this->hasOne(Vente::class, 'idclient', 'idclient');
    }
}
    

Explication : Cette méthode définit une relation où un client est associé à une seule vente via la clé étrangère idclient.

1.2 Relation One-to-Many : hasMany()

Exemple : Une catégorie peut avoir plusieurs produits.


namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Categorie extends Model
{
    public function produits()
    {
        return $this->hasMany(Produit::class, 'idcategorie', 'idcategorie');
    }
}
    

Explication : Cette méthode définit une relation où une catégorie est associée à plusieurs produits via la clé étrangère idcategorie.

1.3 Relation Belongs To : belongsTo()

Exemple : Un produit appartient à une catégorie.


namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Produit extends Model
{
    public function categorie()
    {
        return $this->belongsTo(Categorie::class, 'idcategorie', 'idcategorie');
    }
}
    

Explication : Cette méthode définit une relation où un produit est lié à une catégorie via la clé étrangère idcategorie.

1.4 Relation Many-to-Many : belongsToMany()

Exemple : Une vente peut inclure plusieurs produits, et un produit peut être inclus dans plusieurs ventes.


namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Vente extends Model
{
    public function produits()
    {
        return $this->belongsToMany(Produit::class, 'vente_produit', 'idvente', 'idproduit');
    }
}
    

Explication : Cette méthode définit une relation où une table pivot (vente_produit) relie les tables vente et produit.

2. Chargement des relations

2.1 Charger une relation : with('relationName')

Exemple : Charger les produits d'une catégorie.


use App\Models\Categorie;

$categorie = Categorie::with('produits')->find(1);
foreach ($categorie->produits as $produit) {
    echo $produit->nom;
}
    

Explication : La méthode with() charge la relation produits pour éviter les requêtes N+1.

2.2 Charger plusieurs relations : with(['relation1', 'relation2'])

Exemple : Charger les ventes et les produits d'un client.


use App\Models\Client;

$client = Client::with(['ventePreferee', 'ventePreferee.produits'])->find(1);
echo $client->ventePreferee->produits->first()->nom;
    

Explication : Cette méthode charge plusieurs relations en une seule requête.

2.3 Charger dynamiquement une relation : load('relationName')

Exemple : Charger les produits après avoir récupéré une catégorie.


use App\Models\Categorie;

$categorie = Categorie::find(1);
$categorie->load('produits');
foreach ($categorie->produits as $produit) {
    echo $produit->nom;
}
    

Explication : La méthode load() charge une relation après que le modèle a été récupéré.

2.4 Charger uniquement si elle n'est pas déjà chargée : loadMissing('relationName')

Exemple : Charger les produits uniquement s'ils ne sont pas déjà chargés.


use App\Models\Categorie;

$categorie = Categorie::find(1);
$categorie->loadMissing('produits');
foreach ($categorie->produits as $produit) {
    echo $produit->nom;
}
    

Explication : Cette méthode charge une relation uniquement si elle n'a pas encore été chargée.

2.5 Compter les éléments d’une relation : withCount('relationName')

Exemple : Compter le nombre de produits par catégorie.


use App\Models\Categorie;

$categories = Categorie::withCount('produits')->get();
foreach ($categories as $categorie) {
    echo "Catégorie : " . $categorie->nom . ", Nombre de produits : " . $categorie->produits_count;
}
    

Explication : Cette méthode ajoute une colonne produits_count contenant le nombre de produits associés.

2.6 Calculer la somme d'une colonne sur une relation : withSum('relationName', 'column')

Exemple : Calculer la somme des prix des produits d'une catégorie.


use App\Models\Categorie;

$categories = Categorie::withSum('produits', 'prix')->get();
foreach ($categories as $categorie) {
    echo "Catégorie : " . $categorie->nom . ", Somme des prix : " . $categorie->produits_sum_prix;
}
    

Explication : Cette méthode ajoute une colonne produits_sum_prix contenant la somme des prix.

3. Filtrage sur les relations

3.1 Sélectionner uniquement les enregistrements ayant une relation : has('relationName')

Exemple : Sélectionner les catégories ayant au moins un produit.


use App\Models\Categorie;

$categories = Categorie::has('produits')->get();
foreach ($categories as $categorie) {
    echo $categorie->nom;
}
    

Explication : Cette méthode filtre les catégories qui ont au moins un produit associé.

3.2 Filtrer sur une relation : whereHas('relationName', function ($query) {...})

Exemple : Sélectionner les catégories ayant des produits dont le prix est supérieur à 100.


use App\Models\Categorie;

$categories = Categorie::whereHas('produits', function ($query) {
    $query->where('prix', '>', 100);
})->get();

foreach ($categories as $categorie) {
    echo $categorie->nom;
}
    

Explication : Cette méthode filtre les catégories en fonction des conditions spécifiées sur les produits.

3.3 Ajouter une condition "OU" sur une relation : orWhereHas('relationName', function ($query) {...})

Exemple : Sélectionner les catégories ayant des produits dont le prix est supérieur à 100 ou la marque est "X".


use App\Models\Categorie;

$categories = Categorie::whereHas('produits', function ($query) {
    $query->where('prix', '>', 100);
})->orWhereHas('produits', function ($query) {
    $query->where('marque', 'X');
})->get();

foreach ($categories as $categorie) {
    echo $categorie->nom;
}
    

Explication : Cette méthode ajoute une condition "OU" sur les relations filtrées.

3.4 Sélectionner les enregistrements qui n'ont pas la relation : doesntHave('relationName')

Exemple : Sélectionner les catégories sans produits.


use App\Models\Categorie;

$categories = Categorie::doesntHave('produits')->get();
foreach ($categories as $categorie) {
    echo $categorie->nom;
}
    

Explication : Cette méthode filtre les catégories qui n'ont aucun produit associé.

3.5 Ajouter des conditions aux relations absentes : whereDoesntHave('relationName', function ($query) {...})

Exemple : Sélectionner les catégories sans produits dont le prix est supérieur à 100.


use App\Models\Categorie;

$categories = Categorie::whereDoesntHave('produits', function ($query) {
    $query->where('prix', '>', 100);
})->get();

foreach ($categories as $categorie) {
    echo $categorie->nom;
}
    

Explication : Cette méthode filtre les catégories qui n'ont pas de produits répondant aux conditions spécifiées.





1. Migration pour la Table clients
php artisan make:migration create_clients_table --create=clients
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_clients_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateClientsTable extends Migration
{
    public function up()
    {
        Schema::create('clients', function (Blueprint $table) {
            $table->id('idClient');
            $table->string('nom');
            $table->string('prenom');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('clients');
    }
}
2. Migration pour la Table categories
php artisan make:migration create_categories_table --create=categories
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_categories_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateCategoriesTable extends Migration
{
    public function up()
    {
        Schema::create('categories', function (Blueprint $table) {
            $table->id('idCategorie');
            $table->string('nom');
            $table->text('description')->nullable();
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('categories');
    }
}
3. Migration pour la Table produits
php artisan make:migration create_produits_table --create=produits
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_produits_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateProduitsTable extends Migration
{
    public function up()
    {
        Schema::create('produits', function (Blueprint $table) {
            $table->id('idProduit');
            $table->unsignedBigInteger('idCategorie');
            $table->string('nom');
            $table->decimal('prix', 8, 2);
            $table->integer('quantiteStock');
            $table->string('marque');
            $table->foreign('idCategorie')->references('idCategorie')->on('categories')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('produits');
    }
}
4. Migration pour la Table ventes
php artisan make:migration create_ventes_table --create=ventes
Modifier le fichier généré (database/migrations/xxxx_xx_xx_xxxxxx_create_ventes_table.php):
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateVentesTable extends Migration
{
    public function up()
    {
        Schema::create('ventes', function (Blueprint $table) {
            $table->id('idVente');
            $table->unsignedBigInteger('idClient');
            $table->unsignedBigInteger('idProduit');
            $table->integer('quantite');
            $table->dateTime('dateVente');
            $table->foreign('idClient')->references('idClient')->on('clients')->onDelete('cascade');
            $table->foreign('idProduit')->references('idProduit')->on('produits')->onDelete('cascade');
            $table->timestamps();
        });
    }

    public function down()
    {
        Schema::dropIfExists('ventes');
    }
}
Étape 2: Exécution des Migrations
php artisan migrate
Étape 3: Création des Modèles
1. Modèle Client
php artisan make:model Client
Modifier le fichier généré (app/Models/Client.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Client extends Model
{
    use HasFactory;

    protected $table = 'clients';
    protected $primaryKey = 'idClient';
    protected $fillable = ['nom', 'prenom'];

    public function ventes()
    {
        return $this->hasMany(Vente::class, 'idClient');
    }
}
2. Modèle Categorie
php artisan make:model Categorie
Modifier le fichier généré (app/Models/Categorie.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Categorie extends Model
{
    use HasFactory;

    protected $table = 'categories';
    protected $primaryKey = 'idCategorie';
    protected $fillable = ['nom', 'description'];

    public function produits()
    {
        return $this->hasMany(Produit::class, 'idCategorie');
    }
}
3. Modèle Produit
php artisan make:model Produit
Modifier le fichier généré (app/Models/Produit.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Produit extends Model
{
    use HasFactory;

    protected $table = 'produits';
    protected $primaryKey = 'idProduit';
    protected $fillable = ['idCategorie', 'nom', 'prix', 'quantiteStock', 'marque'];

    public function categorie()
    {
        return $this->belongsTo(Categorie::class, 'idCategorie');
    }

    public function ventes()
    {
        return $this->hasMany(Vente::class, 'idProduit');
    }
}
4. Modèle Vente
php artisan make:model Vente
Modifier le fichier généré (app/Models/Vente.php):
namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Vente extends Model
{
    use HasFactory;

    protected $table = 'ventes';
    protected $primaryKey = 'idVente';
    protected $fillable = ['idClient', 'idProduit', 'quantite', 'dateVente'];

    public function client()
    {
        return $this->belongsTo(Client::class, 'idClient');
    }

    public function produit()
    {
        return $this->belongsTo(Produit::class, 'idProduit');
    }
}
Étape 4: Création des Contrôleurs 1. Contrôleur ClientController
php artisan make:controller ClientController
Modifier le fichier généré (app/Http/Controllers/ClientController.php):
namespace App\Http\Controllers;

use App\Models\Client;
use App\Models\Vente;
use Illuminate\Http\Request;

class ClientController extends Controller
{
    // 1. Récupérer tous les clients
    public function getAllClients()
    {
        return Client::all();
    }

    // 2. Récupérer un client par ID
    public function getClientById($idClient)
    {
        return Client::find($idClient);
    }

    // 3. Ajouter un nouveau client
    public function addClient(Request $request)
    {
        $validatedData = $request->validate([
            'nom' => 'required|string|max:255',
            'prenom' => 'required|string|max:255',
        ]);

        return Client::create($validatedData);
    }

    // 4. Mettre à jour un client
    public function updateClient(Request $request, $idClient)
    {
        $validatedData = $request->validate([
            'nom' => 'required|string|max:255',
            'prenom' => 'required|string|max:255',
        ]);

        $client = Client::find($idClient);
        if ($client) {
            $client->update($validatedData);
            return $client;
        }

        return response()->json(['message' => 'Client not found'], 404);
    }

    // 5. Supprimer un client
    public function deleteClient($idClient)
    {
        $client = Client::find($idClient);
        if ($client) {
            $client->delete();
            return response()->json(['message' => 'Client deleted successfully']);
        }

        return response()->json(['message' => 'Client not found'], 404);
    }

    // 6. Récupérer toutes les ventes d'un client
    public function getClientVentes($idClient)
    {
        return Client::find($idClient)->ventes;
    }

    // 7. Calculer le total des ventes pour un client
    public function getTotalVentesClient($idClient)
    {
        $total = Vente::where('idClient', $idClient)->sum('quantite');
        return response()->json(['total_ventes' => $total]);
    }

    // 8. Filtrer les clients par nom
    public function filterClientsByNom($nom)
    {
        return Client::where('nom', 'like', '%' . $nom . '%')->get();
    }

    // 9. Filtrer les clients par prénom
    public function filterClientsByPrenom($prenom)
    {
        return Client::where('prenom', 'like', '%' . $prenom . '%')->get();
    }

    // 10. Filtrer les clients par nom et prénom
    public function filterClientsByNomEtPrenom($nom, $prenom)
    {
        return Client::where('nom', 'like', '%' . $nom . '%')
                    ->where('prenom', 'like', '%' . $prenom . '%')
                    ->get();
    }

    // 11. Récupérer les clients ayant effectué au moins une vente
    public function getClientsWithVentes()
    {
        return Client::has('ventes')->get();
    }

    // 12. Récupérer les clients sans ventes
    public function getClientsWithoutVentes()
    {
        return Client::doesntHave('ventes')->get();
    }

    // 13. Récupérer les clients ayant effectué plus de X ventes
    public function getClientsWithMoreThanXVentes($x)
    {
        return Client::has('ventes', '>=', $x)->get();
    }

    // 14. Récupérer les clients ayant effectué moins de X ventes
    public function getClientsWithLessThanXVentes($x)
    {
        return Client::has('ventes', '<=', $x)->get();
    }

    // 15. Récupérer les clients ayant effectué des ventes dans une période donnée
    public function getClientsWithVentesInPeriod($startDate, $endDate)
    {
        return Client::whereHas('ventes', function ($query) use ($startDate, $endDate) {
            $query->whereBetween('dateVente', [$startDate, $endDate]);
        })->get();
    }
}
2. Contrôleur CategorieController
php artisan make:controller CategorieController
Modifier le fichier généré (app/Http/Controllers/CategorieController.php):
namespace App\Http\Controllers;
use App\Models\Categorie;
use App\Models\Produit;
use Illuminate\Http\Request;

class CategorieController extends Controller
{
// 1. Récupérer toutes les catégories
public function getAllCategories()
{
return Categorie::all();
}

// 2. Récupérer une catégorie par ID
public function getCategorieById($idCategorie)
{
return Categorie::find($idCategorie);
}

// 3. Ajouter une nouvelle catégorie
public function addCategorie(Request $request)
{
$validatedData = $request->validate([
'nom' => 'required|string|max:255',
'description' => 'nullable|string',
]);

return Categorie::create($validatedData);
}

// 4. Mettre à jour une catégorie
public function updateCategorie(Request $request, $idCategorie)
{
$validatedData = $request->validate([
'nom' => 'required|string|max:255',
'description' => 'nullable|string',
]);

$categorie = Categorie::find($idCategorie);
if ($categorie) {
$categorie->update($validatedData);
return $categorie;
}

return response()->json(['message' => 'Catégorie not found'], 404);
}

// 5. Supprimer une catégorie
public function deleteCategorie($idCategorie)
{
$categorie = Categorie::find($idCategorie);
if ($categorie) {
$categorie->delete();
return response()->json(['message' => 'Catégorie deleted successfully']);
}

return response()->json(['message' => 'Catégorie not found'], 404);
}

// 6. Récupérer tous les produits d'une catégorie
public function getCategorieProduits($idCategorie)
{
return Categorie::find($idCategorie)->produits;
}

// 7. Calculer le nombre total de produits dans une catégorie
public function getTotalProduitsCategorie($idCategorie)
{
$total = Produit::where('idCategorie', $idCategorie)->count();
return response()->json(['total_produits' => $total]);
}

// 8. Filtrer les catégories par nom
public function filterCategoriesByNom($nom)
{
return Categorie::where('nom', 'like', '%' . $nom . '%')->get();
}

// 9. Filtrer les catégories par description
public function filterCategoriesByDescription($description)
{
return Categorie::where('description', 'like', '%' . $description . '%')->get();
}

// 10. Filtrer les catégories par nom et description
public function filterCategoriesByNomEtDescription($nom, $description)
{
return Categorie::where('nom', 'like', '%' . $nom . '%')
->where('description', 'like', '%' . $description . '%')
->get();
}

// 11. Récupérer les catégories ayant au moins un produit
public function getCategoriesWithProduits()
{
return Categorie::has('produits')->get();
}

// 12. Récupérer les catégories sans produits
public function getCategoriesWithoutProduits()
{
return Categorie::doesntHave('produits')->get();
}

// 13. Récupérer les catégories ayant plus de X produits
public function getCategoriesWithMoreThanXProduits($x)
{
return Categorie::has('produits', '>=', $x)->get();
}

// 14. Récupérer les catégories ayant moins de X produits
public function getCategoriesWithLessThanXProduits($x)
{
return Categorie::has('produits', '<=', $x)->get();
}

// 15. Récupérer les catégories dont les produits sont en stock
public function getCategoriesWithProduitsEnStock()
{
return Categorie::whereHas('produits', function ($query) {
$query->where('quantiteStock', '>', 0);
})->get();
}
}
3. Contrôleur ProduitController
php artisan make:controller ProduitController
Modifier le fichier généré (app/Http/Controllers/ProduitController.php):
namespace App\Http\Controllers;

use App\Models\Categorie;
use App\Models\Produit;
use App\Models\Vente;
use Illuminate\Http\Request;

class ProduitController extends Controller
{
// 1. Récupérer tous les produits
public function getAllProduits()
{
return Produit::all();
}

// 2. Récupérer un produit par ID
public function getProduitById($idProduit)
{
return Produit::find($idProduit);
}

// 3. Ajouter un nouveau produit
public function addProduit(Request $request)
{
$validatedData = $request->validate([
'idCategorie' => 'required|exists:categories,idCategorie',
'nom' => 'required|string|max:255',
'prix' => 'required|numeric|min:0',
'quantiteStock' => 'required|integer|min:0',
'marque' => 'required|string|max:255',
]);

return Produit::create($validatedData);
}

// 4. Mettre à jour un produit
public function updateProduit(Request $request, $idProduit)
{
$validatedData = $request->validate([
'idCategorie' => 'required|exists:categories,idCategorie',
'nom' => 'required|string|max:255',
'prix' => 'required|numeric|min:0',
'quantiteStock' => 'required|integer|min:0',
'marque' => 'required|string|max:255',
]);

$produit = Produit::find($idProduit);
if ($produit) {
$produit->update($validatedData);
return $produit;
}

return response()->json(['message' => 'Produit not found'], 404);
}

// 5. Supprimer un produit
public function deleteProduit($idProduit)
{
$produit = Produit::find($idProduit);
if ($produit) {
$produit->delete();
return response()->json(['message' => 'Produit deleted successfully']);
}

return response()->json(['message' => 'Produit not found'], 404);
}

// 6. Récupérer la catégorie d'un produit
public function getProduitCategorie($idProduit)
{
return Produit::find($idProduit)->categorie;
}

// 7. Récupérer toutes les ventes d'un produit
public function getProduitVentes($idProduit)
{
return Produit::find($idProduit)->ventes;
}

// 8. Calculer le total des ventes pour un produit
public function getTotalVentesProduit($idProduit)
{
$total = Vente::where('idProduit', $idProduit)->sum('quantite');
return response()->json(['total_ventes' => $total]);
}

// 9. Filtrer les produits par nom
public function filterProduitsByNom($nom)
{
return Produit::where('nom', 'like', '%' . $nom . '%')->get();
}

// 10. Filtrer les produits par marque
public function filterProduitsByMarque($marque)
{
return Produit::where('marque', 'like', '%' . $marque . '%')->get();
}

// 11. Filtrer les produits par prix minimum
public function filterProduitsByPrixMin($prixMin)
{
return Produit::where('prix', '>=', $prixMin)->get();
}

// 12. Filtrer les produits par prix maximum
public function filterProduitsByPrixMax($prixMax)
{
return Produit::where('prix', '<=', $prixMax)->get();
}

// 13. Filtrer les produits par quantité en stock
public function filterProduitsByQuantiteStock($quantiteStock)
{
return Produit::where('quantiteStock', '>=', $quantiteStock)->get();
}

// 14. Filtrer les produits par catégorie
public function filterProduitsByCategorie($idCategorie)
{
return Produit::where('idCategorie', $idCategorie)->get();
}

// 15. Récupérer les produits en stock
public function getProduitsEnStock()
{
return Produit::where('quantiteStock', '>', 0)->get();
}
}
4. Contrôleur VenteController
php artisan make:controller VenteController
Modifier le fichier généré (app/Http/Controllers/VenteController.php):
namespace App\Http\Controllers;

use App\Models\Client;
use App\Models\Produit;
use App\Models\Vente;
use Illuminate\Http\Request;

class VenteController extends Controller
{
// 1. Récupérer toutes les ventes
public function getAllVentes()
{
return Vente::all();
}

// 2. Récupérer une vente par ID
public function getVenteById($idVente)
{
return Vente::find($idVente);
}

// 3. Ajouter une nouvelle vente
public function addVente(Request $request)
{
$validatedData = $request->validate([
'idClient' => 'required|exists:clients,idClient',
'idProduit' => 'required|exists:produits,idProduit',
'quantite' => 'required|integer|min:1',
'dateVente' => 'required|date',
]);

// Vérifier si la quantité en stock est suffisante
$produit = Produit::find($validatedData['idProduit']);
if ($produit->quantiteStock < $validatedData['quantite']) {
return response()->json(['message' => 'Quantité en stock insuffisante'], 400);
}

// Mettre à jour la quantité en stock
$produit->quantiteStock -= $validatedData['quantite'];
$produit->save();

return Vente::create($validatedData);
}

// 4. Mettre à jour une vente
public function updateVente(Request $request, $idVente)
{
$validatedData = $request->validate([
'idClient' => 'required|exists:clients,idClient',
'idProduit' => 'required|exists:produits,idProduit',
'quantite' => 'required|integer|min:1',
'dateVente' => 'required|date',
]);

$vente = Vente::find($idVente);
if ($vente) {
// Vérifier si la quantité en stock est suffisante
$produit = Produit::find($validatedData['idProduit']);
if ($produit->quantiteStock < $validatedData['quantite']) {
return response()->json(['message' => 'Quantité en stock insuffisante'], 400);
}

// Restaurer la quantité en stock précédente
$produit->quantiteStock += $vente->quantite;
$produit->save();

// Mettre à jour la quantité en stock actuelle
$produit->quantiteStock -= $validatedData['quantite'];
$produit->save();

$vente->update($validatedData);
return $vente;
}

return response()->json(['message' => 'Vente not found'], 404);
}

// 5. Supprimer une vente
public function deleteVente($idVente)
{
$vente = Vente::find($idVente);
if ($vente) {
// Restaurer la quantité en stock
$produit = Produit::find($vente->idProduit);
$produit->quantiteStock += $vente->quantite;
$produit->save();

$vente->delete();
return response()->json(['message' => 'Vente deleted successfully']);
}

return response()->json(['message' => 'Vente not found'], 404);
}

// 6. Récupérer le client d'une vente
public function getVenteClient($idVente)
{
return Vente::find($idVente)->client;
}

// 7. Récupérer le produit d'une vente
public function getVenteProduit($idVente)
{
return Vente::find($idVente)->produit;
}

// 8. Calculer le montant total d'une vente
public function getMontantTotalVente($idVente)
{
$vente = Vente::find($idVente);
if ($vente) {
$montantTotal = $vente->quantite * $vente->produit->prix;
return response()->json(['montant_total' => $montantTotal]);
}

return response()->json(['message' => 'Vente not found'], 404);
}

// 9. Filtrer les ventes par date
public function filterVentesByDate($dateVente)
{
return Vente::whereDate('dateVente', $dateVente)->get();
}

// 10. Filtrer les ventes par date entre deux dates
public function filterVentesByDateRange($startDate, $endDate)
{
return Vente::whereBetween('dateVente', [$startDate, $endDate])->get();
}

// 11. Filtrer les ventes par client
public function filterVentesByClient($idClient)
{
return Vente::where('idClient', $idClient)->get();
}

// 12. Filtrer les ventes par produit
public function filterVentesByProduit($idProduit)
{
return Vente::where('idProduit', $idProduit)->get();
}

// 13. Calculer le total des ventes pour une date donnée
public function getTotalVentesByDate($dateVente)
{
$total = Vente::whereDate('dateVente', $dateVente)->sum('quantite');
return response()->json(['total_ventes' => $total]);
}

// 14. Calculer le total des ventes pour une période donnée
public function getTotalVentesByDateRange($startDate, $endDate)
{
$total = Vente::whereBetween('dateVente', [$startDate, $endDate])->sum('quantite');
return response()->json(['total_ventes' => $total]);
}

// 15. Calculer le montant total des ventes pour une période donnée
public function getMontantTotalVentesByDateRange($startDate, $endDate)
{
$ventes = Vente::whereBetween('dateVente', [$startDate, $endDate])->get();
$montantTotal = $ventes->reduce(function ($carry, $vente) {
return $carry + ($vente->quantite * $vente->produit->prix);
}, 0);

return response()->json(['montant_total' => $montantTotal]);
}
}
Étape 5: Routes Ajoutez les routes pour chaque contrôleur dans le fichier routes/api.php.

use App\Http\Controllers\ClientController;
use App\Http\Controllers\CategorieController;
use App\Http\Controllers\ProduitController;
use App\Http\Controllers\VenteController;
use Illuminate\Support\Facades\Route;

// Routes pour Clients
Route::get('/clients', [ClientController::class, 'getAllClients']);
Route::get('/clients/{idClient}', [ClientController::class, 'getClientById']);
Route::post('/clients', [ClientController::class, 'addClient']);
Route::put('/clients/{idClient}', [ClientController::class, 'updateClient']);
Route::delete('/clients/{idClient}', [ClientController::class, 'deleteClient']);
Route::get('/clients/{idClient}/ventes', [ClientController::class, 'getClientVentes']);
Route::get('/clients/{idClient}/total-ventes', [ClientController::class, 'getTotalVentesClient']);
Route::get('/clients/filter/nom/{nom}', [ClientController::class, 'filterClientsByNom']);
Route::get('/clients/filter/prenom/{prenom}', [ClientController::class, 'filterClientsByPrenom']);
Route::get('/clients/filter/nom/{nom}/prenom/{prenom}', [ClientController::class, 'filterClientsByNomEtPrenom']);
Route::get('/clients/with-ventes', [ClientController::class, 'getClientsWithVentes']);
Route::get('/clients/without-ventes', [ClientController::class, 'getClientsWithoutVentes']);
Route::get('/clients/with-more-than-x-ventes/{x}', [ClientController::class, 'getClientsWithMoreThanXVentes']);
Route::get('/clients/with-less-than-x-ventes/{x}', [ClientController::class, 'getClientsWithLessThanXVentes']);
Route::get('/clients/with-ventes-in-period/{startDate}/{endDate}', [ClientController::class, 'getClientsWithVentesInPeriod']);

// Routes pour Catégories
Route::get('/categories', [CategorieController::class, 'getAllCategories']);
Route::get('/categories/{idCategorie}', [CategorieController::class, 'getCategorieById']);
Route::post('/categories', [CategorieController::class, 'addCategorie']);
Route::put('/categories/{idCategorie}', [CategorieController::class, 'updateCategorie']);
Route::delete('/categories/{idCategorie}', [CategorieController::class, 'deleteCategorie']);
Route::get('/categories/{idCategorie}/produits', [CategorieController::class, 'getCategorieProduits']);
Route::get('/categories/{idCategorie}/total-produits', [CategorieController::class, 'getTotalProduitsCategorie']);
Route::get('/categories/filter/nom/{nom}', [CategorieController::class, 'filterCategoriesByNom']);
Route::get('/categories/filter/description/{description}', [CategorieController::class, 'filterCategoriesByDescription']);
Route::get('/categories/filter/nom/{nom}/description/{description}', [CategorieController::class, 'filterCategoriesByNomEtDescription']);
Route::get('/categories/with-produits', [CategorieController::class, 'getCategoriesWithProduits']);
Route::get('/categories/without-produits', [CategorieController::class, 'getCategoriesWithoutProduits']);
Route::get('/categories/with-more-than-x-produits/{x}', [CategorieController::class, 'getCategoriesWithMoreThanXProduits']);
Route::get('/categories/with-less-than-x-produits/{x}', [CategorieController::class, 'getCategoriesWithLessThanXProduits']);
Route::get('/categories/with-produits-en-stock', [CategorieController::class, 'getCategoriesWithProduitsEnStock']);

// Routes pour Produits
Route::get('/produits', [ProduitController::class, 'getAllProduits']);
Route::get('/produits/{idProduit}', [ProduitController::class, 'getProduitById']);
Route::post('/produits', [ProduitController::class, 'addProduit']);
Route::put('/produits/{idProduit}', [ProduitController::class, 'updateProduit']);
Route::delete('/produits/{idProduit}', [ProduitController::class, 'deleteProduit']);
Route::get('/produits/{idProduit}/categorie', [ProduitController::class, 'getProduitCategorie']);
Route::get('/produits/{idProduit}/ventes', [ProduitController::class, 'getProduitVentes']);
Route::get('/produits/{idProduit}/total-ventes', [ProduitController::class, 'getTotalVentesProduit']);
Route::get('/produits/filter/nom/{nom}', [ProduitController::class, 'filterProduitsByNom']);
Route::get('/produits/filter/marque/{marque}', [ProduitController::class, 'filterProduitsByMarque']);
Route::get('/produits/filter/prix-min/{prixMin}', [ProduitController::class, 'filterProduitsByPrixMin']);
Route::get('/produits/filter/prix-max/{prixMax}', [ProduitController::class, 'filterProduitsByPrixMax']);
Route::get('/produits/filter/quantite-stock/{quantiteStock}', [ProduitController::class, 'filterProduitsByQuantiteStock']);
Route::get('/produits/filter/categorie/{idCategorie}', [ProduitController::class, 'filterProduitsByCategorie']);
Route::get('/produits/en-stock', [ProduitController::class, 'getProduitsEnStock']);

// Routes pour Ventes
Route::get('/ventes', [VenteController::class, 'getAllVentes']);
Route::get('/ventes/{idVente}', [VenteController::class, 'getVenteById']);
Route::post('/ventes', [VenteController::class, 'addVente']);
Route::put('/ventes/{idVente}', [VenteController::class, 'updateVente']);
Route::delete('/ventes/{idVente}', [VenteController::class, 'deleteVente']);
Route::get('/ventes/{idVente}/client', [VenteController::class, 'getVenteClient']);
Route::get('/ventes/{idVente}/produit', [VenteController::class, 'getVenteProduit']);
Route::get('/ventes/{idVente}/montant-total', [VenteController::class, 'getMontantTotalVente']);
Route::get('/ventes/filter/date/{dateVente}', [VenteController::class, 'filterVentesByDate']);
Route::get('/ventes/filter/date-range/{startDate}/{endDate}', [VenteController::class, 'filterVentesByDateRange']);
Route::get('/ventes/filter/client/{idClient}', [VenteController::class, 'filterVentesByClient']);
Route::get('/ventes/filter/produit/{idProduit}', [VenteController::class, 'filterVentesByProduit']);
Route::get('/ventes/total-ventes/date/{dateVente}', [VenteController::class, 'getTotalVentesByDate']);
Route::get('/ventes/total-ventes/date-range/{startDate}/{endDate}', [VenteController::class, 'getTotalVentesByDateRange']);
Route::get('/ventes/montant-total/date-range/{startDate}/{endDate}', [VenteController::class, 'getMontantTotalVentesByDateRange']);

Utilisation des Factories et Seeders avec les Modèles Categorie et Produit

Dans ce tutoriel, nous allons explorer comment utiliser les factories et les seeders dans Laravel pour générer et insérer des données de test dans la base de données. Nous utiliserons les modèles Categorie et Produit que nous avons créés précédemment.


1. Introduction aux Factories et Seeders

Qu'est-ce qu'une Factory ?

  • Une factory est une classe qui permet de générer des données fictives pour un modèle donné.
  • Elle est utile pour créer rapidement des instances d'un modèle avec des valeurs aléatoires ou prédéfinies.

Qu'est-ce qu'un Seeder ?

  • Un seeder est une classe utilisée pour remplir la base de données avec des données initiales (par exemple, des données de test ou des données par défaut).
  • Les seeders peuvent utiliser des factories pour générer des données.

2. Étape 1 : Créer les Factories

Créer une Factory pour le Modèle Categorie

Exécutez la commande suivante pour générer une factory pour le modèle Categorie :

php artisan make:factory CategorieFactory --model=Categorie

Cela générera un fichier CategorieFactory.php dans le dossier database/factories. Ouvrez ce fichier et définissez les attributs par défaut pour une catégorie :

namespace Database\Factories;

use App\Models\Categorie;
use Illuminate\Database\Eloquent\Factories\Factory;

class CategorieFactory extends Factory
{
protected $model = Categorie::class;

public function definition()
{
return [
'nom' => $this->faker->word, // Génère un mot aléatoire
'description' => $this->faker->sentence, // Génère une phrase aléatoire
];
}
}

Créer une Factory pour le Modèle Produit

Exécutez la commande suivante pour générer une factory pour le modèle Produit :

php artisan make:factory ProduitFactory --model=Produit

Cela générera un fichier ProduitFactory.php dans le dossier database/factories. Ouvrez ce fichier et définissez les attributs par défaut pour un produit :

namespace Database\Factories;

use App\Models\Produit;
use App\Models\Categorie;
use Illuminate\Database\Eloquent\Factories\Factory;

class ProduitFactory extends Factory
{
protected $model = Produit::class;

public function definition()
{
return [
'nom' => $this->faker->word, // Génère un mot aléatoire
'prix' => $this->faker->randomFloat(2, 10, 1000), // Génère un prix aléatoire entre 10 et 1000
'categorie_id' => Categorie::factory(), // Crée automatiquement une catégorie associée
];
}
}

3. Étape 2 : Créer les Seeders

Créer un Seeder pour les Catégories

Exécutez la commande suivante pour générer un seeder pour les catégories :

php artisan make:seeder CategorieSeeder

Cela générera un fichier CategorieSeeder.php dans le dossier database/seeders. Ouvrez ce fichier et utilisez la factory pour créer des catégories :

namespace Database\Seeders;

use App\Models\Categorie;
use Illuminate\Database\Seeder;

class CategorieSeeder extends Seeder
{
public function run()
{
// Créer 5 catégories en utilisant la factory
Categorie::factory()->count(5)->create();
}
}

Créer un Seeder pour les Produits

Exécutez la commande suivante pour générer un seeder pour les produits :

php artisan make:seeder ProduitSeeder

Cela générera un fichier ProduitSeeder.php dans le dossier database/seeders. Ouvrez ce fichier et utilisez la factory pour créer des produits :

namespace Database\Seeders;

use App\Models\Produit;
use Illuminate\Database\Seeder;

class ProduitSeeder extends Seeder
{
public function run()
{
// Créer 20 produits en utilisant la factory
Produit::factory()->count(20)->create();
}
}

4. Étape 3 : Intégrer les Seeders dans DatabaseSeeder

Le fichier DatabaseSeeder.php est le point d'entrée principal pour exécuter tous les seeders. Ouvrez ce fichier (database/seeders/DatabaseSeeder.php) et appelez les seeders que vous avez créés :

namespace Database\Seeders;

use Illuminate\Database\Seeder;

class DatabaseSeeder extends Seeder
{
public function run()
{
// Exécuter le seeder pour les catégories
$this->call(CategorieSeeder::class);

// Exécuter le seeder pour les produits
$this->call(ProduitSeeder::class);
}
}

5. Étape 4 : Exécuter les Migrations et les Seeders

Étape 1 : Vider et Remplir la Base de Données

Pour vider et remplir la base de données avec les nouvelles données, exécutez la commande suivante :

php artisan migrate:fresh --seed

Cette commande :

  1. Supprime toutes les tables existantes.
  2. Réexécute les migrations pour recréer les tables.
  3. Exécute les seeders pour remplir la base de données avec des données de test.

6. Étape 5 : Tester les Données

Vérifier les Données dans la Base de Données

Vous pouvez vérifier que les données ont été correctement insérées en utilisant Tinker, un outil interactif fourni par Laravel :

php artisan tinker

Dans Tinker, exécutez les commandes suivantes pour afficher les catégories et les produits :

// Afficher toutes les catégories
\App\Models\Categorie::all();

// Afficher tous les produits
\App\Models\Produit::with('categorie')->get();

7. Étape 6 : Personnaliser les Factories et Seeders

Personnaliser la Factory ProduitFactory

Si vous souhaitez personnaliser les données générées par la factory, vous pouvez ajouter des méthodes statiques dans la factory. Par exemple, pour créer des produits "en promotion" :

public function enPromotion()
{
return $this->state(function (array $attributes) {
return [
'prix' => $this->faker->randomFloat(2, 1, 50), // Prix réduit
];
});
}

Ensuite, vous pouvez utiliser cette méthode dans un seeder :

Produit::factory()->count(5)->enPromotion()->create();

8. Conclusion

Vous avez maintenant une compréhension approfondie de l'utilisation des factories et des seeders dans Laravel. Voici un résumé des étapes que nous avons suivies :

  1. Création de factories pour les modèles Categorie et Produit.
  2. Création de seeders pour insérer des données dans la base de données.
  3. Intégration des seeders dans DatabaseSeeder.
  4. Exécution des migrations et des seeders pour remplir la base de données.
  5. Personnalisation des factories pour générer des données spécifiques.

Avec ces outils, vous pouvez facilement générer des données de test pour développer et tester votre application. Bon développement !

Cours : Validation des Données dans Laravel avec les Modèles Categorie et Produit

Dans ce cours, nous allons explorer en détail la validation des données dans Laravel. Nous travaillerons sur deux modèles : Categorie et Produit. Nous inclurons également des colonnes supplémentaires pour le modèle Produit (comme codebar, quantitystock, etc.) afin de rendre l'exemple plus réaliste.


1. Introduction à la Validation des Données

La validation des données est une étape cruciale dans le développement d'une application web. Elle permet de s'assurer que les données soumises par les utilisateurs respectent les règles définies avant d'être stockées dans la base de données.

Dans Laravel, la validation peut être effectuée directement dans les contrôleurs ou via des classes de requête personnalisées (FormRequest). Dans ce cours, nous utiliserons la validation directement dans les contrôleurs.


2. Étape 1 : Créer les Migrations

Migration pour Categorie

Créez une migration pour la table categories :

php artisan make:migration create_categories_table

Ouvrez le fichier de migration généré et définissez la structure de la table :

public function up()
{
Schema::create('categories', function (Blueprint $table) {
$table->id(); // Clé primaire auto-incrémentée
$table->string('nom')->unique(); // Nom unique de la catégorie
$table->text('description')->nullable(); // Description facultative
$table->timestamps(); // Colonnes created_at et updated_at
});
}

Migration pour Produit

Créez une migration pour la table produits :

php artisan make:migration create_produits_table

Ouvrez le fichier de migration généré et définissez la structure de la table :

public function up()
{
Schema::create('produits', function (Blueprint $table) {
$table->id(); // Clé primaire auto-incrémentée
$table->string('nom'); // Nom du produit
$table->foreignId('categorie_id')->constrained()->onDelete('cascade'); // Relation avec categories
$table->string('codebar')->unique(); // Code-barres unique
$table->integer('quantitystock')->unsigned(); // Quantité en stock (non négative)
$table->decimal('prix', 8, 2); // Prix du produit
$table->timestamps(); // Colonnes created_at et updated_at
});
}

Exécutez les migrations pour créer les tables dans la base de données :

php artisan migrate

3. Étape 2 : Créer les Modèles

Modèle Categorie

Créez un modèle Categorie :

php artisan make:model Categorie

Ajoutez les règles de validation et la relation avec Produit :

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Categorie extends Model
{
use HasFactory;

protected $fillable = ['nom', 'description'];

// Une catégorie a plusieurs produits
public function produits()
{
return $this->hasMany(Produit::class);
}
}

Modèle Produit

Créez un modèle Produit :

php artisan make:model Produit

Ajoutez les règles de validation et la relation avec Categorie :

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Produit extends Model
{
use HasFactory;

protected $fillable = ['nom', 'categorie_id', 'codebar', 'quantitystock', 'prix'];

// Un produit appartient à une catégorie
public function categorie()
{
return $this->belongsTo(Categorie::class);
}
}

4. Étape 3 : Créer les Contrôleurs

Contrôleur CategorieController

Créez un contrôleur CategorieController :

php artisan make:controller CategorieController

Ajoutez la méthode store pour valider et enregistrer une nouvelle catégorie :

namespace App\Http\Controllers;

use App\Models\Categorie;
use Illuminate\Http\Request;

class CategorieController extends Controller
{
// Afficher le formulaire de création
public function create()
{
return view('categories.create');
}

// Valider et enregistrer une nouvelle catégorie
public function store(Request $request)
{
$validatedData = $request->validate([
'nom' => 'required|string|max:255|unique:categories',
'description' => 'nullable|string',
]);

Categorie::create($validatedData);

return redirect()->route('categories.index')->with('success', 'Catégorie créée avec succès.');
}
}

Contrôleur ProduitController

Créez un contrôleur ProduitController :

php artisan make:controller ProduitController

Ajoutez la méthode store pour valider et enregistrer un nouveau produit :

namespace App\Http\Controllers;

use App\Models\Produit;
use App\Models\Categorie;
use Illuminate\Http\Request;

class ProduitController extends Controller
{
// Afficher le formulaire de création
public function create()
{
$categories = Categorie::all();
return view('produits.create', compact('categories'));
}

// Valider et enregistrer un nouveau produit
public function store(Request $request)
{
$validatedData = $request->validate([
'nom' => 'required|string|max:255',
'categorie_id' => 'required|exists:categories,id',
'codebar' => 'required|string|max:50|unique:produits',
'quantitystock' => 'required|integer|min:0',
'prix' => 'required|numeric|min:0',
]);

Produit::create($validatedData);

return redirect()->route('produits.index')->with('success', 'Produit créé avec succès.');
}
}

5. Étape 4 : Créer les Vues

Vue categories/create.blade.php

Créez une vue pour ajouter une nouvelle catégorie :

<!-- resources/views/categories/create.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Ajouter une Catégorie</title>
</head>
<body>
<h1>Ajouter une Catégorie</h1>

@if ($errors->any())
<div>
<ul>
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif

<form action="{{ route('categories.store') }}" method="POST">
@csrf
<label for="nom">Nom :</label>
<input type="text" name="nom" id="nom" required><br>

<label for="description">Description :</label>
<textarea name="description" id="description"></textarea><br>

<button type="submit">Enregistrer</button>
</form>

<a href="{{ route('categories.index') }}">Retour à la liste</a>
</body>
</html>

Vue produits/create.blade.php

Créez une vue pour ajouter un nouveau produit :

<!-- resources/views/produits/create.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Ajouter un Produit</title>
</head>
<body>
<h1>Ajouter un Produit</h1>

@if ($errors->any())
<div>
<ul>
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif

<form action="{{ route('produits.store') }}" method="POST">
@csrf
<label for="nom">Nom :</label>
<input type="text" name="nom" id="nom" required><br>

<label for="categorie_id">Catégorie :</label>
<select name="categorie_id" id="categorie_id" required>
@foreach ($categories as $categorie)
<option value="{{ $categorie->id }}">{{ $categorie->nom }}</option>
@endforeach
</select><br>

<label for="codebar">Code-barres :</label>
<input type="text" name="codebar" id="codebar" required><br>

<label for="quantitystock">Quantité en Stock :</label>
<input type="number" name="quantitystock" id="quantitystock" min="0" required><br>

<label for="prix">Prix :</label>
<input type="number" step="0.01" name="prix" id="prix" min="0" required><br>

<button type="submit">Enregistrer</button>
</form>

<a href="{{ route('produits.index') }}">Retour à la liste</a>
</body>
</html>

6. Étape 5 : Définir les Routes

Ajoutez les routes dans routes/web.php :

use App\Http\Controllers\CategorieController;
use App\Http\Controllers\ProduitController;

// Routes pour Catégorie
Route::get('/categories/create', [CategorieController::class, 'create'])->name('categories.create');
Route::post('/categories', [CategorieController::class, 'store'])->name('categories.store');

// Routes pour Produit
Route::get('/produits/create', [ProduitController::class, 'create'])->name('produits.create');
Route::post('/produits', [ProduitController::class, 'store'])->name('produits.store');

7. Conclusion

Vous avez maintenant une application complète avec des fonctionnalités de validation des données pour les modèles Categorie et Produit. Voici un résumé des étapes que nous avons suivies :

  1. Création des migrations pour les tables categories et produits.
  2. Création des modèles avec des relations.
  3. Implémentation des contrôleurs avec des méthodes de validation.
  4. Création des vues avec affichage des erreurs de validation.
  5. Définition des routes pour accéder aux fonctionnalités.

Avec ces bases, vous pouvez facilement étendre votre application pour inclure des validations plus complexes ou des fonctionnalités supplémentaires. Bon développement !

Gestion des Sessions et Authentification dans Laravel avec le Modèle Produit

Dans ce tutoriel, nous allons implémenter une gestion des sessions et de l'authentification dans une application Laravel. Nous allons restreindre les actions CRUD (Ajouter, Modifier, Supprimer, Afficher) sur le modèle Produit afin que seuls les utilisateurs connectés puissent effectuer ces opérations.


1. Introduction à la Gestion des Sessions et Authentification

Pourquoi Utiliser l'Authentification ?

L'authentification permet de vérifier si un utilisateur est autorisé à accéder à certaines parties d'une application. Dans notre cas, nous voulons que seuls les utilisateurs connectés puissent interagir avec les produits.

Étapes à Suivre

  1. Créer les modèles et migrations pour User et Produit.
  2. Configurer l'authentification avec Laravel Breeze ou Laravel UI.
  3. Implémenter les contrôleurs avec des protections d'accès.
  4. Créer les vues avec des messages d'erreur pour les utilisateurs non connectés.
  5. Définir les routes avec des middlewares d'authentification.

2. Étape 1 : Créer les Migrations

Migration pour User

Laravel inclut déjà une migration par défaut pour la table users. Si vous n'avez pas encore exécuté les migrations, vous pouvez le faire maintenant :

php artisan migrate

Migration pour Produit

Créez une migration pour la table produits :

php artisan make:migration create_produits_table

Ouvrez le fichier de migration généré et définissez la structure de la table :

public function up()
{
Schema::create('produits', function (Blueprint $table) {
$table->id(); // Clé primaire auto-incrémentée
$table->string('nom'); // Nom du produit
$table->decimal('prix', 8, 2); // Prix du produit
$table->integer('quantitystock')->unsigned(); // Quantité en stock
$table->timestamps(); // Colonnes created_at et updated_at
});
}

Exécutez les migrations :

php artisan migrate

3. Étape 2 : Configurer l'Authentification

Installer Laravel Breeze

Laravel Breeze est un package simple pour configurer rapidement l'authentification. Installez-le avec Composer :

composer require laravel/breeze --dev

Publiez les fichiers nécessaires :

php artisan breeze:install

Compilez les assets :

npm install && npm run build

Exécutez les migrations pour créer la table users :

php artisan migrate

Démarrer le serveur :

php artisan serve

Vous pouvez maintenant accéder aux pages d'inscription (/register) et de connexion (/login).


4. Étape 3 : Créer les Modèles

Modèle User

Le modèle User est déjà inclus dans Laravel. Vous n'avez pas besoin de le créer manuellement.

Modèle Produit

Créez un modèle Produit :

php artisan make:model Produit

Ajoutez les règles de validation et les attributs remplissables :

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Produit extends Model
{
use HasFactory;

protected $fillable = ['nom', 'prix', 'quantitystock'];
}

5. Étape 4 : Créer les Contrôleurs

Contrôleur ProduitController

Créez un contrôleur ProduitController :

php artisan make:controller ProduitController

Ajoutez les méthodes CRUD avec des protections d'accès :

namespace App\Http\Controllers;

use App\Models\Produit;
use Illuminate\Http\Request;

class ProduitController extends Controller
{
public function __construct()
{
// Appliquer le middleware d'authentification à toutes les méthodes
$this->middleware('auth');
}

// Liste tous les produits
public function index()
{
$produits = Produit::all();
return view('produits.index', compact('produits'));
}

// Affiche le formulaire de création
public function create()
{
return view('produits.create');
}

// Enregistre un nouveau produit
public function store(Request $request)
{
$validatedData = $request->validate([
'nom' => 'required|string|max:255',
'prix' => 'required|numeric|min:0',
'quantitystock' => 'required|integer|min:0',
]);

Produit::create($validatedData);

return redirect()->route('produits.index')->with('success', 'Produit créé avec succès.');
}

// Affiche un produit spécifique
public function show(Produit $produit)
{
return view('produits.show', compact('produit'));
}

// Affiche le formulaire d'édition
public function edit(Produit $produit)
{
return view('produits.edit', compact('produit'));
}

// Met à jour un produit existant
public function update(Request $request, Produit $produit)
{
$validatedData = $request->validate([
'nom' => 'required|string|max:255',
'prix' => 'required|numeric|min:0',
'quantitystock' => 'required|integer|min:0',
]);

$produit->update($validatedData);

return redirect()->route('produits.index')->with('success', 'Produit mis à jour avec succès.');
}

// Supprime un produit
public function destroy(Produit $produit)
{
$produit->delete();

return redirect()->route('produits.index')->with('success', 'Produit supprimé avec succès.');
}
}

6. Étape 5 : Créer les Vues

Vue produits/index.blade.php

Affiche la liste des produits :

<!-- resources/views/produits/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Liste des Produits</title>
</head>
<body>
<h1>Liste des Produits</h1>

@if(session('success'))
<div>{{ session('success') }}</div>
@endif

<a href="{{ route('produits.create') }}">Ajouter un Produit</a>

<ul>
@foreach ($produits as $produit)
<li>
{{ $produit->nom }} - {{ $produit->prix }} € (Stock: {{ $produit->quantitystock }})
<a href="{{ route('produits.edit', $produit->id) }}">Éditer</a>
<form action="{{ route('produits.destroy', $produit->id) }}" method="POST" style="display:inline;">
@csrf
@method('DELETE')
<button type="submit">Supprimer</button>
</form>
</li>
@endforeach
</ul>

<a href="{{ route('logout') }}" onclick="event.preventDefault(); document.getElementById('logout-form').submit();">
Déconnexion
</a>

<form id="logout-form" action="{{ route('logout') }}" method="POST" style="display: none;">
@csrf
</form>
</body>
</html>

Vue produits/create.blade.php

Formulaire pour ajouter un produit :

<!-- resources/views/produits/create.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Ajouter un Produit</title>
</head>
<body>
<h1>Ajouter un Produit</h1>

<form action="{{ route('produits.store') }}" method="POST">
@csrf
<label for="nom">Nom :</label>
<input type="text" name="nom" id="nom" required><br>

<label for="prix">Prix :</label>
<input type="number" step="0.01" name="prix" id="prix" min="0" required><br>

<label for="quantitystock">Quantité en Stock :</label>
<input type="number" name="quantitystock" id="quantitystock" min="0" required><br>

<button type="submit">Enregistrer</button>
</form>

<a href="{{ route('produits.index') }}">Retour à la liste</a>
</body>
</html>

Les autres vues (edit, show) peuvent être créées de manière similaire.


7. Étape 6 : Définir les Routes

Ajoutez les routes dans routes/web.php :

use App\Http\Controllers\ProduitController;

// Routes protégées par authentification
Route::middleware(['auth'])->group(function () {
Route::get('/produits', [ProduitController::class, 'index'])->name('produits.index');
Route::get('/produits/create', [ProduitController::class, 'create'])->name('produits.create');
Route::post('/produits', [ProduitController::class, 'store'])->name('produits.store');
Route::get('/produits/{produit}', [ProduitController::class, 'show'])->name('produits.show');
Route::get('/produits/{produit}/edit', [ProduitController::class, 'edit'])->name('produits.edit');
Route::put('/produits/{produit}', [ProduitController::class, 'update'])->name('produits.update');
Route::delete('/produits/{produit}', [ProduitController::class, 'destroy'])->name('produits.destroy');
});

// Routes d'authentification
Auth::routes();

8. Conclusion

Vous avez maintenant une application complète avec une gestion des sessions et de l'authentification. Voici un résumé des étapes que nous avons suivies :

  1. Création des migrations pour User et Produit.
  2. Configuration de l'authentification avec Laravel Breeze.
  3. Implémentation des contrôleurs avec des protections d'accès.
  4. Création des vues avec des formulaires et des messages d'erreur.
  5. Définition des routes avec des middlewares d'authentification.

Avec cette configuration, seuls les utilisateurs connectés peuvent ajouter, modifier, supprimer ou afficher la liste des produits. Bon développement !

Ajouter la Notion de Rôle pour Gérer les Permissions dans Laravel

Dans ce tutoriel, nous allons étendre notre application précédente en ajoutant la notion de rôles pour gérer les permissions des utilisateurs. Nous implémenterons deux rôles :

  • Admin : Peut ajouter, modifier, supprimer et afficher les produits.
  • Manager : Peut uniquement afficher les produits.

Nous allons mettre à jour les modèles, migrations, contrôleurs, vues et routes pour prendre en charge cette logique de rôle.


1. Introduction aux Rôles et Permissions

Pourquoi Utiliser des Rôles ?

Les rôles permettent de définir des niveaux d'accès différents pour les utilisateurs. Par exemple :

  • Un admin a un accès complet (CRUD).
  • Un manager a un accès limité (lecture seule).

Nous allons utiliser une colonne role dans la table users pour stocker le rôle de chaque utilisateur.


2. Étape 1 : Mettre à Jour la Migration users

Ajoutez une colonne role à la table users pour stocker le rôle de l'utilisateur.

Créer une Nouvelle Migration

Exécutez la commande suivante pour créer une migration qui ajoute la colonne role :

php artisan make:migration add_role_to_users_table --table=users

Ouvrez le fichier de migration généré et ajoutez la colonne role :

public function up()
{
Schema::table('users', function (Blueprint $table) {
$table->string('role')->default('manager'); // Valeur par défaut : 'manager'
});
}

public function down()
{
Schema::table('users', function (Blueprint $table) {
$table->dropColumn('role');
});
}

Exécutez la migration :

php artisan migrate

3. Étape 2 : Mettre à Jour le Modèle User

Ajoutez une méthode pour vérifier si un utilisateur a un rôle spécifique.

Mise à Jour du Modèle User

Ouvrez le fichier User.php dans app/Models et ajoutez la méthode suivante :

namespace App\Models;

use Illuminate\Foundation\Auth\User as Authenticatable;

class User extends Authenticatable
{
use HasFactory, Notifiable;

protected $fillable = [
'name', 'email', 'password', 'role',
];

// Vérifie si l'utilisateur est un admin
public function isAdmin()
{
return $this->role === 'admin';
}

// Vérifie si l'utilisateur est un manager
public function isManager()
{
return $this->role === 'manager';
}
}

4. Étape 3 : Mettre à Jour le Contrôleur ProduitController

Modifiez le contrôleur pour restreindre les actions en fonction du rôle de l'utilisateur.

Mise à Jour du Contrôleur ProduitController

Ajoutez des vérifications de rôle dans les méthodes du contrôleur :

namespace App\Http\Controllers;

use App\Models\Produit;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;

class ProduitController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}

// Liste tous les produits (accessible à tous les rôles)
public function index()
{
$produits = Produit::all();
return view('produits.index', compact('produits'));
}

// Affiche le formulaire de création (uniquement pour admin)
public function create()
{
if (!Auth::user()->isAdmin()) {
return redirect()->route('produits.index')->with('error', 'Vous n\'avez pas la permission d\'ajouter des produits.');
}
return view('produits.create');
}

// Enregistre un nouveau produit (uniquement pour admin)
public function store(Request $request)
{
if (!Auth::user()->isAdmin()) {
return redirect()->route('produits.index')->with('error', 'Vous n\'avez pas la permission d\'ajouter des produits.');
}

$validatedData = $request->validate([
'nom' => 'required|string|max:255',
'prix' => 'required|numeric|min:0',
'quantitystock' => 'required|integer|min:0',
]);

Produit::create($validatedData);

return redirect()->route('produits.index')->with('success', 'Produit créé avec succès.');
}

// Supprime un produit (uniquement pour admin)
public function destroy(Produit $produit)
{
if (!Auth::user()->isAdmin()) {
return redirect()->route('produits.index')->with('error', 'Vous n\'avez pas la permission de supprimer des produits.');
}

$produit->delete();

return redirect()->route('produits.index')->with('success', 'Produit supprimé avec succès.');
}
}

5. Étape 4 : Mettre à Jour les Vues

Ajoutez des conditions dans les vues pour afficher ou masquer les boutons en fonction du rôle de l'utilisateur.

Vue produits/index.blade.php

Modifiez la vue pour afficher les boutons uniquement si l'utilisateur est un admin :

<!-- resources/views/produits/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Liste des Produits</title>
</head>
<body>
<h1>Liste des Produits</h1>

@if(session('success'))
<div>{{ session('success') }}</div>
@endif

@if(session('error'))
<div>{{ session('error') }}</div>
@endif

@if(Auth::user()->isAdmin())
<a href="{{ route('produits.create') }}">Ajouter un Produit</a>
@endif

<ul>
@foreach ($produits as $produit)
<li>
{{ $produit->nom }} - {{ $produit->prix }} € (Stock: {{ $produit->quantitystock }})
@if(Auth::user()->isAdmin())
<a href="{{ route('produits.edit', $produit->id) }}">Éditer</a>
<form action="{{ route('produits.destroy', $produit->id) }}" method="POST" style="display:inline;">
@csrf
@method('DELETE')
<button type="submit">Supprimer</button>
</form>
@endif
</li>
@endforeach
</ul>

<a href="{{ route('logout') }}" onclick="event.preventDefault(); document.getElementById('logout-form').submit();">
Déconnexion
</a>

<form id="logout-form" action="{{ route('logout') }}" method="POST" style="display: none;">
@csrf
</form>
</body>
</html>

6. Étape 5 : Définir les Routes

Aucune modification supplémentaire n'est nécessaire dans les routes, car les vérifications de rôle sont déjà gérées dans le contrôleur.


7. Étape 6 : Tester l'Application

Créer des Utilisateurs avec Différents Rôles

Vous pouvez créer des utilisateurs avec des rôles différents en utilisant Tinker :

php artisan tinker

Créez un utilisateur admin :

\App\Models\User::create([
'name' => 'Admin',
'email' => 'admin@example.com',
'password' => bcrypt('password'),
'role' => 'admin',
]);

Créez un utilisateur manager :

\App\Models\User::create([
'name' => 'Manager',
'email' => 'manager@example.com',
'password' => bcrypt('password'),
'role' => 'manager',
]);

Tester les Fonctionnalités

  1. Connectez-vous en tant qu'admin et vérifiez que vous pouvez ajouter, modifier et supprimer des produits.
  2. Connectez-vous en tant que manager et vérifiez que vous ne pouvez que consulter la liste des produits.

8. Conclusion

Vous avez maintenant une application complète avec une gestion des rôles et des permissions. Voici un résumé des étapes que nous avons suivies :

  1. Ajout d'une colonne role dans la table users.
  2. Mise à jour du modèle User pour inclure des méthodes de vérification de rôle.
  3. Modification du contrôleur ProduitController pour appliquer des restrictions basées sur le rôle.
  4. Mise à jour des vues pour afficher ou masquer les boutons en fonction du rôle.
  5. Test de l'application avec des utilisateurs ayant des rôles différents.

Avec cette configuration, vous pouvez facilement étendre votre application pour inclure d'autres rôles ou permissions. Bon développement !

Gestion des Rôles et Permissions dans Laravel avec les Modèles Client et Comment

Dans ce tutoriel, nous allons créer une application complète pour gérer les rôles et permissions en utilisant deux modèles :

  • Client (idclient, nom, email, password, role) : Représente un utilisateur (client ou admin).
  • Comment (idcomment, date, content, idClient) : Représente un commentaire ajouté par un client.

Nous implémenterons les fonctionnalités suivantes :

  1. Un client peut ajouter et supprimer ses propres commentaires.
  2. Un admin peut lister, modifier et supprimer tous les comptes clients ainsi que tous les commentaires.

1. Étape 1 : Créer les Migrations

Migration pour clients

Créez une migration pour la table clients :

php artisan make:migration create_clients_table

Ouvrez le fichier de migration généré et définissez la structure de la table :

public function up()
{
Schema::create('clients', function (Blueprint $table) {
$table->id(); // Clé primaire auto-incrémentée
$table->string('nom'); // Nom du client
$table->string('email')->unique(); // Email unique
$table->string('password'); // Mot de passe crypté
$table->enum('role', ['client', 'admin'])->default('client'); // Rôle : client ou admin
$table->timestamps(); // Colonnes created_at et updated_at
});
}

Migration pour comments

Créez une migration pour la table comments :

php artisan make:migration create_comments_table

Ouvrez le fichier de migration généré et définissez la structure de la table :

public function up()
{
Schema::create('comments', function (Blueprint $table) {
$table->id(); // Clé primaire auto-incrémentée
$table->text('content'); // Contenu du commentaire
$table->timestamp('date')->useCurrent(); // Date automatique
$table->foreignId('idClient')->constrained('clients')->onDelete('cascade'); // Relation avec clients
$table->timestamps(); // Colonnes created_at et updated_at
});
}

Exécutez les migrations :

php artisan migrate

2. Étape 2 : Créer les Modèles

Modèle Client

Créez un modèle Client :

php artisan make:model Client

Ajoutez les relations et les attributs remplissables :

namespace App\Models;

use Illuminate\Foundation\Auth\User as Authenticatable;

class Client extends Authenticatable
{
protected $fillable = ['nom', 'email', 'password', 'role'];

// Relation : Un client a plusieurs commentaires
public function comments()
{
return $this->hasMany(Comment::class, 'idClient');
}

// Vérifie si l'utilisateur est un admin
public function isAdmin()
{
return $this->role === 'admin';
}

// Vérifie si l'utilisateur est un client
public function isClient()
{
return $this->role === 'client';
}
}

Modèle Comment

Créez un modèle Comment :

php artisan make:model Comment

Ajoutez les relations et les attributs remplissables :

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Comment extends Model
{
use HasFactory;

protected $fillable = ['content', 'idClient'];

// Relation : Un commentaire appartient à un client
public function client()
{
return $this->belongsTo(Client::class, 'idClient');
}
}

3. Étape 3 : Configurer l'Authentification

Installez Laravel Breeze pour configurer rapidement l'authentification :

composer require laravel/breeze --dev
php artisan breeze:install
npm install && npm run build
php artisan migrate

4. Étape 4 : Créer les Contrôleurs

Contrôleur CommentController

Créez un contrôleur CommentController :

php artisan make:controller CommentController

Ajoutez les méthodes CRUD avec des vérifications de rôle :

namespace App\Http\Controllers;

use App\Models\Comment;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;

class CommentController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}

// Ajouter un commentaire (uniquement pour les clients)
public function store(Request $request)
{
$validatedData = $request->validate([
'content' => 'required|string',
]);

$comment = new Comment();
$comment->content = $validatedData['content'];
$comment->idClient = Auth::user()->id;
$comment->save();

return redirect()->back()->with('success', 'Commentaire ajouté avec succès.');
}

// Supprimer un commentaire (client : ses propres commentaires, admin : tous les commentaires)
public function destroy(Comment $comment)
{
if (Auth::user()->isAdmin() || Auth::user()->id === $comment->idClient) {
$comment->delete();
return redirect()->back()->with('success', 'Commentaire supprimé avec succès.');
}

return redirect()->back()->with('error', 'Vous n\'avez pas la permission de supprimer ce commentaire.');
}
}

Contrôleur AdminController

Créez un contrôleur AdminController pour gérer les actions réservées aux admins :

php artisan make:controller AdminController

Ajoutez les méthodes pour lister, modifier et supprimer les clients :

namespace App\Http\Controllers;

use App\Models\Client;
use Illuminate\Http\Request;

class AdminController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}

// Liste tous les clients (uniquement pour admin)
public function index()
{
if (!Auth::user()->isAdmin()) {
return redirect()->route('home')->with('error', 'Accès refusé.');
}

$clients = Client::all();
return view('admin.clients.index', compact('clients'));
}

// Supprimer un client (uniquement pour admin)
public function destroy(Client $client)
{
if (!Auth::user()->isAdmin()) {
return redirect()->route('home')->with('error', 'Accès refusé.');
}

$client->delete();
return redirect()->route('admin.clients.index')->with('success', 'Client supprimé avec succès.');
}
}

5. Étape 5 : Créer les Vues

Vue comments/create.blade.php

Formulaire pour ajouter un commentaire :

<!-- resources/views/comments/create.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Ajouter un Commentaire</title>
</head>
<body>
<h1>Ajouter un Commentaire</h1>

<form action="{{ route('comments.store') }}" method="POST">
@csrf
<label for="content">Contenu :</label>
<textarea name="content" id="content" required></textarea><br>
<button type="submit">Ajouter</button>
</form>

<a href="{{ route('home') }}">Retour</a>
</body>
</html>

Vue admin/clients/index.blade.php

Liste des clients pour l'admin :

<!-- resources/views/admin/clients/index.blade.php -->
<!DOCTYPE html>
<html>
<head>
<title>Liste des Clients</title>
</head>
<body>
<h1>Liste des Clients</h1>

<ul>
@foreach ($clients as $client)
<li>
{{ $client->nom }} - {{ $client->email }}
<form action="{{ route('admin.clients.destroy', $client->id) }}" method="POST" style="display:inline;">
@csrf
@method('DELETE')
<button type="submit">Supprimer</button>
</form>
</li>
@endforeach
</ul>

<a href="{{ route('home') }}">Retour</a>
</

1. Qu'est-ce qu'un Middleware ?

Un Middleware est un filtre qui intercepte les requêtes HTTP avant qu'elles n'atteignent le contrôleur ou la route finale. Il peut modifier la requête, effectuer des vérifications (par exemple, l'authentification), ou même arrêter la requête si certaines conditions ne sont pas remplies.

2. Pourquoi utiliser des Middleware ?

3. Les Middleware par défaut dans Laravel

Lorsque vous installez Laravel, plusieurs middleware sont déjà configurés pour vous dans le dossier app/Http/Middleware. Voici quelques exemples courants :

4. Création d'un Middleware personnalisé

Pour créer un middleware personnalisé, utilisez la commande Artisan suivante :

php artisan make:middleware NomDuMiddleware

Exemple :

php artisan make:middleware CheckAge

Cette commande générera un fichier dans le dossier app/Http/Middleware.

5. Enregistrement d'un Middleware

Ajoutez votre middleware dans le fichier app/Http/Kernel.php :


protected $routeMiddleware = [
'check.age' => \App\Http\Middleware\CheckAge::class,
];

6. Utilisation d'un Middleware

Appliquez un middleware à une route :


Route::get('/dashboard', function () {
return view('dashboard');
})->middleware('check.age');

7. Passage de paramètres à un Middleware

Modifiez le middleware pour accepter des paramètres :


public function handle(Request $request, Closure $next, $minAge)
{
if ($request->input('age') < $minAge) {
return redirect('/home');
}

return $next($request);
}

Utilisez-le avec des paramètres :


Route::get('/restricted', function () {
return view('restricted');
})->middleware('check.age:21');




Documentation de l'API de Gestion des Voyages

1. Configuration initiale du projet

Pour commencer, assurez-vous d'avoir installé PHP, Composer et Laravel sur votre machine. Ces outils sont nécessaires pour créer et exécuter une application Laravel.

1.1 Créer un nouveau projet Laravel

Pour créer un nouveau projet Laravel, utilisez la commande suivante dans votre terminal :

composer create-project --prefer-dist laravel/laravel travel-api

Cette commande crée un nouveau projet Laravel nommé "travel-api".

1.2 Accéder au dossier du projet

Après avoir créé le projet, accédez au dossier du projet en utilisant la commande suivante :

cd travel-api

Cela vous permet de naviguer dans le répertoire où se trouve votre projet Laravel.

1.3 Configurer la base de données

Ouvrez le fichier .env situé à la racine de votre projet. Ce fichier contient les configurations de votre application, y compris celles de la base de données. Modifiez les lignes suivantes pour configurer votre base de données :


DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=travel_db
DB_USERNAME=root
DB_PASSWORD=

Remplacez les valeurs par celles de votre propre base de données MySQL. Par exemple, si vous avez un mot de passe pour votre base de données, indiquez-le dans DB_PASSWORD.

2. Création des modèles et migrations

Pour gérer les voyages, nous aurons besoin de plusieurs entités, telles que les utilisateurs (User), les voyages (Trip) et les destinations (Destination). Nous allons créer ces entités avec leurs migrations correspondantes.

2.1 Créer le modèle et la migration pour Trip

Pour créer un modèle et une migration pour les voyages, utilisez la commande suivante :

php artisan make:model Trip -m

Cette commande crée un modèle nommé Trip et une migration associée. La migration est un fichier qui définit la structure de la table dans la base de données.

Dans le fichier de migration généré (database/migrations/..._create_trips_table.php), ajoutez les colonnes suivantes :


public function up()
{
Schema::create('trips', function (Blueprint $table) {
$table->id();
$table->string('title');
$table->text('description')->nullable();
$table->date('start_date');
$table->date('end_date');
$table->decimal('price', 8, 2);
$table->timestamps();
});
}

Explication des colonnes :

Exécutez les migrations pour créer la table dans la base de données :

php artisan migrate

2.2 Créer le modèle et la migration pour Destination

Pour créer un modèle et une migration pour les destinations, utilisez la commande suivante :

php artisan make:model Destination -m

Dans le fichier de migration généré (database/migrations/..._create_destinations_table.php), ajoutez les colonnes suivantes :


public function up()
{
Schema::create('destinations', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('country');
$table->text('description')->nullable();
$table->timestamps();
});
}

Explication des colonnes :

Exécutez les migrations pour créer la table dans la base de données :

php artisan migrate

3. Création des contrôleurs

Les contrôleurs sont responsables de gérer les requêtes HTTP et de renvoyer des réponses appropriées. Nous allons créer des contrôleurs pour gérer les voyages et les destinations.

3.1 Créer un contrôleur pour Trip

Pour créer un contrôleur pour les voyages, utilisez la commande suivante :

php artisan make:controller Api/TripController --api

Cette commande crée un contrôleur API nommé TripController avec des méthodes prédéfinies pour les opérations CRUD (Create, Read, Update, Delete).

Dans app/Http/Controllers/Api/TripController.php, ajoutez le code suivant :


namespace App\Http\Controllers\Api;

use App\Models\Trip;
use Illuminate\Http\Request;

class TripController extends Controller
{
public function index()
{
return Trip::all();
}

public function store(Request $request)
{
$trip = Trip::create($request->all());
return response()->json($trip, 201);
}

public function show($id)
{
$trip = Trip::find($id);
if (!$trip) {
return response()->json(['message' => 'Voyage non trouvé'], 404);
}
return $trip;
}

public function update(Request $request, $id)
{
$trip = Trip::find($id);
if (!$trip) {
return response()->json(['message' => 'Voyage non trouvé'], 404);
}
$trip->update($request->all());
return response()->json($trip, 200);
}

public function destroy($id)
{
$trip = Trip::find($id);
if (!$trip) {
return response()->json(['message' => 'Voyage non trouvé'], 404);
}
$trip->delete();
return response()->json(['message' => 'Voyage supprimé'], 204);
}
}

Explication des méthodes :

3.2 Créer un contrôleur pour Destination

Pour créer un contrôleur pour les destinations, utilisez la commande suivante :

php artisan make:controller Api/DestinationController --api

Dans app/Http/Controllers/Api/DestinationController.php, ajoutez le code suivant :


namespace App\Http\Controllers\Api;

use App\Models\Destination;
use Illuminate\Http\Request;

class DestinationController extends Controller
{
public function index()
{
return Destination::all();
}

public function store(Request $request)
{
$destination = Destination::create($request->all());
return response()->json($destination, 201);
}

public function show($id)
{
$destination = Destination::find($id);
if (!$destination) {
return response()->json(['message' => 'Destination non trouvée'], 404);
}
return $destination;
}

public function update(Request $request, $id)
{
$destination = Destination::find($id);
if (!$destination) {
return response()->json(['message' => 'Destination non trouvée'], 404);
}
$destination->update($request->all());
return response()->json($destination, 200);
}

public function destroy($id)
{
$destination = Destination::find($id);
if (!$destination) {
return response()->json(['message' => 'Destination non trouvée'], 404);
}
$destination->delete();
return response()->json(['message' => 'Destination supprimée'], 204);
}
}

4. Définir les routes API

Les routes définissent les points d'accès de votre API. Ouvrez le fichier routes/api.php et ajoutez les routes suivantes :


use App\Http\Controllers\Api\TripController;
use App\Http\Controllers\Api\DestinationController;

Route::prefix('v1')->group(function () {
// Routes pour les voyages
Route::apiResource('trips', TripController::class);

// Routes pour les destinations
Route::apiResource('destinations', DestinationController::class);
});

Cela crée des routes pour les opérations CRUD sur les voyages et les destinations. Le préfixe v1 signifie que ces routes appartiennent à la version 1 de l'API.

5. Tester l'API

Vous pouvez tester l'API en utilisant des outils comme Postman ou cURL.

Exemple de requêtes :

6. Ajouter des relations entre les modèles

Si un voyage est lié à une destination, vous pouvez définir une relation dans les modèles.

Dans app/Models/Trip.php :


public function destination()
{
return $this->belongsTo(Destination::class);
}

Cela signifie qu'un voyage appartient à une destination.

Dans app/Models/Destination.php :


public function trips()
{
return $this->hasMany(Trip::class);
}

Cela signifie qu'une destination peut avoir plusieurs voyages.

Ensuite, mettez à jour les migrations pour ajouter une clé étrangère dans la table trips :

$table->foreignId('destination_id')->constrained()->onDelete('cascade');

Cela lie chaque voyage à une destination et supprime automatiquement les voyages liés si la destination est supprimée.