• Час читання ~6 хв
  • 26.06.2023

Поліморфний зв'язок Ларавеля дозволяє моделі належати до більш ніж однієї іншої моделі на одній асоціації. Ми візьмемо офіційний приклад документації Laravel для цього підручника. Візьмемо приклад «коментарів» як у публікаціях, так і у відео. Використовуючи поліморфні зв'язки, можна використовувати одну таблицю приміток для обох цих сценаріїв.

За замовчуванням Laravel використовуватиме повне ім'я класу для зберігання типу пов'язаної моделі.

У Ларавелі існує чотири типи поліморфних відносин.

  1. One To One Polymorphic Relationship
  2. One To Many Polymorphic Relationship
  3. Many To Many Polymorphic Relationship
  4. Custom Polymorphic Relationship

Поліморфний зв'язок

один до одногоПоліморфний зв'язок один-до-одного можна порівняти з простим відношенням один-до-одного; Однак цільова модель може належати до більш ніж одного типу моделі на одній асоціації.

Наприклад, публікація блогу та користувач можуть мати поліморфне відношення до моделі зображення.

Використання поліморфного відношення один до одного дозволяє мати єдиний список унікальних зображень, які приймаються як для записів блогу, так і для облікових записів користувачів.

Один до багатьох поліморфних зв'язків

Поліморфний зв'язок один-до-багатьох можна порівняти з простим відношенням один-до-багатьох; Однак цільова модель може належати до більш ніж одного типу моделі на одній асоціації.

Наприклад, уявіть, що користувачі вашого додатка можуть "коментувати" як публікації, так і відео.

Використовуючи поліморфні зв'язки, ви можете використовувати таблицю окремих коментарів для обох цих випадків використання.

Багато поліморфних відносин

Поліморфні відносини багато-до-багатьох дещо складніші, ніж морфОдин і морфБагато відносин.

Наприклад, модель публікації в блозі та відео може мати поліморфне відношення до моделі тегів.

Використовуючи поліморфне відношення багато-до-багатьох, ви отримаєте єдиний список унікальних тегів, спільних для записів блогу та відео.

Настроюваний поліморфний зв'язок

Наприклад, враховуючи наведений вище приклад «один-до-багатьох», де коментар може належати до допису або відео, commentable_type за замовчуванням буде «App\Post» або «App\Video» відповідно.

Однак ви можете позаздрити відокремити вашу базу даних від внутрішньої структури вашої програми.

У цьому випадку ви можете встановити "карту морфінгу", щоб наказати Eloquent використовувати власне ім'я для кожної моделі замість імені класу.

Тепер давайте розглянемо загальний приклад поліморфного зв'язку.

Всього є три таблиці.

  1. posts
  2. videos
  3. comments

Тепер причина, по якій ми можемо застосувати поліморфний зв'язок тут, полягає в тому, що коментар можна застосовувати як до публікацій, так і до відео.

Так, модель Comment може бути пов'язана з Post і Video.

Тепер нам потрібно додати два додаткові стовпці всередині таблиці публікацій .

  1. commentable_id (Integer)
  2. commentable_type (String)

Стовпець commentable_id  міститиме ідентифікаційне значення публікації або відео.

Стовпець commentable_type  міститиме ім'я класу моделі, що володіє. Тепер давайте почнемо практику на прикладі поліморфних відносин Ларавела.

Ми починаємо наш проект з установки проекту Laravel.

Крок 1: встановіть Laravel 6

Введіть таку команду у своєму терміналі.

laravel new relationships

# або

composer create-project laravel/laravel relationships --prefer-dist

Після установки заходимо в проект.

cd relationships

Відкрийте проект у редакторі коду.

code .

Настройте базу даних всередині файлу .env .

Тепер створіть риштування автентифікації за допомогою такої команди.

php artisan make:auth

Крок 2: Створення моделей і міграції.

Перейдіть до свого терміналу та спочатку створіть модель Post .

php artisan make:model Post -m

Також, ми створюємо Відео модель.

php artisan make:model Video -m

Тепер визначте схему для обох міграцій. Але, для початку, визначимо схему для create_posts_table.

// create_posts_table

public function up()
{
   Schema::create('posts', function (Blueprint $table) {
        $table->increments('id');
        $table->string('name');
        $table->timestamps();
    });
}

Тепер визначте схему для create_videos_table.

// create_videos_table

public function up()
{
     Schema::create('videos', function (Blueprint $table) {
         $table->increments('id');
         $table->string('name');            
         $table->timestamps();
     });
}

Гаразд, тепер перенесіть за допомогою такої команди.

php artisan migrate

Крок 3: Створіть два файли контролера.

Гаразд, тепер ми створимо два контролери для відображення представлень.

  1. PostController
  2. VideoController

Введіть таку команду, щоб створити її.

php artisan make:controller PostController
php artisan make:controller VideoController

 Тепер напишіть наступний код всередині файлу PostController.php .

// PostController.php

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Post;

class PostController extends Controller
{
    public function show(Post $post)
    {
        return view('post.show', compact('post'));
    }
}

Те ж саме для, VideoController.php файлу.

// VideoController.php

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Video;

class VideoController extends Controller
{
    public function show(Video $video)
    {
        return view('video.show', compact('video'));
    }
}

