Real time user specific notifications with Laravel, Pusher and Vue

Written by on

Real time notifications are everywhere in modern applications - We no longer expect to have to expect our browser to know if someone has "Liked" our pictures or "Commented" on our tweets. With Laravel's built in broadcasting and Pusher this is made really easy. There are already some fantastic tutorials on getting started with Laravel and Pusher at https://pusher.com and I suggest downloading their real time chat app here: https://github.com/ammezie/laravel-chat - It'll give us a good starting point.

First thing to note is that if you're not using the chat application then you will need to uncomment the following line from config/app.php:

App\Providers\BroadcastServiceProvider::class,

 And if you're using tokens for your User Authentication you'll need to go to app>Providers>BroadcastServiceProvider.php and replace the following line:

Broadcast::routes();

 With:

 Broadcast::routes(['middleware' => ['auth:api']]);

 Or if you're using JWT then:

Broadcast::routes(['middleware' => ['jwt.auth']]);

And finally in your resources>assets>js>bootstap.js replace:

window.Echo = new Echo({
    broadcaster: 'pusher',
    key: process.env.MIX_PUSHER_APP_KEY,
    cluster: process.env.MIX_PUSHER_APP_CLUSTER,
    encrypted: true
});

 With:

window.Echo = new Echo({
    broadcaster: 'pusher',
    key: process.env.MIX_PUSHER_APP_KEY,
    cluster: process.env.MIX_PUSHER_APP_CLUSTER,
    encrypted: true,
    auth: {
        headers: {
            Authorization: 'Bearer ' + auth.token
        }
    }
});

 If you're not using tokens then you can ignore the last 5 code blocks.

In our project we now need to create a new Event, we're going to create one called NewNotification to do this run the following command in your terminal:

php artisan make:event NewNotification

 This will create a new event in app/Events called NewNotification.php.

Next we need to include our User model and create and constructor that will take the User model as a parameter.

We then need to edit the broadcastOn() method to broadcast on a private channel which we will create in a minute. You'll notice we append the Users ID to the end of the channel - This will allow us to broadcast to a specific User.

Here's a look at NewNotification.php:

<?php

namespace App\Events;

use App\User;

use Illuminate\Broadcasting\Channel;
use Illuminate\Queue\SerializesModels;
use Illuminate\Broadcasting\PrivateChannel;
use Illuminate\Broadcasting\PresenceChannel;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Contracts\Broadcasting\ShouldBroadcast;

class NewNotification implements ShouldBroadcast
{
    use Dispatchable, InteractsWithSockets, SerializesModels;

    /**
     * Create a new event instance.
     *
     * @return  void
     */
     public $user;

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


    /**
     * Get the channels the event should broadcast on.
     *
     * @return  \Illuminate\Broadcasting\Channel|array
     */
     public function broadcastOn()
     {
         return new PrivateChannel('notification.'.$this->user->id);
     }

}

 We now need to create out notification channel, for this we need to open routes>channels.php and add the following code:

Broadcast::channel('notification.*', function ($user) {
    return true;
});

 The star in the case represents a wildcard for your User ID's.

 Now we need to listen for our notification in our Vue front end - For ease here we will add it to resources>assets>js>app.js. Please note you may access your Authenticated User's ID differently in your application:

created() {
        Echo.private('notification.'+auth.user.id)
            .listen('NotificationSent', (e) => {
                console.log(e);
            });
    },

This simply console logs the target users information - Of course you could make it send an alert or open up a modal window etc but we're keeping it nice and simple for the moment.

All that's left to do now is to broadcast the event from the back end of your Laravel application. This can be down from any controller you wish, we just need to add the following to the top of our chosen controller:

use App\Events\NotificationSent;

 And within our chosen method we add the following line:

$user = User::find(1);

broadcast(new NewNotification($user))->toOthers();

 We've chosen User with the ID of one specifically in this example but you can make this a variable ID. In Our Application now every time Any user other than user one makes a call to this method with their browser - If User 1 is signed in they will receive a console.log of their information.

You can test this out by signing in as User 1 on one browser client and any other User on a different browser client and point browser to a route that hits your chosen method.

  • Real time application
  • Laravel
  • Vue
  • Pusher
Three Bears - Web design and development
Loading