it feels like I'm paying for this computation over and over - plus it triggers parent loads
It feels to me too.
Besides that, you get unpredictable problems if parent is deleted or moved somewhere in hierarchy, your paths turn into a mess.
Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.
I have a Page model without a path column.
The path is derived from the slug and the nested parent_id hierarchy, and it’s rebuilt every time it’s accessed.
/about/team/history
slug: "history"
parent slug: "team"
parent slug: "about"
I've enabled strict models, so I get lazy-loading exceptions unless I eager-load parents. The problem is:
with('parent.parent.parent...'), but that's brittle.Model::automaticallyEagerLoadRelationships(), but I'm unsure if that's a good idea here.public function parent(): BelongsTo
{
return $this->belongsTo(self::class);
}
public function path(): string
{
$segments = [];
$page = $this;
while ($page) {
$segments[] = $page->slug;
$page = $page->parent;
}
$segments = array_reverse($segments);
return '/' . ltrim(implode('/', $segments), '/');
}
This works, but I call path() in many places (Search queries, Livewire components, etc.), so it feels like I'm paying for this computation over and over - plus it triggers parent loads.
Is there a Laravel "industry standard" for this?
Should I stick with on-the-fly path building and recursive eager loading, or is the recommended approach to add a path column and keep it in sync with slug & parent_id (for example with an Observer)?
Or would a package like https://github.com/staudenmeir/laravel-adjacency-list or https://github.com/lazychaser/laravel-nestedset be the best bet?
If anyone has had a similar issue, I'd love to hear the different solutions you've come up with.
Please or to participate in this conversation.