chijioke-ibekwe / raven
Multi-channel Laravel notification sender
Requires
- aws/aws-sdk-php: ^3.300
- phpmailer/phpmailer: ^6.9
- sendgrid/sendgrid: ~7
Requires (Dev)
- orchestra/testbench: ^6.0
- phpunit/phpunit: ^9.6
This package is auto-updated.
Last update: 2024-05-13 14:10:39 UTC
README
Multi-channel Laravel notification package
📝 Table of Contents
🧐 About
In Laravel, crafting notification classes can often feel repetitive (and WET), especially in projects that rely heavily on notifications. Meet Raven – the solution that streamlines the process of sending notifications through multiple channels in Laravel, allowing you to focus on your peculiar business logic. Currently, Raven seamlessly handles email notifications through SendGrid and Amazon SES, as well as database notifications. Stay tuned, as support for SMS notifications will be integrated in the near future.
🏁 Getting Started
Prerequisites
To use this package, you need the following requirements:
- PHP >= v8.0
- Laravel >= v8.0
- Composer
🎈 Usage
-
You can install this package via Composer using the command:
composer require chijioke-ibekwe/raven
-
Next, you will need to publish and run the migration files, and the config file. The following command will allow you do all of the above:
php artisan raven:install
-
The migrations will be published in your project's migrations directory
./database/migrations
while the config fileraven.php
, will be published in your config directory./config
. Content of the config file is as shown below:<?php return [ 'default' => [ 'email' => env('EMAIL_NOTIFICATION_PROVIDER', 'sendgrid'), 'sms' => env('SMS_NOTIFICATION_PROVIDER', 'nexmo') ], 'providers' => [ 'sendgrid' => [ 'key' => env('SENDGRID_API_KEY') ], 'ses' => [ 'key' => env('AWS_ACCESS_KEY_ID'), 'secret' => env('AWS_SECRET_ACCESS_KEY'), 'region' => env('AWS_DEFAULT_REGION', 'us-east-1'), 'template_source' => env('AWS_SES_TEMPLATE_SOURCE', 'sendgrid'), 'template_directory' => env('AWS_SES_TEMPLATE_DIRECTORY', 'resources/views/emails') ] ], 'customizations' => [ 'mail' => [ 'from' => [ 'address' => env('MAIL_FROM_ADDRESS', 'hello@example.com'), 'name' => env('MAIL_FROM_NAME', 'Example'), ] ], 'queue_name' => env('RAVEN_QUEUE_NAME') ], 'api' => [ 'prefix' => 'api/v1', 'middleware' => 'api' ] ];
- The
default
array allows you to configure your default service providers for your notification channels. Options aresendgrid
andses
. (nexmo
for SMS will be integrated soon). - The
providers
array is where you supply the credentials for the service provider you choose. When usingses
, you can provide the email template in 2 ways.- First is by hosting your email template on
sendgrid
. If this is your preferred option, thetemplate_source
should be set assendgrid
. NB: For this to work, you need to also provide your credentials for thesendgrid
provider. - Second option is by storing your email templates on the file system as blade templates. The
template_source
in this case should be set asfile
and the directory of the templates should be provided on thetemplate_directory
. (This option is not currently available, but will be in the near future).
- First is by hosting your email template on
- The
customizations
array allows you to customize your email parameters, and optionally yourqueue_name
(not queue connection) for queueing your notifications. If a queue name is not provided, the default queue will be used. - The
api
array allows you to customize the provided API routes.
- The
-
After the migrations have been run successfully, you can then proceed to add notification contexts to the database. To do this, simply create and run migration files similar to the ones below:
- Email Notification Context
<?php use Illuminate\Database\Migrations\Migration; use Illuminate\Support\Facades\DB; return new class extends Migration { /** * Run the migrations. */ public function up(): void { $id = DB::table('notification_contexts')->insertGetId( array( 'name' => 'user-verified', 'email_template_id' => 'd-ad34ghAwe3mQRvb29', 'description' => 'Notification to inform a user that they have been verified on the platform' ) ); DB::table('notification_channel_notification_context')->insert( array( 'notification_channel_id' => 1, //EMAIL 'notification_context_id' => $id ) ); } /** * Reverse the migrations. */ public function down(): void { DB::table('notification_contexts')->where('name', 'user-verified')->delete(); } };
- Database Notification Context
<?php use Illuminate\Database\Migrations\Migration; use Illuminate\Support\Facades\DB; return new class extends Migration { /** * Run the migrations. */ public function up(): void { $id = DB::table('notification_contexts')->insertGetId( array( 'name' => 'user-verified', 'description' => 'Notification to inform a user that they have been verified on the platform', 'title' => 'You have been verified', 'body' => 'Hello {name}. This is to let you know that your account with email {email} has been verified', 'type' => 'user' ) ); DB::table('notification_channel_notification_context')->insert( array( 'notification_channel_id' => 2, //DATABASE 'notification_context_id' => $id ) ); } /** * Reverse the migrations. */ public function down(): void { DB::table('notification_contexts')->where('name', 'user-verified')->delete(); } };
- Email and Database Notification Context
<?php use Illuminate\Database\Migrations\Migration; use Illuminate\Support\Facades\DB; return new class extends Migration { /** * Run the migrations. */ public function up(): void { $id = DB::table('notification_contexts')->insertGetId( array( 'name' => 'user-verified', 'email_template_id' => 'd-ad34ghAwe3mQRvb29', 'description' => 'Notification to inform a user that they have been verified on the platform', 'title' => 'You have been verified', 'body' => 'Hello {name}. This is to let you know that your account with email {email} has been verified', 'type' => 'user' ) ); DB::table('notification_channel_notification_context')->insert( array( array( 'notification_channel_id' => 1, //EMAIL 'notification_context_id' => $id, ), array( 'notification_channel_id' => 2, //DATABASE 'notification_context_id' => $id, ) ) ); } /** * Reverse the migrations. */ public function down(): void { DB::table('notification_contexts')->where('name', 'user-verified')->delete(); } };
-
To send a notification at any point in your code, build a
Scroll
object, set the relevant fields as shown below, and dispatch aRaven
with theScroll
:$verified_user = User::find(1); $document_url = "https://example.com/laravel-cheatsheet.pdf"; $scroll = new Scroll(); $scroll->setContextName('user-verified'); $scroll->setRecipients([$verified_user, 'admin@raven.com']); $scroll->setCcs(['john.doe@raven.com' => 'John Doe', 'jane.doe@raven.com' => 'Jane Doe']) $scroll->setParams([ 'id' => $verified_user->id, 'name' => $verified_user->name 'email' => $verified_user->email ]); $scroll->setAttachmentUrls($document_url) Raven::dispatch($scroll);
- The
contextName
property is required and must match the notification context name for that notification on the database. - The
recipients
property is required and takes any single notifiable/email string, or an array of notifiables/email strings that should receive the notification. - The
ccs
property is exclusively for email notifications and takes an array (or associative array with email/name as key/value pairs respectively) of emails you want to CC on the email notification. - The
params
property is an associative array of all the variables that exist on the notification template with their values, where the key must match the variable name on the template. - Finally, the
attachmentUrls
field takes a url or an array of urls that point to the publicly accessible resource(s) that needs to be attached to the email notification.
- The
-
To successfully send Database Notifications, it is assumed that the user of this package has already set up a notifications table in their project via the command below:
php artisan notifications:table
And subsequently:
php artisan migrate
The data column for database notifications using this package, captures the following properties:
[ 'title' => $title, 'body' => $body ];
The
title
andbody
properties are obtained from the notification context for the said notification on the database. -
The package takes care of the rest of the logic.
API
The following API is included in this package for ease of use:
GET /api/v1/notification-contexts
- Fetches all notification contexts on the database. The user of this API has to be authenticated.
- Return a JSON of the format below:
{ "status": true, "msg": "Success", "data": [ { "id": 1, "email_template_id": "d-ad34ghAwe3mQRvb29", "name": "user-verified", "description": "Notification to inform a user that they have been verified on the platform", "title": "You have been verified", "body": "Hello {name}. This is to let you know that your account with email {email} has been verified", "type": "user", "active": true, "notification_channels": [ { "id": 1, "type": "EMAIL" } ] } ] }
- When user is not authenticated, it returns the following
401
response:
{ "status": false, "msg": "You are not authorized to access this API" }
Exceptions
The following exceptions can be thrown by the package for the scenarios outlined below:
RavenEntityNotFoundException
code: 404
- Dispatching a Raven with a
Scroll
object that has acontextName
which does not exist on the database.
- Dispatching a Raven with a
RavenInvalidDataException
code: 422
- Dispatching a Raven with a
Scroll
object without acontextName
orrecipient
. - Attempting to send an Email Notification using a
NotificationContext
that has noemail_template_id
. - Attempting to send a Database Notification using a
NotificationContext
that has notitle
orbody
. - Attempting to send an Email Notification to a notifiable that has no
email
field or arouteNotificationForMail()
method in the model class.
- Dispatching a Raven with a
⛏️ Built Using
- PHP - Language
- Orchestral Testbench - Library
- AWS PHP SDK - Library
- Sendgrid PHP Library - Library
- PHP Mailer - Library
📝 TODO
- Add support for SMS notifications
✍️ Authors
- @chijioke-ibekwe - Initial work