Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Message Bus Laravel Package

dlakomski/message-bus

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup in Laravel

  1. Install the Package

    composer require dlakomski/message-bus
    

    (Note: The package is a fork of simplebus/message-bus with no direct Laravel integration, so manual setup is required.)

  2. Define a Message Interface

    // app/Domain/Messages/ExampleMessage.php
    namespace App\Domain\Messages;
    
    interface ExampleMessage {}
    
  3. Create a Message Handler

    // app/Domain/Handlers/ExampleMessageHandler.php
    namespace App\Domain\Handlers;
    
    use App\Domain\Messages\ExampleMessage;
    use SimpleBus\Message\Bus\MessageBus;
    
    class ExampleMessageHandler
    {
        public function __invoke(ExampleMessage $message): void
        {
            // Handle the message
        }
    }
    
  4. Register the Bus in Laravel

    // config/app.php (Service Providers)
    SimpleBus\MessageBus\MessageBus::class => function ($app) {
        $bus = new \SimpleBus\MessageBus\MessageBus(
            new \SimpleBus\MessageBus\Middleware\LogMessagesMiddleware(),
            new \SimpleBus\MessageBus\Middleware\HandleMessageMiddleware(
                new \SimpleBus\MessageBus\Middleware\CallHandlerMiddleware(
                    new \SimpleBus\MessageBus\Middleware\CreateMessageFromEnvelopeMiddleware()
                )
            )
        );
        return $bus;
    },
    
  5. Dispatch a Message

    use App\Domain\Messages\ExampleMessage;
    use SimpleBus\Message\Bus\MessageBus;
    
    class SomeService
    {
        public function __construct(private MessageBus $bus) {}
    
        public function triggerExample()
        {
            $this->bus->dispatch(new class implements ExampleMessage {});
        }
    }
    

Implementation Patterns

1. Command Bus Workflow

  • Use Case: Synchronous, one-way operations (e.g., CreateUserCommand).
  • Pattern:
    // Define Command
    interface CreateUserCommand {}
    
    // Handler
    class CreateUserHandler {
        public function __invoke(CreateUserCommand $command) {
            // Logic here
        }
    }
    
    // Dispatch
    $bus->dispatch(new CreateUserCommand());
    

2. Event Bus Workflow

  • Use Case: Asynchronous, publish-subscribe (e.g., UserCreatedEvent).
  • Pattern:
    // Define Event
    interface UserCreatedEvent {}
    
    // Subscriber
    class UserCreatedSubscriber {
        public function __invoke(UserCreatedEvent $event) {
            // Logic here
        }
    }
    
    // Dispatch (fire-and-forget)
    $bus->dispatch(new UserCreatedEvent());
    

3. Middleware Integration

  • Logging Middleware:
    $bus = new \SimpleBus\MessageBus\MessageBus(
        new \SimpleBus\MessageBus\Middleware\LogMessagesMiddleware(),
        // ... other middleware
    );
    
  • Custom Middleware:
    class ValidateMessageMiddleware {
        public function __invoke($message, callable $next) {
            if (!$this->isValid($message)) {
                throw new \RuntimeException("Invalid message");
            }
            return $next($message);
        }
    }
    

4. Dependency Injection

  • Laravel Service Container:
    $this->app->bind(MessageBus::class, function ($app) {
        return new MessageBus(
            new \SimpleBus\MessageBus\Middleware\HandleMessageMiddleware(
                new \SimpleBus\MessageBus\Middleware\CallHandlerMiddleware(
                    new \SimpleBus\MessageBus\Middleware\CreateMessageFromEnvelopeMiddleware()
                )
            )
        );
    });
    

5. Grouping Handlers

  • Use SimpleBus\MessageBus\Middleware\RouteMessagesToHandlersMiddleware to route messages to specific handlers:
    $bus = new MessageBus(
        new RouteMessagesToHandlersMiddleware([
            ExampleMessage::class => [new ExampleMessageHandler()],
        ]),
        // ... other middleware
    );
    