Тепер створіть дві папки всередині папки «Подання ».

  1. post
  2. video

Усередині папки запису створіть новий файл, який називається файлом show.blade.php . Крім того, те ж саме створює той самий файл show.blade.php всередині папки відео .

Крок 4: Визначте маршрути для показу публікації та відео.

У файлі web.php напишіть наступний код.

// web.php

Route::get('/post/{post}', 'PostController@show')->name('post.show');
Route::get('/video/{video}', 'VideoController@show')->name('video.show');

Тепер введіть дані вручну в базу даних. У режимі реального часу дані надходять з форми, але для цієї демонстрації, по-перше, введіть деякі фіктивні дані в таблицю публікацій .

Laravel Polymorphic Relationship Tutorial ExampleТепер вставте дані в таблицю відео .

Polymorphic Relationship in Laravel

Отже, ми вставили фіктивні дані в обидві таблиці.

Крок 5: Закодуйте файли перегляду.

Всередині повідомлення  >>  файлі show.blade.php напишіть наступний код.

<h3>{{ $post->name }}</h3>

Тепер перейдіть до браузера та введіть цю URL-адресу: http://relationships.test/post/1. Ви можете побачити 1-й пост.

Те ж саме для відео  >>  файлі show.blade.php напишіть наступний код.

<h3>{{ $video->name }}</h3>

Те саме, перейдіть до браузера та натисніть цю URL-адресу: http://relationships.test/video/1. Ви можете подивитися 1-е відео.

Крок 6: Створіть модель коментаря.

Введіть наведену нижче команду для створення моделі, а також перенесення.

php artisan make:model Comment -m

Тепер напишіть наступну схему всередині create_comments_table.

// create_comments_table

public function up()
{
    Schema::create('comments', function (Blueprint $table) {
         $table->increments('id');
         $table->integer('user_id')->unsigned();
         $table->text('body');
         $table->integer('commentable_id')->unsigned();
         $table->string('commentable_type');
         $table->timestamps();
    });
}

Перенесіть цю схему до бази даних.

php artisan migrate

Крок 7: Визначте зв'язки.

Тепер ми зберігаємо user_id всередині таблиці коментарів ; ми маємо відносини з Користувачем.

Коментар - це належитьКористувачеві. Таким чином, ми можемо записати цей зв'язок всередині файлу моделі Comment.php.

 // Comment.php

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

Гаразд, тепер ми пишемо ще одну функцію всередині файлу Comment.php , яка commentable().

// Comment.php

public function commentable()
{
    return $this->morphTo();
}

Тепер це означає, що тепер одна або кілька моделей можуть використовувати цю модель коментарів. У нашому прикладі це можна пов'язати з публікацією та відео. Обидва використовують ту саму модель коментарів .

Гаразд, отже, наступним кроком є модель публікації має багато коментарів. Таким чином, ми можемо визначити зв'язок всередині файлу Post.php так.

// Post.php

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Post extends Model
{
    public function comments()
    {
        return $this->morphMany(Comment::class, 'commentable');
    }
}

Те ж саме і для файлу Video.php .

 // Video.php

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Video extends Model
{
    public function comments()
    {
        return $this->morphMany(Comment::class, 'commentable');
    }
}

Крок 8: Вставте дані вручну в таблицю коментарів.

Ми налагодили всі відносини. Нам потрібно ввести демонстраційні коментарі та подивитися, чи отримаємо ми коментарі на сторінці шоу відео та публікації.

Polymorphic hasMany Relationship

Так, перший стовпець id, як зазвичай, авто-інкременти, другий - user_id, який в даний момент підписаний користувачем.

Третій стовпець - commentable_id; у нашому випадку це або ідентифікатор таблиці публікацій , або ідентифікатор таблиці відео .

Отже, ми додали таблиці публікацій та відео до відповідних коментарів.

Тепер відтворіть публікацію з їхніми коментарями у файлі show.blade.php .

<h3>{{ $post->name }}</h3>

<ul>
    @foreach($post->comments as $comment)
    <li>{{ $comment->body }}</li>
    @endforeach
</ul>

Перейдіть до браузера та натисніть цю URL-адресу: http://relationships.test/post/1. Ви можете побачити назву публікації та тіло коментаря. Ви можете записати той самий файл перегляду для відео  >>  show.blade.php.

 

<h3>{{ $video->name }}</h3>

<ul>
    @foreach($video->comments as $comment)
    <li>{{ $comment->body }}</li>
    @endforeach
</ul>

Тепер перевірте цю URL-адресу: http://relationships.test/video/1.

Ось і все; Ми успішно відобразили публікацію та відео з відповідними коментарями.

Хоча, в цьому прикладі, я вставив значення жорсткого коду, але ми побачимо програмно в майбутньому.

Comments

No comments yet
Yurij Finiv

Yurij Finiv

Full stack

Про мене

Professional Fullstack Developer with extensive experience in website and desktop application development. Proficient in a wide range of tools and technologies, including Bootstrap, Tailwind, HTML5, CSS3, PUG, JavaScript, Alpine.js, jQuery, PHP, MODX, and Node.js. Skilled in website development using Symfony, MODX, and Laravel. Experience: Contributed to the development and translation of MODX3 i...

Про автора CrazyBoy49z
WORK EXPERIENCE
Контакти
Ukraine, Lutsk
+380979856297