Skip to content

Lifecycle Callbacks

Run entity methods around persistence, update, removal, and hydration events.

#[PrePersist]
public function onPrePersist(): void
{
}
#[PostPersist]
public function onPostPersist(): void
{
}

Available callback attributes:

#[PrePersist]

#[PostPersist]

#[PreUpdate]

#[PostUpdate]

#[PreRemove]

#[PostRemove]

#[PostLoad]

Timestamps

Set created_at in #[PrePersist] and updated_at in #[PreUpdate]. There is no built-in auto-timestamp attribute — this is done by hand in the callback, as in the example below.

Auditing

Write an audit-log record in #[PostPersist] / #[PostUpdate] / #[PostRemove], once the write is known to have succeeded.

Validation

Reject invalid state in #[PrePersist] / #[PreUpdate] by throwing — the throw prevents the write (see pitfalls below).

Normalization

Trim, cast, or recompute derived fields in #[PostLoad] right after hydration, so every code path sees the same shape.

Soft-delete bookkeeping

Stamp the soft-delete marker in #[PreRemove] for entities that don’t rely solely on #[SoftDeleteable]’s own handling.

#[PreUpdate]
public function onPreUpdate(): void
{
$this->updated_at = self::now();
}
#[PostLoad]
public function onPostLoad(): void
{
$this->record('PostLoad');
}