PHP
Implementing Eloquent Polymorphic Relationships
Understand and implement polymorphic relationships in Laravel Eloquent, allowing a single model to belong to multiple different models on a single association.
// In your migration for comments/tags (example: comments table)
Schema::create('comments', function (Blueprint $table) {
$table->id();
$table->text('body');
$table->morphTo('commentable'); // Adds commentable_id and commentable_type
$table->timestamps();
});
// In your App\Models\Comment model
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Comment extends Model
{
/**
* Get the parent commentable model (post or video).
*/
public function commentable()
{
return $this->morphTo();
}
}
// In your App\Models\Post model
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Post extends Model
{
/**
* Get all of the post's comments.
*/
public function comments()
{
return $this->morphMany(Comment::class, 'commentable');
}
}
// In your App\Models\Video model
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Video extends Model
{
/**
* Get all of the video's comments.
*/
public function comments()
{
return $this->morphMany(Comment::class, 'commentable');
}
}
// Usage example
$post = App\Models\Post::find(1);
foreach ($post->comments as $comment) {
echo $comment->body;
}
$video = App\Models\Video::find(1);
$comment = $video->comments()->create(['body' => 'Great video!']);
$comment = App\Models\Comment::find(1);
$commentable = $comment->commentable; // Can be a Post or a Video instance
How it works: Polymorphic relationships allow a model to belong to more than one other model on a single association. For example, a `Comment` model might belong to either a `Post` or a `Video`. This is achieved using `morphTo()` on the child model and `morphMany()` (or `morphOne()`) on the parent models. The `morphTo` method automatically creates `_id` and `_type` columns in the migration, storing the ID of the related model and its class name.