overtrue/easy-sms
A flexible SMS sending package for PHP/Laravel with a unified API for multiple providers. Supports templates, verification codes, failover and load balancing, and easy configuration so you can switch gateways without changing your application code.
Installation
composer require overtrue/easy-sms
Publish the config file:
php artisan vendor:publish --provider="Overtrue\EasySms\EasySmsServiceProvider"
Configure Default Channel
Edit config/easy-sms.php and set your preferred provider (e.g., aliyun, tencent, yunpeng).
Example for Aliyun:
'default' => env('EASY_SMS_DEFAULT', 'aliyun'),
'aliyun' => [
'access_key_id' => env('ALIYUN_ACCESS_KEY_ID'),
'access_key_secret' => env('ALIYUN_ACCESS_KEY_SECRET'),
'sign_name' => env('ALIYUN_SIGN_NAME'),
'domain' => env('ALIYUN_DOMAIN', 'dysmsapi.aliyuncs.com'),
],
First Send
use Overtrue\EasySms\EasySmsFactory;
$sms = EasySmsFactory::make('aliyun');
$result = $sms->send('SMS_123456', ['code' => '1234'], '15812345678');
config/easy-sms.php (provider settings, defaults, and templates).Overtrue\EasySms\EasySmsServiceProvider (registers bindings and macros).Use the factory to dynamically switch providers based on environment or business logic:
$sms = EasySmsFactory::make(env('SMS_PROVIDER', 'default'));
Store templates in the config or database for reusability:
// config/easy-sms.php
'templates' => [
'verify_code' => [
'aliyun' => 'SMS_123456',
'tencent' => '1234567890',
],
],
Then use:
$sms->send('verify_code', ['code' => '1234'], '15812345678');
Send SMS to multiple numbers efficiently:
$sms->multiSend('SMS_123456', ['code' => '1234'], ['15812345678', '15887654321']);
Delay SMS sending for performance:
use Illuminate\Support\Facades\Queue;
Queue::push(function () use ($sms) {
$sms->send('SMS_123456', ['code' => '1234'], '15812345678');
});
Extend for unsupported providers (e.g., custom HTTP API):
use Overtrue\EasySms\Contracts\SmsManager;
class CustomSmsManager implements SmsManager {
public function send($template, $data, $phone) {
// Custom logic (e.g., HTTP request to your SMS gateway)
}
}
// Register in config/easy-sms.php:
'custom' => [
'class' => \App\Providers\CustomSmsManager::class,
],
Enable logging for debugging and retry failed sends:
$sms->setRetryTimes(3); // Retry 3 times on failure
$sms->sendWithRetry('SMS_123456', ['code' => '1234'], '15812345678');
Rate Limits
config/easy-sms.php for throttle settings or implement exponential backoff in custom providers.Template Mismatch
SMS_123456) match the provider’s actual template IDs. Test with a single number first.Phone Number Formatting
+8615812345678). Validate input:
$phone = preg_replace('/^86/', '+86', $phone); // Example for Chinese numbers
Async Failures
Environment Variables
.env keys (e.g., ALIYUN_ACCESS_KEY_ID) exist before sending. Use env() checks:
if (!env('ALIYUN_ACCESS_KEY_ID')) {
throw new \RuntimeException('SMS provider not configured');
}
Enable Logging
Add to config/easy-sms.php:
'log' => true,
Check Laravel logs (storage/logs/laravel.log) for provider responses.
Mock Providers for Testing
Use the mock provider in tests:
$sms = EasySmsFactory::make('mock');
$sms->setMockResponse(['Code' => 'OK']);
Provider-Specific Quirks
sign_name (sender ID) to be pre-approved.smsid instead of template_code in some cases.app_id and app_key in addition to credentials.Macros Add reusable methods to the SMS manager:
\Overtrue\EasySms\EasySms::macro('sendVerification', function ($phone, $code) {
return $this->send('verify_code', ['code' => $code], $phone);
});
Usage:
$sms->sendVerification('15812345678', '1234');
Events Listen for send events (e.g., log or notify admins):
\Overtrue\EasySms\Events\SmsSent::class => function ($event) {
\Log::info('SMS sent to ' . $event->phone, $event->data);
}
Middleware Validate phone numbers or check user permissions before sending:
$sms->extend('validated', function ($sms) {
return new class($sms) implements SmsManager {
public function send($template, $data, $phone) {
if (!preg_match('/^1[3-9]\d{9}$/', $phone)) {
throw new \InvalidArgumentException('Invalid phone number');
}
return $this->sms->send($template, $data, $phone);
}
};
});
Fallback Providers Chain providers for redundancy:
$sms = EasySmsFactory::make('aliyun');
$sms->setFallbackProvider('tencent');
$sms->send('SMS_123456', ['code' => '1234'], '15812345678');
How can I help you explore Laravel packages today?