ritechoice23/laravel-chat-engine
Laravel Chat Engine adds drop-in chat and messaging to Laravel apps, with conversations, participants, messages, and real-time updates so you can ship private or group messaging without building the backend yourself.
This is the first tagged release (1.0.0), and the only merged change is a Dependabot bump of dependabot/fetch-metadata in CI. There is no application-facing changelog to reconcile against, so treat 1.0.0 as the baseline API rather than an upgrade from a prior version.
Minimal path to a working prototype:
composer require ritechoice23/laravel-chat-engine
php artisan vendor:publish --provider="Ritechoice23\ChatEngine\ChatEngineServiceProvider"
php artisan migrate
Then, in order:
User, Team, Bot can all join) and whether messages are soft-deletable before you build UI on top of them.HasChats-style trait; the README's installation section is the authority on the exact name.Don't start with broadcasting, attachments, or read receipts. Get the synchronous create-conversation/send-message path working first; everything else is additive and much harder to debug when the foundation is unproven.
Resolve the engine from the container, don't instantiate it. Chat packages typically bind a manager or service in the provider. Type-hint the contract rather than new-ing a concrete class, so you can swap the implementation in tests and so config-driven model overrides actually take effect.
Wrap multi-step operations in your own application service. Creating a conversation, attaching participants, and posting the first message is a three-write operation. Putting it behind App\Services\StartConversation rather than calling the package fluent API from a controller gives you one place to add transactions, domain events, and authorization — and one place to change if the package API shifts in a later 1.x.
Authorize at the boundary, not inside the package. Treat the package as a persistence layer. Add a ConversationPolicy and check participation yourself before allowing reads or writes. Do not assume the package enforces "only participants can post" — verify it explicitly in a test, because that assumption is a security bug when it's wrong.
Drive real-time through Laravel events. The idiomatic integration is: your service persists the message, then dispatches a broadcast event on a private channel keyed by conversation ID (private-conversation.{id}). Keep the broadcast payload small — an ID plus a rendered fragment — and let the frontend refetch. This avoids coupling your JS to the package's internal serialization.
Use model factories and a test helper for setup. Chat features generate a lot of fixture noise. Write a Conversation::factory() helper or a tests/Support/ChatScenario.php that spins up N users in a conversation with M messages. Every subsequent test gets dramatically cheaper.
Prefer scoped queries over loading relationships wholesale. Message tables grow fast and unboundedly. Always paginate (cursor pagination is a better fit than offset for a chat feed), always constrain by conversation, and never ->with('messages') on a conversation list endpoint.
Integration tip for notifications: rather than duplicating recipient logic, derive "who to notify" from the conversation's participants at send time, and dispatch a Laravel notification from your own listener. This keeps the package out of your notification preferences/unsubscribe logic, which is inevitably app-specific.
^1.0 and read the changelog on every minor release; a 1.x minor is permitted to add features and may add required config keys.User model's morph alias must be stable. Adding a Relation::enforceMorphMap() later will orphan existing rows unless you write a data migration. Also watch for missing indexes on (participant_type, participant_id) and (conversation_id, created_at) — add them yourself if the package's migrations don't.php artisan config:clear. If conversation creation silently no-ops, verify the participant model actually uses the required trait before digging into the package source.BROADCAST_CONNECTION, that the private channel authorization callback in routes/channels.php permits the participant, and that the queue worker is actually running — broadcast events are frequently queued and will sit silently in the jobs table otherwise.composer update may pull a new tag with no functional change — keep the lockfile diff reviewable by upgrading deliberately rather than running composer update blind in CI.How can I help you explore Laravel packages today?