Broadcasting events with Pusher.com & Socket.io in Laravel 5.1

(This is part of a series of posts on New Features in Laravel 5.1.)

  1. Broadcasting events with Pusher.com & Socket.io in Laravel 5.1
  2. Injecting an object (from the IOC) using Laravel Blade Service Injection
  3. Passing parameters to Middleware in Laravel 5.1
  4. Creating Artisan commands with the new, simpler syntax in Laravel 5.1
  5. Advanced input & output with Artisan commands, tables, & progress bars in Laravel 5.1
  6. Better Integration Testing in Laravel 5.1: Powerful Integration Tests in A Few Lines
  7. Better Integration Testing in Laravel 5.1: Model Factories
  8. Better Integration Testing in Laravel 5.1: DatabaseMigrations, DatabaseTransactions, and WithoutMiddleware
  9. Improvements to Elixir in Laravel 5.1 (coming soon)
  10. Excluding Routes from the CSRF Middleware in Laravel 5.1
  11. Login Throttling in Laravel 5.1
  12. ACL (Access Control List) Authorization in Laravel 5.1

Taylor's put up a new Laracast video about using the new Broadcasting tool in Laravel 5.1, which is a simple contract that allows you to "broadcast" any Event out to Pusher.com or a Redis-backed Socket.io instance.

What are Pusher.com and Socket.io? #

These are tools that use websockets to open a direct connection to your user's web browser so that you can push events directly to the user without reloading their page view.

If you've ever been on a web page and gotten "push" notifications of events (for example, when Laravel Forge updates the status of your server without you reloading the page), it's likely it was using websockets to open the connection between your browser and a server somewhere. Pusher.com is a hosted SaaS that makes it super easy to set it up, but you can also set up your own server using Socket.io.

How do websockets work? #

I'll save you from most of the technical details, but just know: There's a direct connection being opened between a web browser and a backend server. The server can push "events" (which each have a name and optionally a payload of data) along "channels". So, for example, Forge might have a "server-status" channel which can push out an event every time a server's status changes.

So if you set up Pusher.com to handle your websockets, you'll install a Javascript-based client on the frontend, and then use the Pusher PHP SDK to "push" events from your server to Pusher.com, which will then push them to the client.

So, what are Laravel broadcast events? #

If you're not familiar, check out how Laravel 5 events work. So, we now know that we can fire events--in the Forge event, maybe it would be a ServerUpdated event.

// ServerControllerOrSomething.php
    public function update()
    {
        // Do updating stuff...

        // Now send event
        event(new ServerUpdated($server));
    }

In the past, if you wanted to push a websocket notification to your users here, you would pull in the Pusher SDK, and manually send a notification over to Pusher.com in the event handler.

Now, you just add two things to your event: a ShouldBroadcast interface and a broadcastOn method.

Updating your Event to be broadcast-friendly #

Check it out:

<?php

use Illuminate\Contracts\Broadcasting\ShouldBroadcast;

class ServerUpdated implements ShouldBroadcast
{
    public $server;

    public function __construct($server)
    {
        $this->server = $server;
    }

    public function broadcastOn()
    {
        return ['server-updates'];
    }
}

As you can see, the broadcastOn method just sends back an array, and as you can guess from what we talked about earlier, this array is a list of all of the Pusher channels we want to broadcast this event on.

Payload #

Every public property on your event will be sent along as a part of the Pusher payload. Protected or private properties won't be sent along.

Note that we passed in an Eloquent object $server on ours; since Eloquent objects are JSONable, the $server object will be converted to JSON and delivered with the payload.

Using these events in our client-side code #

You'll want to follow the Pusher directions to get your client code up and running, but you'll end up with something like this:

var serverChannel = pusher.subscribe('server-status');
serverChannel.bind('ServerUpdated', function(message) {
    console.log(message); // Full payload
});

Config #

There's a new config/broadcasting.php configuration file that allows you to set up your connections and pass in which each instance should be using.

The three possible drivers right now are Pusher.com, Socket.io, and log, which just writes it out to a local log file for testing:

[2015-04-28 20:00:00] local.INFO: Broadcasting [ServerUpdated] on channels [server-status] with payload:
{
    "server": {
        "id": 1
    }
}

Conclusion #

Now there are even less barriers getting in the way of you adding websockets to your app. Set your Event to broadcast, plug it into a Pusher.com account, and then pull in the Pusher client on your frontend and you're up and running!


Comments? I'm @stauffermatt on Twitter


Tags: laravel | laravel 5.1

Matt Stauffer headshot

Hi, I'm Matt Stauffer.

I'm partner & technical director at Tighten Co.

You can find me on Twitter at @stauffermatt


Like what you're reading?

I wrote an entire 450+ page book for O'Reilly: Laravel: Up and Running.

You can order the eBook or print book today.