Bird
Raised Fist0
Laravelframework~10 mins

Polymorphic relationships in Laravel - Step-by-Step Execution

Choose your learning style10 modes available
Concept Flow - Polymorphic relationships
Define polymorphic relation in Model A
↓
Define polymorphic relation in Model B
↓
Create tables with morph columns
↓
Save related models
↓
Query polymorphic relation
↓
Access related models polymorphically
This flow shows how Laravel sets up and uses polymorphic relationships by defining relations, creating tables, saving data, and querying related models.
Execution Sample
Laravel
class Comment extends Model {
  public function commentable() {
    return $this->morphTo();
  }
}

class Post extends Model {
  public function comments() {
    return $this->morphMany(Comment::class, 'commentable');
  }
}
Defines a polymorphic relation where comments can belong to multiple models like posts or videos.
Execution Table
StepActionModel StateDatabase ActionResult
1Define Comment model with morphTo relationComment model ready with commentable()No DB actionRelation method set
2Define Post model with morphMany relationPost model ready with comments()No DB actionRelation method set
3Create posts table and comments table with commentable_id and commentable_typeTables createdDB tables createdTables ready for polymorphic data
4Create Post instance and savePost instance saved with id=1Insert into postsPost record created
5Create Comment instance and associate with PostComment instance with commentable_id=1, commentable_type='App\Models\Post'Insert into commentsComment linked to Post
6Query Post commentsPost model queriedSelect comments where commentable_id=1 and commentable_type='App\Models\Post'Returns comments for Post
7Query Comment's parentComment model queriedSelect model where id=commentable_id and type=commentable_typeReturns Post model
8ExitNo further actionsNo DB actionPolymorphic relation works bidirectionally
💡 All polymorphic relations defined, data saved, and queries return expected related models.
Variable Tracker
VariableStartAfter Step 4After Step 5After Step 6Final
Post instancenullPost{id=1}Post{id=1}Post{id=1}Post{id=1}
Comment instancenullnullComment{commentable_id=1, commentable_type='App\Models\Post'}Comment{...}Comment{...}
comments collectionemptyemptyempty[Comment{...}][Comment{...}]
commentable parentnullnullnullnullPost{id=1}
Key Moments - 3 Insights
Why do we need both commentable_id and commentable_type in the comments table?
Because polymorphic relations can link to different models, commentable_type stores the model class, and commentable_id stores the record id. See execution_table step 3 and 5.
How does Laravel know which model a comment belongs to when querying?
Laravel uses commentable_type to know the model class and commentable_id to find the record. This is shown in execution_table step 7.
Can a comment belong to both a Post and a Video at the same time?
No, each comment belongs to one model instance at a time, but the relation can point to different model types. This is clear from the morphTo relation in step 1.
Visual Quiz - 3 Questions
Test your understanding
Look at the execution table, what is the commentable_type value stored in the Comment instance after step 5?
A'commentable'
B'App\Models\Post'
C'Post'
D1
💡 Hint
Check the 'Model State' column in step 5 of the execution_table.
At which step does the database insert the comment linked to the post?
AStep 6
BStep 4
CStep 5
DStep 3
💡 Hint
Look for the step where commentable_id and commentable_type are set and inserted.
If we add a Video model with comments, which part of the execution flow changes?
AStep 2: Define morphMany relation in Video model
BStep 4: Create posts table
CStep 7: Query Comment's parent will fail
DStep 3: Remove commentable_type column
💡 Hint
Adding a new polymorphic model requires defining the relation method like in step 2.
Concept Snapshot
Polymorphic relationships let one model belong to multiple other models using a single association.
Use morphTo() in the child model and morphMany() or morphOne() in parent models.
Database tables need 'morph' columns: *_id and *_type to store related model info.
This allows flexible relations like comments belonging to posts or videos.
Querying uses these columns to fetch related models dynamically.
Full Transcript
Polymorphic relationships in Laravel allow a model to belong to more than one other model on a single association. The child model uses morphTo() to define the relation, while parent models use morphMany() or morphOne() to define their side. The database tables include columns like commentable_id and commentable_type to store the related model's id and class name. When saving a comment linked to a post, Laravel stores the post's id and class in these columns. Queries use this information to retrieve related models dynamically. This setup enables flexible relations such as comments belonging to posts or videos without needing separate foreign keys for each model type.

Practice

(1/5)
1. What is the main purpose of polymorphic relationships in Laravel?
easy
A. To allow a model to belong to more than one other model on a single association
B. To create many-to-many relationships between two models
C. To enforce strict foreign key constraints in the database
D. To automatically generate database migrations

