🤪Laravel 9 One To One Polymorphic Relationship Example (ok)

https://www.laravelia.com/post/laravel-one-to-one-polymorphic-relationship-example

Mẫu 1.1 xây dựng type model App\Models\Post

https://loremflickr.com/320/240
App/Models/Post
App/Models/User
INSERT INTO `images`(`id`, `imageable_id`, `imageable_type`, `url`) VALUES
(NULL, '1', 'App/Models/Post', 'https://loremflickr.com/320/240'), 
(NULL, '3', 'App/Models/Post', 'https://loremflickr.com/320/240'), 
(NULL, '2', 'App/Models/User', 'https://loremflickr.com/320/240'), 
(NULL, '4', 'App/Models/User', 'https://loremflickr.com/320/240');

C:\xampp\htdocs\wayarmy\routes\web.php

<?php
use Illuminate\Support\Facades\Route;
use App\Http\Controllers\TestController as TestController;
/*
|--------------------------------------------------------------------------
| Web Routes
|--------------------------------------------------------------------------
|
| Here is where you can register web routes for your application. These
| routes are loaded by the RouteServiceProvider within a group which
| contains the "web" middleware group. Now create something great!
|
*/
Route::get('/', function () {
    return view('welcome');
});
Route::get('test/{id}', [TestController::class,'index'])->name('index');
Route::get('test2/{id}', [TestController::class,'index2'])->name('index2');
Route::get('test3/{id}', [TestController::class,'index3'])->name('index3');

C:\xampp\htdocs\wayarmy\app\Http\Controllers\TestController.php

<?php
namespace App\Http\Controllers;
use App\Models\User;
use App\Models\Post;
use App\Models\Image;
use Illuminate\Http\Request;
class TestController extends Controller
{
  public function index($id)
  {
    $user = User::find($id);
    $user->image;
  }
  public function index2($id)
  {
    $post = Post::find($id);
    $post->image;
  }
  public function index3($id)
  {
    $post = Post::find($id);
    $image = new Image;
    $image->url = "your_image";
    $post->image()->save($image);
  }
}

C:\xampp\htdocs\wayarmy\database\factories\UserFactory.php

<?php
namespace Database\Factories;
use App\Models\User;
use Illuminate\Database\Eloquent\Factories\Factory;
class UserFactory extends Factory
{
  protected $model = User::class;
  /**
   * Define the model's default state.
   *
   * @return array
   */
  public function definition()
  {
    return [
      'name' => $this->faker->name()
    ];
  }
}

C:\xampp\htdocs\wayarmy\database\factories\PostFactory.php

<?php
namespace Database\Factories;
use App\Models\Post;
use Illuminate\Database\Eloquent\Factories\Factory;
class PostFactory extends Factory
{
  protected $model = Post::class;
  /**
   * Define the model's default state.
   *
   * @return array
   */
  public function definition()
  {
    return [
      'name' => $this->faker->text(15)
    ];
  }
}

C:\xampp\htdocs\wayarmy\database\seeders\DatabaseSeeder.php

<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
use App\Models\User;
use App\Models\Post;
class DatabaseSeeder extends Seeder
{
  /**
   * Seed the application's database.
   *
   * @return void
   */
  public function run()
  {
    User::factory(10)->create();
    Post::factory(10)->create();
  }
}

C:\xampp\htdocs\wayarmy\app\Models\Post.php

<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class Post extends Model
{
  use HasFactory;
  /**
   * The attributes that are mass assignable.
   *
   * @var array<int, string>
   */
  public $timestamps  = false;
  protected $fillable = [
    'name'
  ];
  /**
   * Get the post's image.
   */
  public function image()
  {
    return $this->morphOne(Image::class, 'imageable');
  }
}

C:\xampp\htdocs\wayarmy\app\Models\Image.php

<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class Image extends Model
{
  use HasFactory;
  public $timestamps  = false;
  protected $fillable = [
    'url',
    'imageable_id',
    'imageable_type'
  ];
  /**
   * Get the parent imageable model (user or post).
   */
  public function imageable()
  {
    return $this->morphTo();
  }
}

C:\xampp\htdocs\wayarmy\database\migrations\2022_11_20_160032_create_images_table.php

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateImagesTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('images', function (Blueprint $table) {
          $table->increments('id');
          $table->string("url");
          $table->integer('imageable_id');
          $table->string('imageable_type');
        });
    }
    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::dropIfExists('images');
    }
}

C:\xampp\htdocs\wayarmy\database\migrations\2014_10_12_000000_create_users_table.php

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateUsersTable extends Migration
{
  /**
   * Run the migrations.
   *
   * @return void
   */
  public function up()
  {
    Schema::create('users', function (Blueprint $table) {
      $table->increments('id');
      $table->string('name');
    });
  }
  /**
   * Reverse the migrations.
   *
   * @return void
   */
  public function down()
  {
    Schema::dropIfExists('users');
  }
}

C:\xampp\htdocs\wayarmy\database\migrations\2022_11_17_164213_create_posts_table.php

<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreatePostsTable extends Migration
{
  /**
   * Run the migrations.
   *
   * @return void
   */
  public function up()
  {
    Schema::create('posts', function (Blueprint $table) {
      $table->increments('id');
      $table->string("name");
    });
  }
  /**
   * Reverse the migrations.
   *
   * @return void
   */
  public function down()
  {
    Schema::dropIfExists('posts');
  }
}

Mẫu 1.2 xây dựng type model App\Models\User

C:\xampp\htdocs\wayarmy\routes\web.php

