PHPackages                             juzaweb/notification - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Mail &amp; Notifications](/categories/mail)
4. /
5. juzaweb/notification

ActiveJuzaweb-module[Mail &amp; Notifications](/categories/mail)

juzaweb/notification
====================

Notification module for Juzaweb cms

1.0.4(2y ago)119MITPHPPHP ^8.0|^8.1CI passing

Since Oct 1Pushed 2mo ago1 watchersCompare

[ Source](https://github.com/juzaweb/notification)[ Packagist](https://packagist.org/packages/juzaweb/notification)[ Docs](https://juzaweb.com)[ RSS](/packages/juzaweb-notification/feed)WikiDiscussions master Synced 1mo ago

READMEChangelog (6)Dependencies (2)Versions (9)Used By (0)

Juzaweb CMS Notification Module
===============================

[](#juzaweb-cms-notification-module)

This package provides notification management functionality with support for registering and managing different recipient types and notification channels.

Features
--------

[](#features)

- Singleton `NotificationManager` service for managing recipient types and notification channels
- Facade for easy access
- Register custom recipient types and channels with callback pattern
- Query registered recipient types and channels

Installation
------------

[](#installation)

The package is auto-registered via Laravel's service provider discovery.

Usage
-----

[](#usage)

### Registering Notification Channels

[](#registering-notification-channels)

You can register notification channels in your service provider's `boot()` method:

```
use Juzaweb\Modules\Notification\Facades\Notification;
use Juzaweb\Modules\Notification\Channels\EmailChannel;

// Register using a class
Notification::registerChannel('email', fn() => new EmailChannel());

// Or register using anonymous class
Notification::registerChannel('sms', function () {
    return new class implements NotificationChannelInterface {
        public function getLabel(): string {
            return 'SMS';
        }

        public function getDescription(): ?string {
            return 'Send notifications via SMS';
        }

        public function toArray(): array {
            return [
                'label' => $this->getLabel(),
                'description' => $this->getDescription(),
            ];
        }
    };
});
```

### Registering Recipient Types

[](#registering-recipient-types)

You can register recipient types in your service provider's `boot()` method:

```
use Juzaweb\Modules\Notification\Facades\Notification;

// Register recipient types with callback pattern
Notification::registerRecipientType('all_users', function () {
    return new class implements RecipientTypeInterface {
        public function getLabel(): string {
            return 'All Users';
        }

        public function getDescription(): ?string {
            return 'Send to all registered users';
        }

        public function toArray(): array {
            return [
                'label' => $this->getLabel(),
                'description' => $this->getDescription(),
            ];
        }
    };
});

Notification::registerRecipientType('premium_users', function () {
    return new class implements RecipientTypeInterface {
        public function getLabel(): string {
            return 'Premium Users';
        }

        public function getDescription(): ?string {
            return 'Send to users with premium subscription';
        }

        public function toArray(): array {
            return [
                'label' => $this->getLabel(),
                'description' => $this->getDescription(),
            ];
        }
    };
});
```

### Creating Custom Recipient Types

[](#creating-custom-recipient-types)

You can create your own custom recipient type classes by implementing `RecipientTypeInterface`:

```
use Juzaweb\Modules\Notification\Contracts\RecipientTypeInterface;

class PremiumUsersRecipientType implements RecipientTypeInterface
{
    public function getLabel(): string
    {
        return __('Premium Users');
    }

    public function getDescription(): ?string
    {
        return __('Send to users with active premium subscription');
    }

    public function toArray(): array
    {
        return [
            'label' => $this->getLabel(),
            'description' => $this->getDescription(),
        ];
    }

    // You can add custom methods
    public function getRecipients(): array
    {
        // Custom logic to get recipients
        return User::where('is_premium', true)->get();
    }
}

// Register the custom type
Notification::registerRecipientType('premium_users', fn() => new PremiumUsersRecipientType());
```

### Creating Custom Notification Channels

[](#creating-custom-notification-channels)

Create notification channels by implementing `NotificationChannelInterface`:

```
use Juzaweb\Modules\Notification\Contracts\NotificationChannelInterface;

class PushNotificationChannel implements NotificationChannelInterface
{
    public function getLabel(): string
    {
        return __('Push Notification');
    }

    public function getDescription(): ?string
    {
        return __('Send push notifications to mobile devices');
    }

    public function toArray(): array
    {
        return [
            'label' => $this->getLabel(),
            'description' => $this->getDescription(),
        ];
    }
}

// Register the custom channel
Notification::registerChannel('push', fn() => new PushNotificationChannel());
```

### Getting Recipient Types

[](#getting-recipient-types)

```
use Juzaweb\Modules\Notification\Facades\Notification;

// Get all registered recipient types (as objects)
$recipientTypes = Notification::getRecipientTypes();
/*
Returns array of RecipientTypeInterface objects:
[
    'all_users' => RecipientType object,
    'premium_users' => PremiumUsersRecipientType object,
    // ...
]
*/

// Get all registered recipient types as arrays
$recipientTypesArray = Notification::getRecipientTypesArray();
/*
Returns:
[
    'all_users' => [
        'label' => 'All Users',
        'description' => 'Send to all registered users'
    ],
    'premium_users' => [
        'label' => 'Premium Users',
        'description' => 'Send to users with premium subscription'
    ],
    // ...
]
*/

// Get a specific recipient type (as object)
$type = Notification::getRecipientType('all_users');
// Returns RecipientTypeInterface object or null

// Access properties
if ($type) {
    echo $type->getLabel(); // "All Users"
    echo $type->getDescription(); // "Send to all registered users"
}
```

### Getting Notification Channels

[](#getting-notification-channels)

```
use Juzaweb\Modules\Notification\Facades\Notification;

// Get all registered channels (as objects)
$channels = Notification::getChannels();

// Get all registered channels as arrays
$channelsArray = Notification::getChannelsArray();
/*
Returns:
[
    'email' => [
        'label' => 'Email',
        'description' => 'Send notifications via email'
    ],
    'sms' => [
        'label' => 'SMS',
        'description' => 'Send notifications via SMS'
    ],
    // ...
]
*/

// Check if a channel exists
if (Notification::hasChannel('email')) {
    // Channel exists
}
```

### Using in Views

[](#using-in-views)

In your controller:

```
use Juzaweb\Modules\Notification\Facades\Notification;

public function create()
{
    // Get as array for easier use in views
    $recipientTypes = Notification::getRecipientTypesArray();
    $channels = Notification::getChannelsArray();

    return view('notification::create', compact('recipientTypes', 'channels'));
}
```

In your Blade view:

```

    @foreach($recipientTypes as $key => $type)

            {{ $type['label'] }}
            @if(!empty($type['description']))
                - {{ $type['description'] }}
            @endif

    @endforeach

    @foreach($channels as $key => $channel)

            {{ $channel['label'] }}
            @if(!empty($channel['description']))
                - {{ $channel['description'] }}
            @endif

    @endforeach

```

### Subscriptable Channels

[](#subscriptable-channels)

Mark channels as subscriptable to allow users to subscribe/unsubscribe:

```
use Juzaweb\Modules\Notification\Facades\Notification;

// Mark a channel as subscriptable
Notification::subscriptable('email', [
    'can_unsubscribe' => true,
    'default_enabled' => true,
]);

Notification::subscriptable('sms', [
    'can_unsubscribe' => true,
    'default_enabled' => false,
]);

// Get all subscriptable channels
$subscriptableChannels = Notification::getSubscriptableChannels();
// Returns: ['email', 'sms']

// Get subscriptable data for a specific channel
$emailData = Notification::getSubscriptableData('email');
/*
Returns:
[
    'can_unsubscribe' => true,
    'default_enabled' => true,
]
*/
```

### Sending Bulk Notifications

[](#sending-bulk-notifications)

Use the `SendNotificationJob` to send notifications to multiple recipients:

```
use Juzaweb\Modules\Notification\Jobs\SendNotificationJob;
use Juzaweb\Modules\Notification\Models\SentNotification;

// Create a notification
$notification = SentNotification::create([
    'title' => 'System Maintenance',
    'message' => 'The system will be under maintenance tomorrow.',
    'recipient_type' => 'all_users',
    'via' => ['email', 'database'],
]);

// Dispatch job to send notifications
SendNotificationJob::dispatch($notification);

// Or with custom chunk size (default is 100)
SendNotificationJob::dispatch($notification, 50);
```

The job will:

1. Get recipients from the registered recipient type
2. Process recipients in chunks to avoid memory issues
3. Send notifications via specified channels
4. Update the `sent_at` timestamp when complete

### Bulk Actions in Admin Panel

[](#bulk-actions-in-admin-panel)

From the admin panel, you can select multiple notifications and perform bulk actions:

- **Delete**: Remove selected notifications
- **Send**: Queue selected notifications for sending

```
// In your controller
public function bulk(SentNotificationActionsRequest $request)
{
    $action = $request->input('action'); // 'delete' or 'sent'
    $ids = $request->input('ids', []);

    $models = SentNotification::whereIn('id', $ids)->get();

    foreach ($models as $model) {
        if ($action === 'delete') {
            $model->delete();
        }

        if ($action === 'sent') {
            SendNotificationJob::dispatch($model);
        }
    }
}
```

API Reference
-------------

[](#api-reference)

### NotificationManager Methods

[](#notificationmanager-methods)

#### `registerRecipientType(string $key, callable $callback): self`

[](#registerrecipienttypestring-key-callable-callback-self)

Register a new recipient type.

**Parameters:**

- `$key` - The unique key for the recipient type
- `$callback` - Callback that returns a `RecipientTypeInterface` instance

**Returns:** `self` for method chaining

**Example:**

```
Notification::registerRecipientType('all_users', fn() => new AllUsersRecipientType());
```

---

#### `registerChannel(string $key, callable $callback): self`

[](#registerchannelstring-key-callable-callback-self)

Register a new notification channel.

**Parameters:**

- `$key` - The unique key for the channel
- `$callback` - Callback that returns a `NotificationChannelInterface` instance

**Returns:** `self` for method chaining

**Example:**

```
Notification::registerChannel('email', fn() => new EmailChannel());
```

---

#### `getRecipientTypes(): array`

[](#getrecipienttypes-arraystring-recipienttypeinterface)

Get all registered recipient types as objects.

**Returns:** Array of `RecipientTypeInterface` objects indexed by key

---

#### `getRecipientTypesArray(): array`

[](#getrecipienttypesarray-arraystring-array)

Get all registered recipient types as arrays (useful for views).

**Returns:** Array of arrays with `label` and `description` for each type

---

#### `getRecipientType(string $key): ?RecipientTypeInterface`

[](#getrecipienttypestring-key-recipienttypeinterface)

Get a specific recipient type by key.

**Parameters:**

- `$key` - The recipient type key

**Returns:** `RecipientTypeInterface` object or `null` if not found

---

#### `hasRecipientType(string $key): bool`

[](#hasrecipienttypestring-key-bool)

Check if a recipient type is registered.

**Parameters:**

- `$key` - The recipient type key

**Returns:** `true` if exists, `false` otherwise

---

#### `unregisterRecipientType(string $key): self`

[](#unregisterrecipienttypestring-key-self)

Remove a recipient type.

**Parameters:**

- `$key` - The recipient type key to remove

**Returns:** `self` for method chaining

---

#### `getChannels(): array`

[](#getchannels-arraystring-notificationchannelinterface)

Get all registered channels as objects.

**Returns:** Array of `NotificationChannelInterface` objects indexed by key

---

#### `getChannelsArray(): array`

[](#getchannelsarray-arraystring-array)

Get all registered channels as arrays (useful for views).

**Returns:** Array of arrays with `label` and `description` for each channel

---

#### `hasChannel(string $key): bool`

[](#haschannelstring-key-bool)

Check if a channel is registered.

**Parameters:**

- `$key` - The channel key

**Returns:** `true` if exists, `false` otherwise

---

#### `unregisterChannel(string $key): self`

[](#unregisterchannelstring-key-self)

Remove a channel.

**Parameters:**

- `$key` - The channel key to remove

**Returns:** `self` for method chaining

---

#### `subscriptable(string $channel, array $data = []): void`

[](#subscriptablestring-channel-array-data---void)

Mark a channel as subscriptable, allowing users to subscribe or unsubscribe.

**Parameters:**

- `$channel` - The channel key
- `$data` - Optional configuration data (e.g., `['can_unsubscribe' => true]`)

**Example:**

```
Notification::subscriptable('email', [
    'can_unsubscribe' => true,
    'default_enabled' => true,
]);
```

---

#### `getSubscriptableChannels(): array`

[](#getsubscriptablechannels-arraystring)

Get all channels marked as subscriptable.

**Returns:** Array of channel keys that are subscriptable

**Example:**

```
$channels = Notification::getSubscriptableChannels();
// Returns: ['email', 'sms', 'push']
```

---

#### `getSubscriptableData(string $channel): array`

[](#getsubscriptabledatastring-channel-arraystring-mixed)

Get the subscriptable configuration data for a specific channel.

**Parameters:**

- `$channel` - The channel key

**Returns:** Array of configuration data for the channel, or empty array if not found

**Example:**

```
$data = Notification::getSubscriptableData('email');
/*
Returns:
[
    'can_unsubscribe' => true,
    'default_enabled' => true,
]
*/
```

---

### RecipientTypeInterface

[](#recipienttypeinterface)

Interface that all recipient type classes must implement.

#### `getLabel(): string`

[](#getlabel-string)

Get the display label for the recipient type.

---

#### `getDescription(): ?string`

[](#getdescription-string)

Get the description for the recipient type (optional).

---

#### `toArray(): array`

[](#toarray-array)

Convert the recipient type to an array representation.

**Returns:** Array with `label` and `description` keys

---

#### `getRecipients(): \Illuminate\Database\Eloquent\Builder`

[](#getrecipients-illuminatedatabaseeloquentbuilder)

Get the Eloquent query builder for fetching recipients.

**Returns:** Eloquent Builder instance that can be used to fetch recipients

**Example:**

```
public function getRecipients(): \Illuminate\Database\Eloquent\Builder
{
    return User::where('is_premium', true);
}
```

---

### NotificationChannelInterface

[](#notificationchannelinterface)

Interface that all notification channel classes must implement.

#### `getLabel(): string`

[](#getlabel-string-1)

Get the display label for the notification channel.

---

#### `getDescription(): ?string`

[](#getdescription-string-1)

Get the description for the notification channel (optional).

---

#### `toArray(): array`

[](#toarray-array-1)

Convert the notification channel to an array representation.

**Returns:** Array with `label` and `description` keys

---

Examples
--------

[](#examples)

### Complete Recipient Type Implementation

[](#complete-recipient-type-implementation)

```
use Juzaweb\Modules\Notification\Contracts\RecipientTypeInterface;
use App\Models\User;

class ActiveUsersRecipientType implements RecipientTypeInterface
{
    public function getLabel(): string
    {
        return __('Active Users');
    }

    public function getDescription(): ?string
    {
        return __('Users who have logged in within the last 30 days');
    }

    public function getRecipients(): \Illuminate\Database\Eloquent\Builder
    {
        return User::where('last_login_at', '>=', now()->subDays(30))
            ->whereNotNull('email');
    }

    public function toArray(): array
    {
        return [
            'label' => $this->getLabel(),
            'description' => $this->getDescription(),
        ];
    }
}

// Register it
Notification::registerRecipientType('active_users', fn() => new ActiveUsersRecipientType());
```

### Sending Notifications with Error Handling

[](#sending-notifications-with-error-handling)

```
use Juzaweb\Modules\Notification\Jobs\SendNotificationJob;
use Juzaweb\Modules\Notification\Models\SentNotification;
use Juzaweb\Modules\Notification\Exceptions\RecipientTypeNotFoundException;

try {
    $notification = SentNotification::create([
        'title' => 'Welcome!',
        'message' => 'Thank you for joining us.',
        'recipient_type' => 'new_users',
        'via' => ['email', 'database'],
    ]);

    SendNotificationJob::dispatch($notification);

} catch (RecipientTypeNotFoundException $e) {
    Log::error('Recipient type not found: ' . $e->getMessage());
}
```

### Unregistering Types and Channels

[](#unregistering-types-and-channels)

```
// Unregister a recipient type
Notification::unregisterRecipientType('old_type');

// Unregister a channel
Notification::unregisterChannel('deprecated_channel');

// Check before unregistering
if (Notification::hasRecipientType('temp_type')) {
    Notification::unregisterRecipientType('temp_type');
}
```

License
-------

[](#license)

Same as the main application license.

###  Health Score

37

—

LowBetter than 83% of packages

Maintenance56

Moderate activity, may be stable

Popularity8

Limited adoption so far

Community9

Small or concentrated contributor base

Maturity64

Established project with proven stability

 Bus Factor1

Top contributor holds 96.6% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~188 days

Recently: every ~182 days

Total

6

Last Release

740d ago

PHP version history (2 changes)v1.0PHP ^7.2.5|^8.0

v1.0.1PHP ^8.0|^8.1

### Community

Maintainers

![](https://www.gravatar.com/avatar/3169e8a8781068840e9300a57785089da521287dbe0279fc9cc7e8de1c1d95a9?d=identicon)[juzaweb](/maintainers/juzaweb)

---

Top Contributors

[![juzaweb](https://avatars.githubusercontent.com/u/47020363?v=4)](https://github.com/juzaweb "juzaweb (57 commits)")[![google-labs-jules[bot]](https://avatars.githubusercontent.com/in/842251?v=4)](https://github.com/google-labs-jules[bot] "google-labs-jules[bot] (2 commits)")

---

Tags

pluginnotificationcmsjuzaweb

### Embed Badge

![Health badge](/badges/juzaweb-notification/health.svg)

```
[![Health](https://phpackages.com/badges/juzaweb-notification/health.svg)](https://phpackages.com/packages/juzaweb-notification)
```

###  Alternatives

[kartik-v/yii2-widget-growl

A widget to generate growl based notifications using bootstrap-growl plugin (sub repo split from yii2-widgets)

384.2M14](/packages/kartik-v-yii2-widget-growl)[kartik-v/yii2-widget-alert

A widget to generate alert based notifications using bootstrap-alert plugin (sub repo split from yii2-widgets)

284.1M24](/packages/kartik-v-yii2-widget-alert)[friendsofsilverstripe/backendmessages

DRY way to create message boxes in SilverStripe backend.

1015.4k2](/packages/friendsofsilverstripe-backendmessages)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
