3neti/laravel-model-channel
laravel-model-channel
A schema-light Laravel capability package for attaching delivery and communication channels to Eloquent models through a polymorphic channels table.
Release-tested platforms
- PHP 8.3+ with Laravel 12
- PHP 8.3+ with Laravel 13
- Pest 3 or 4 for package development
The runtime constraint remains compatible with Laravel 11 for existing consumers, but Laravel 11 is no longer a release-tested lane because currently available versions are blocked by Composer security advisories.
Why this package exists
This package lets a model expose capabilities like mobile or webhook delivery without requiring host apps to add direct columns such as users.mobile or users.webhook.
Channels are stored in the package-owned morph table, keeping your application schema clean and flexible.
Installation
composer require 3neti/laravel-model-channel:^1.1
php artisan migrate
Supported Channel Types
Out of the box, the package supports:
mobile(normalized to E.164 without+)webhook(validated URL)telegram(numeric ID)whatsapp(phone-based)viber(phone-based)
All channels are validated via enum-backed rules.
Basic usage
use Illuminate\Database\Eloquent\Model;
use LBHurtado\ModelChannel\Contracts\HasMobileChannel;
use LBHurtado\ModelChannel\Contracts\HasWebhookChannel;
use LBHurtado\ModelChannel\Traits\HasChannels;
class User extends Model implements HasMobileChannel, HasWebhookChannel
{
use HasChannels;
}
Explicit capability API
Mobile
$user->setMobileChannel('09171234567');
$user->getMobileChannel(); // 639171234567
$user->hasMobileChannel(); // true
Accepted formats:
$user->setMobileChannel('09171234567');
$user->setMobileChannel('0917 123 4567');
$user->setMobileChannel('639171234567');
$user->setMobileChannel('+639171234567');
$user->setMobileChannel('+63 (917) 123-4567');
All normalize to:
639171234567
Webhook
$user->setWebhookChannel('https://example.com/webhook');
$user->getWebhookChannel(); // https://example.com/webhook
$user->hasWebhookChannel(); // true
Generic API
$user->setChannel('webhook', 'https://example.com/webhook');
$user->getChannel('webhook');
$user->hasChannel('webhook');
Using enum:
use LBHurtado\ModelChannel\Enums\Channel;
$user->setChannel(Channel::WEBHOOK, 'https://example.com/webhook');
Delete a channel:
$user->setChannel(Channel::WEBHOOK, null);
$user->setChannel(Channel::WEBHOOK, '');
Magic properties (backward compatibility)
$user->mobile = '09171234567';
$user->mobile; // 639171234567
$user->getMobileChannel(); // 639171234567
Additional helpers
Telegram
$user->setTelegramChannel('123456789');
$user->getTelegramChannel();
$user->hasTelegramChannel();
$user->setWhatsappChannel('09171234567');
$user->getWhatsappChannel();
$user->hasWhatsappChannel();
Viber
$user->setViberChannel('09171234567');
$user->getViberChannel();
$user->hasViberChannel();
Finders
User::findByMobile('09171234567');
User::findByWebhook('https://example.com/webhook');
User::findByChannel('telegram', '123456789');
Mobile finder supports multiple formats.
Performance & Caching
Database Indexing (Recommended)
For optimal performance, especially for findByMobile() and findByChannel(), add indexes:
$table->index(['name', 'value']);
$table->index(['model_type', 'model_id', 'name']);
Lookup Caching (Optional)
Caching is designed for finder methods only, not accessor reads.
Supported cached operations:
findByMobile()findByWebhook()findByChannel()(for configured channels)
Example config:
'cache' => [
'enabled' => true,
'ttl' => 600,
'channels' => ['mobile', 'webhook'],
]
Cache Behavior
- caches model IDs only (not full models)
- caches misses to prevent repeated DB queries
- automatically invalidates on update or delete
- does NOT cache accessor methods like
getMobileChannel()
External package integration
use LBHurtado\ModelChannel\Contracts\HasMobileChannel;
function sendOtp(HasMobileChannel $user)
{
$mobile = $user->getMobileChannel();
}
Storage model
No schema changes required.
All data is stored in the polymorphic channels table.
Related Packages
Powerful PHP database abstraction layer (DBAL) with many features for database s...
Laravel Serializable Closure provides an easy and secure way to serialize closur...
Cli error handling for console/command-line PHP applications.