Gotchas and Tips

1. Middleware Order Matters

  • Issue: Incorrect middleware order can break message handling.
  • Fix: Follow the SimpleBus middleware stack:
    LogMessagesMiddleware → HandleMessageMiddleware → CallHandlerMiddleware → CreateMessageFromEnvelopeMiddleware
    
  • Example:
    $bus = new MessageBus(
        new LogMessagesMiddleware(), // Logs before/after
        new HandleMessageMiddleware(
            new CallHandlerMiddleware(
                new CreateMessageFromEnvelopeMiddleware()
            )
        )
    );
    

2. Exception Handling

  • Gotcha: By default, unhandled exceptions in handlers do not stop the bus (since v1.0.1).
  • Tip: Add a middleware to handle failures globally:
    class HandleExceptionsMiddleware {
        public function __invoke($message, callable $next) {
            try {
                return $next($message);
            } catch (\Throwable $e) {
                \Log::error("Message failed: {$e->getMessage()}");
                throw $e; // Re-throw or handle silently
            }
        }
    }
    

3. Message Validation

  • Gotcha: No built-in validation for message payloads.
  • Tip: Use a middleware to validate messages:
    class ValidateMessageMiddleware {
        public function __invoke($message, callable $next) {
            if (!method_exists($message, 'validate')) {
                throw new \RuntimeException("Message must implement validation");
            }
            $message->validate();
            return $next($message);
        }
    }
    

4. Performance Considerations

  • Gotcha: Middleware adds overhead. Avoid unnecessary middleware in high-throughput systems.
  • Tip: For async buses (e.g., queues), use SimpleBus\MessageBus\Middleware\AsyncMiddleware:
    $bus = new MessageBus(
        new AsyncMiddleware(new \Enqueue\Client()),
        // ... other middleware
    );
    

5. Testing

  • Tip: Mock the bus in tests:
    $mockBus = Mockery::mock(MessageBus::class);
    $mockBus->shouldReceive('dispatch')->once();
    $this->app->instance(MessageBus::class, $mockBus);
    
  • Tip: Use SimpleBus\MessageBus\Test\MessageBusTestCase for assertions:
    $this->bus->shouldHaveDispatched(ExampleMessage::class);
    

6. Laravel-Specific Quirks

  • Gotcha: No built-in queue integration (unlike laravel-queue).
  • Tip: Combine with spatie/laravel-queueable-messages for queue support:
    composer require spatie/laravel-queueable-messages
    
    use Spatie\QueueableMessages\QueueableMessageBus;
    
    $queueableBus = new QueueableMessageBus($bus, $this->app['queue']);
    

7. Debugging

  • Tip: Enable logging middleware to trace message flow:
    $bus = new MessageBus(
        new LogMessagesMiddleware(\Monolog\Logger::create('message_bus')),
        // ...
    );
    
  • Tip: Use SimpleBus\MessageBus\Middleware\DebugMiddleware for dev environments:
    $bus = new MessageBus(
        new DebugMiddleware(),
        // ...
    );
    

8. Extending the Package

  • Tip: Create custom message buses by extending SimpleBus\MessageBus\MessageBus:
    class CustomMessageBus extends \SimpleBus\MessageBus\MessageBus {
        public function dispatchWithRetry($message, int $retries = 3) {
            // Custom logic
        }
    }
    
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
terminal42/code-quality-tools
codifyo/ts-generator-bundle
andydefer/laravel-cluster
testo/fiber
mintobit/jobqueue
a4sex/maintenance-bundle
a4sex/entity-date-update
a4sex/client-identifier
a4sex/base-utilites
a4sex/key-value-storage
a4sex/micro-status
chilldev/dependency-injection-extra
datinglibre/datinglibre-app-api
biberltd/corebundle
bricre/symfony-bundle-test
biberltd/logbundle
dominium/http-adapter-bundle
dominium/google-analytics
a4sex/auto-clean-entity
christhompsontldr/laravel-inky