Add freshOr and freshOrFail methods to Eloquent models #61180
Replies: 1 comment 2 replies
|
A small application-level helper can cover this today while the framework API is discussed: trait RefreshesModels
{
public function freshOrFail(array|string $with = []): static
{
$fresh = $this->fresh($with);
if ($fresh === null) {
throw (new ModelNotFoundException)->setModel(static::class, $this->getKey());
}
return $fresh;
}
}The important detail for the proposed framework method is to return the new instance from If this becomes a core API, the tests should cover: a deleted model throwing with the concrete model class/key, the array and variadic relationship forms, and a successful call returning a distinct fresh instance with only the requested relations. The existing |
Uh oh!
There was an error while loading. Please reload this page.
Eloquent's
fresh()method returns a new model instance ornullwhen the model no longer exists:This requires repeating the same null handling whenever a caller requires the model to still exist.
Eloquent query builders already provide methods such as
firstOr,firstOrFail,findOr, andfindOrFail. It would be useful forfresh()to provide the same alternatives:Broadcasting example
Broadcast events are one place where this is useful.
Without
#[WithoutRelations], the same event may receive models with different relationships already loaded at different dispatch sites:If the event returns the model directly from
broadcastWith():Laravel serializes the loaded relationships with the queued event. The same event can therefore include
authorwhen dispatched from one place andcommentswhen dispatched from another.Adding
#[WithoutRelations]prevents relationships loaded before dispatch from being serialized. However, this does not cover relationships loaded while the broadcast event is being handled because Laravel invokesbroadcastOn()beforebroadcastWith().For example,
broadcastOn()can load a relationship that later affects the payload returned bybroadcastWith():Because
broadcastOn()loadedauthor, the payload now unexpectedly contains the relationship:{ "article": { "id": 1, "title": "Laravel Broadcasting", "author": { "id": 10, "name": "Taylor" } } }The event can retrieve a clean model in
broadcastWith(), but it must repeat the null check:With
freshOrFail(), this becomes:Proposed API
The relationship arguments support the same array and variadic forms as
fresh():Benefits
fresh()null checks.firstOr,firstOrFail,findOr, andfindOrFail.fresh()relationship-loading syntax.ModelNotFoundExceptionwith the model class and key.fresh()unchanged and fully backwards compatible.This keeps the model-loading requirements local to the code that produces the payload instead of relying on the state of the model passed by its caller.
Related references
#9835
All reactions