Solution

  1. Step 1: Understand polymorphic relationships

    Polymorphic relationships allow a model to belong to multiple other models using a single association.
  2. Step 2: Compare with other relationship types

    Unlike many-to-many or one-to-many, polymorphic lets one model relate to different models without separate foreign keys.
  3. Final Answer:

    To allow a model to belong to more than one other model on a single association -> Option A
  4. Quick Check:

    Polymorphic relationships = single association to multiple models [OK]
Hint: Polymorphic = one model relates to many different models [OK]
Common Mistakes:
  • Confusing polymorphic with many-to-many relationships
  • Thinking it automatically creates migrations
  • Assuming it enforces database constraints
2. Which method should you use in the related model to define a polymorphic relationship?
easy
A. morphTo()
B. hasMany()
C. belongsToMany()
D. morphMany()

Solution

  1. Step 1: Identify the related model method

    The related model uses morphTo() to define the polymorphic inverse relationship.
  2. Step 2: Differentiate from owning model methods

    Owning models use morphMany(), but the related model uses morphTo().
  3. Final Answer:

    morphTo() -> Option A
  4. Quick Check:

    Related model uses morphTo() [OK]
Hint: Related model always uses morphTo() for polymorphic [OK]
Common Mistakes:
  • Using morphMany() in the related model
  • Confusing belongsToMany() with polymorphic
  • Using hasMany() instead of morphTo()
3. Given the following code, what will $comment->commentable->name output?
class Comment extends Model {
  public function commentable() {
    return $this->morphTo();
  }
}

$comment = Comment::find(1);

Assuming the comment belongs to a Post with name = 'Laravel Tips'.
medium
A. Error: Undefined property 'name'
B. 'Laravel Tips'
C. null
D. 'Comment'

Solution

  1. Step 1: Understand morphTo() behavior

    The commentable() method returns the related model instance, here a Post.
  2. Step 2: Access the related model's property

    Accessing name on the Post model returns 'Laravel Tips'.
  3. Final Answer:

    'Laravel Tips' -> Option B
  4. Quick Check:

    commentable->name = 'Laravel Tips' [OK]
Hint: morphTo() returns related model instance [OK]
Common Mistakes:
  • Expecting null if not eager loaded
  • Confusing property with method call
  • Assuming error without checking model relation
4. What is wrong with this polymorphic relationship definition?
class Image extends Model {
  public function imageable() {
    return $this->morphMany();
  }
}
medium
A. morphMany() requires parameters but none are given
B. No relationship method is needed in Image model
C. The method name should be morphable()
D. The method should be morphTo(), not morphMany()

Solution

  1. Step 1: Identify the model role

    Image is the related model, so it should use morphTo() for polymorphic inverse.
  2. Step 2: Check method used

    morphMany() is for owning models, not related models.
  3. Final Answer:

    The method should be morphTo(), not morphMany() -> Option D
  4. Quick Check:

    Related model uses morphTo() [OK]
Hint: Related model must use morphTo(), not morphMany() [OK]
Common Mistakes:
  • Using morphMany() without parameters
  • Wrong method name for polymorphic inverse
  • Thinking no method is needed
5. You want to create a polymorphic relationship where both Post and Video models can have many Comment models. Which of the following is the correct way to define the relationship in the Post model?
hard
A. public function comments() { return $this->belongsToMany(Comment::class); }
B. public function comments() { return $this->hasMany(Comment::class); }
C. public function comments() { return $this->morphMany(Comment::class, 'commentable'); }
D. public function comments() { return $this->morphTo(Comment::class, 'commentable'); }

Solution

  1. Step 1: Identify owning model relationship

    Post owns many comments via polymorphic relation, so use morphMany().
  2. Step 2: Use correct parameters

    morphMany() requires the related model class and the polymorphic name 'commentable'.
  3. Final Answer:

    public function comments() { return $this->morphMany(Comment::class, 'commentable'); } -> Option C
  4. Quick Check:

    Owning model uses morphMany() with polymorphic name [OK]
Hint: Owning model uses morphMany() with polymorphic name [OK]
Common Mistakes:
  • Using hasMany() instead of morphMany()
  • Using morphTo() in owning model
  • Using belongsToMany() for polymorphic
Recommended

Ready to prove it?

Pass the test and this pattern moves unknown strong while earning +1 Grip toward your certificate.

10 questions~5 mineasy hard