---
title: "Domain events — Events for Laravel | Roundly"
description: "42 after-commit domain events for events, venues, ticket types, RSVPs, holds, payments, check-ins, co-hosts and invitations — payloads and listening."
url: https://roundly-consulting.com/open-source/docs/events-for-laravel/domain-events
language: en
---

[All packages](https://roundly-consulting.com/open-source.md)

[Events for Laravel](https://roundly-consulting.com/open-source/docs/events-for-laravel.md)

# Domain events

Every event is a final readonly class in RoundlyConsulting\\Events\\Events, implements ShouldDispatchAfterCommit — a rolled-back write dispatches nothing — and holds models. None broadcasts by itself; if you broadcast from a listener, render references, never class names.

```php
use Illuminate\Support\Facades\Event as EventBus;   // Models\Event shadows Laravel's facade name
use RoundlyConsulting\Events\Events\AttendeeCheckedIn;
use RoundlyConsulting\Events\Events\RsvpCancelled;

EventBus::listen(RsvpCancelled::class, function (RsvpCancelled $cancelled): void {
    if ($cancelled->wasPaid) {
        // refund $cancelled->rsvp->payment_reference at your provider
    }
});

EventBus::listen(AttendeeCheckedIn::class, function (AttendeeCheckedIn $in): void {
    logger()->info('door scan', ['event' => $in->result->rsvp->event->uuid, 'first' => $in->result->firstCheckIn]);
});
```

Import Laravel’s facade under another name — the package’s Models\\Event shadows Event. Listeners see the committed rows.

| Event | Payload | When |
| --- | --- | --- |
| `EventCreated` | `Event $event, ?Model $actor` | Created (a draft). |
| `EventUpdated` | `Event $event, list<string> $changed, ?Model $actor, bool $silent` | Fields changed (category, labels for tag changes). |
| `EventDeleted / EventRestored` | `Event $event, ?Model $actor (+ bool $force)` | — |
| `EventPublished / EventUnpublished / EventCompleted` | `Event $event, ?Model $actor` | — |
| `EventPostponed / EventCancelled` | `Event $event, ?string $reason, ?Model $actor, bool $silent (+ list $releasedHolds)` | releasedHolds: the RSVPs whose holds the cancellation released. |
| `EventRescheduled` | `Event $event, CarbonImmutable $previousStartsAt, ?string $reason, ?Model $actor, bool $silent` | — |
| `EventMovedOnline` | `Event $event, ?Model $actor, bool $silent` | An announced event moved online (never a draft). |
| `EventStatusChanged` | `Event $event, ?string $transition, $from, $to, ?Model $actor, bool $silent` | Every status change. |
| `OrganizerTransferred` | `Event $event, Model $from, Model $to, ?Model $actor` | — |
| `PosterChanged` | `Event $event, ?Media $poster, ?Model $actor` | Set or removed. |
| `VenueCreated / VenueDeleted / VenueRestored · VenueUpdated` | `Venue $venue, ?Model $actor (+ list<string> $changed)` | — |
| `VenueGeocoded / VenueGeocodingFailed` | `Venue $venue` | — |
| `TierCreated / TierDeleted / TierRestored · TierUpdated` | `AdmissionTier $tier, ?Model $actor (+ list<string> $changed)` | — |
| `RsvpChanged` | `Rsvp $rsvp, ?RsvpStatus $from, ?Model $actor` | Every RSVP status change. |
| `AttendeeConfirmed` | `Rsvp $rsvp, bool $late` | Entered going (late: a payment after the hold expired). |
| `AttendeeWaitlisted / AttendeePromoted / RsvpHoldExpired` | `Rsvp $rsvp` | — |
| `RsvpHeld` | `Rsvp $rsvp, Money $amount, ?PaymentRequest $paymentRequest` | A paid seat is held — with a checkout the package stored, or none (collect another way). |
| `RsvpPaymentRequestDiscarded` | `Rsvp $rsvp, PaymentRequest $paymentRequest` | A checkout for a hold that changed meanwhile — void it at your provider. |
| `RsvpPaymentRequestFailed` | `Rsvp $rsvp, Throwable $exception` | The collector threw. |
| `RsvpCancelled` | `Rsvp $rsvp, bool $wasPaid` | Someone with seats left — refund the paid ones. |
| `AttendeeCheckedIn · CheckInUndone` | `CheckInResult $result · Rsvp $rsvp, ?Model $actor` | A first scan or a manual check-in · an undo. |
| `CoHostAdded / CoHostRemoved` | `Event $event, Model $host, ?Model $actor` | — |
| `InvitationSent` | `EventInvitation $invitation, string $token, ?string $message` | Sent or re-sent — and again, with a fresh token, for each pending invitation of a draft when it is published. Keep the token out of logs; encrypt queued listeners. |
| `InvitationAccepted · InvitationDeclined · InvitationRevoked` | `EventInvitation $invitation (+ Rsvp $rsvp · + ?Model $actor)` | — |
| `RemindersDispatched` | `Event $event, string $offset, int $recipients` | The sweep sent one reminder offset. |

- The package listens to lifecycle’s LifecycleTransitioning and LifecycleTransitioned — the sequence, the cancellation effects, the phase events above — and to its own events for the notices. Fake only the events you assert; Testing explains why.
- InvitationSent carries the plain token: keep it out of logs and encrypt queued listeners (ShouldBeEncrypted).

## Show your open-source love

This package is free and MIT-licensed. If it saves you time, a one-off donation or a Patreon membership keeps it maintained, tested and documented.

[More ways to support, including crypto](https://roundly-consulting.com/support-us.md)

By donating, you agree to our [donation terms](https://roundly-consulting.com/donation-terms.md).

[Support our open source work (opens in a new tab)](https://donate.stripe.com/dRmeVe8FX5PF1Qd9pXcEw00) [Join us on Patreon (opens in a new tab)](https://www.patreon.com/cw/roundly)

## Want this built into your product?

We integrate our packages into custom Laravel and AI builds. Tell us what you're working on and we'll reply within 48 hours.

[Get a quote in 48 hours](https://roundly-consulting.com/contact.md) [Browse all packages](https://roundly-consulting.com/open-source/docs/events-for-laravel.md)
