Laravel listener listen to multiple event

Stefan Bogdanescu

Founder & Senior Architect · 2026-06-29

Laravel Company

Mastering Multiple Events: Handling Diverse Information in Laravel Listeners

When working with Laravel's Event system, understanding how listeners interact with the event payload is crucial. As demonstrated by the documentation on Laravel Events, a listener receives an instance of the event, allowing it to access data passed from the event source (like $event->food).

However, a common architectural challenge arises when a single listener needs to react to multiple, distinct events, such as FoodWasPurchased and DrinksWasPurchased. The original approach suggested—using an if/elseif block inside the handle method—is functional but often leads to bloated, tightly coupled code.

As senior developers, our goal isn't just making the code work, but making it maintainable, scalable, and adhering to SOLID principles. This post explores why a direct conditional check is often an anti-pattern and presents better, more robust architectural solutions for handling multiple events in Laravel.

The Pitfall of Conditional Logic in Listeners

Consider a listener trying to manage inventory or notifications based on what triggered the event:

php
// Example of the less ideal approach
class BillListener
{
    public function handle($event)
    {
        if (isset($event->food)) {
            // Logic specific to food purchase
            $this->processFoodOrder($event->food);
        } elseif (isset($event->drinks)) {
            // Logic specific to drink purchase
            $this->processDrinkOrder($event->drinks);
        }
    }
}

While this works, it introduces several issues:

  1. Violation of SRP (Single Responsibility Principle): The listener is now responsible for knowing about the internal structure of all related events and deciding which path to take. If a new event (ItemsWereAdded) is introduced, this method must be modified, increasing coupling.
  2. Readability: As more conditions are added, the handler becomes a complex chain of checks, making debugging difficult.
  3. Maintainability: The listener becomes brittle. Any change to the structure of the event objects requires corresponding changes in every listening class.

Best Practice: Decoupling with Dedicated Listeners

The superior architectural approach when dealing with multiple distinct events is to embrace decoupling. Instead of forcing one listener to be a general dispatcher, we should ensure each listener has a single, focused responsibility—a concept central to clean Laravel design.

If the logic for processing food and the logic for processing drinks are fundamentally different, they should reside in separate classes.

Solution 1: Separate Listeners (The Cleanest Approach)

The most robust solution is to create dedicated listeners for each event type. This adheres to the principle of "one listener, one job," making the system highly scalable.

Example Implementation:

php
// Listener for Food Events
class FoodPurchasedListener
{
    public function handle(FoodWasPurchased $event)
    {
        // Logic specific to food purchase, tightly coupled only to this event.
        $this->processFoodOrder($event->food);
    }
}

// Listener for Drink Events
class DrinksPurchasedListener
{
    public function handle(DrinksWasPurchased $event)
    {
        // Logic specific to drink purchase.
        $this->processDrinkOrder($event->drinks);
    }
}

In your EventServiceProvider, you would register these listeners independently. This design ensures that if you modify how food is processed, it does not inadvertently affect the logic for drinks. This separation is a core tenet of good object-oriented design and aligns perfectly with the philosophy behind frameworks like Laravel.

Solution 2: Using Event Broadcasting or Service Layers (For Complex Scenarios)

If the actions are highly related, you might use an intermediate service layer instead of directly handling the events in the listener. The initial event triggers a broadcast to a central service, and that service handles the subsequent logic based on the data it receives. This further abstracts the business logic away from the event handlers themselves.

Conclusion

While using if/elseif offers a quick fix for simple scenarios, it sacrifices long-term maintainability. When dealing with multiple, distinct events, the best practice is to decouple your concerns. By creating separate listeners for each specific event type—as shown above—you create a system that is easier to test, debug, and scale. Embrace separation of concerns; it is the path to building resilient applications in Laravel.