<?php
use Illuminate\Support\Facades\Route;
use App\Http\Controllers\TestController as TestController;
/*
|--------------------------------------------------------------------------
| Web Routes
|--------------------------------------------------------------------------
|
| Here is where you can register web routes for your application. These
| routes are loaded by the RouteServiceProvider within a group which
| contains the "web" middleware group. Now create something great!
|
*/
Route::get('/', function () {
    return view('welcome');
});
Route::get('test/{id}', [TestController::class,'index'])->name('index');
Route::get('test2/{id}', [TestController::class,'index2'])->name('index2');
Route::get('test3/{id}', [TestController::class,'index3'])->name('index3');
Route::get('test4/{id}', [TestController::class,'index4'])->name('index4');

C:\xampp\htdocs\wayarmy\app\Http\Controllers\TestController.php

<?php
namespace App\Http\Controllers;
use App\Models\User;
use App\Models\Post;
use App\Models\Image;
use Illuminate\Http\Request;
class TestController extends Controller
{
  public function index($id)
  {
    $user = User::find($id);
    $userimage = $user->image;
    echo '<pre>';
    var_export($userimage);
    echo '<pre>';
  }
  public function index2($id)
  {
    $post = Post::find($id);
    $postimage = $post->image;
    echo '<pre>';
    var_export($postimage->url); // your_image
    echo '<pre>';
  }
  public function index3($id)
  {
    $image = new Image;
    $image->url = "your_image";
    $post = Post::find($id);
    $post->image()->save($image);
  }
  public function index4($id)
  {
    $image = new Image;
    $image->url = "your_image_2";
    $user = User::find($id);
    $user->image()->save($image);
  }
}

cùng xem kết quả :) 😒

https://oec.wayarmy.net/test/1

https://oec.wayarmy.net/test2/3

In this laravel 9 polymorphic relationship example, I will discuss about polymorphic relationship in laravel. In this example, I will discuss about laravel polymorphic one to one example. I will discuss about what is polymorphic relationship is and when we need this relationship in the Laravel application.

In this example, we will see polymorphic relationship laravel, laravel polymorphic one to one example, laravel polymorphic migration and laravel save polymorphic relationship. You need to just follow this tutorial to learn the above scenarios.

laravel-9-one-to-one-polymorphic-relationship-example

Polymorphic Relationships in Laravel

In Laravel, a polymorphic relationship allows the child model to belong to more than one type of model using a single association. For example, imagine you are building an application that allows users to share their feedback for posts and videos. In such an application, a Comment model might belong to both the Blog and Video models. Now we know what is polymorphic relationship in laravel. Now we will see when we will use it in our Laravel application.

One To One (Polymorphic) Scenario

Taking the example mentioned above into consideration, we have two entities: Post and User. To allow for images on each of these, we can decide to set up our database like this:

posts
    id - integer
    name - string
 
users
    id - integer
    name - string
 
images
    id - integer
    url - string
    imageable_id - integer
    imageable_type - string

PerlCopy

If we avoid polymorphic relationship schema, then our database schema will look like:

posts:
  id
  title
  content
  
posts_images:
  id
  post_id
  image
  date
  
users:
  id
  name
  
users_images:
  id
  user_id
  image
  date

PHPCopy

But look at that our polymorphic schema, how cool it is. Here, we have three entities: Post, User, and Image. Post can have Image. User can have Image. Let's create our migration like:

Schema::create('posts', function (Blueprint $table) {
    $table->increments('id');
    $table->string('title');
    $table->text('content');
});

Schema::create('users', function (Blueprint $table) {
    $table->increments('id');
    $table->text('name');
});

Schema::create('images', function (Blueprint $table) {
    $table->increments('id');
    $table->morphs(‘commentable’);
    $table->text('image');
    $table->date('date');
});

PHPCopy

Read also: Laravel One To One/HasOne Eloquent Relationship Tutorial

Remember: $table→morphs('commentable') would automatically create two columns for the id and type using the text passed to it, so it will result in commentable_id and commentable_type.

Define One to One Polymorphic Relationship

Now let's define the one to one polymorphic relationship in our model class.

app/Models/User.php

<?php
 
namespace App\Models;
 
use Illuminate\Database\Eloquent\Model;
 
class User extends Model
{
    /**
     * Get the user's image.
     */
    public function image()
    {
        return $this->morphOne(Image::class, 'imageable');
    }
}

PHPCopy

Now define the relationship in the Post model like:

app/Models/Post.php

<?php
 
namespace App\Models;
 
use Illuminate\Database\Eloquent\Model;
 
class Post extends Model
{
    /**
     * Get the post's image.
     */
    public function image()
    {
        return $this->morphOne(Image::class, 'imageable');
    }
}

PHPCopy

Now define the relationship in the Image model like:

app/Models/Image.php

<?php
 
namespace App\Models;
 
use Illuminate\Database\Eloquent\Model;
 
class Image extends Model
{
    /**
     * Get the parent imageable model (user or post).
     */
    public function imageable()
    {
        return $this->morphTo();
    }
}

PHPCopy

To access the image for a User, we can use the image property declared in the model.

App\Http\Controllers\TestController.php

<?php

namespace App\Http\Controllers;

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

class TestController extends Controller
{
    public function index($id)
    {   
        $user = User::find($id);

        $user->image;
    }
}

PHPCopy

For retrieving image on a post:

<?php

namespace App\Http\Controllers;

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

class TestController extends Controller
{
    public function index($id)
    {   
        $post = Post::find($id);

        $post->image;
    }
}

PHPCopy

Save Polymorphic Relationship Data

If we want to save or create polymorphic relationship data then we can follow the below structure:

<?php

namespace App\Http\Controllers;

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

class TestController extends Controller
{
    public function index($id)
    {   
        $post = Post::find($id);

        $image = new Image;
        $image->image = "your_image";
 
        $post->image()->save($image);
    }
}

Last updated

Was this helpful?