Laravel Eloquent HasMany Recursive Relationship with Subitems
Today I’m going to show how to view items and deep level sub-items. Let’s get started:
Table of Contents
Database Migration
Create a model, migrations and controller using this command:
php artisan make:model Item -mc
Open the newly created migration file from database/migrations folder and update up()
method:
public function up()
{
Schema::create('items', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->unsignedBigInteger('parent_id')->nullable();
$table->foreign('parent_id')->references('id')->on('items');
$table->timestamps();
});
}
Now migrate the database:
php artisan migrate
Eloquent Model and Relationships
We’re going to add two relations in app/Item.php model. One for displaying level one items and another one for showing recursive items:
class Item extends Model
{
// return one level of child items
public function items()
{
return $this->hasMany(Item::class, 'parent_id');
}
// recursive relationship
public function childItems()
{
return $this->hasMany(Item::class, 'parent_id')->with('items');
}
}
Modify Controller and Define Route
Open ItemController from app\Http\Controllers and add the index()
method:
<?php
namespace App\Http\Controllers;
use App\Item;
use Illuminate\Http\Request;
class ItemController extends Controller
{
public function index() {
$items = Item::whereNull('parent_id')
->with('childItems')
->get();
return view('items', compact('items'));
}
}
Now define a route in routes/web.php for the index()
method:
Route::get('items', '[email protected]');
Create Views
Go to resources/views folder and create 2 files named items.blade.php and sub_items.blade.php. Then paste these codes:
<ul>
@if(count($items) > 0)
@foreach ($items as $item)
<li>{{ $item->name }}</li>
<ul>
@if(count($item->childItems))
@foreach ($item->childItems as $childItems)
@include('sub_items', ['sub_items' => $childItems])
@endforeach
@endif
</ul>
@endforeach
@endif
</ul>
<li>{{ $sub_items->name }}</li>
@if ($sub_items->items)
<ul>
@if(count($sub_items->items) > 0)
@foreach ($sub_items->items as $childItems)
@include('sub_items', ['sub_items' => $childItems])
@endforeach
@endif
</ul>
@endif
Now insert some data into items tables and run the project. Then visit http://localhost:8000/items
route to see the output. Here’s my one:

Comment
Preview may take a few seconds to load.
Markdown Basics
Below you will find some common used markdown syntax. For a deeper dive in Markdown check out this Cheat Sheet
Bold & Italic
Italics *asterisks*
Bold **double asterisks**
Code
Inline Code
`backtick`Code Block```
Three back ticks and then enter your code blocks here.
```
Headers
# This is a Heading 1
## This is a Heading 2
### This is a Heading 3
Quotes
> type a greater than sign and start typing your quote.
Links
You can add links by adding text inside of [] and the link inside of (), like so:
Lists
To add a numbered list you can simply start with a number and a ., like so:
1. The first item in my list
For an unordered list, you can add a dash -, like so:
- The start of my list
Images
You can add images by selecting the image icon, which will upload and add an image to the editor, or you can manually add the image by adding an exclamation !, followed by the alt text inside of [], and the image URL inside of (), like so:
Dividers
To add a divider you can add three dashes or three asterisks:
--- or ***

Comments (0)