symfony/linked-in-notifier
Symfony Notifier integration for LinkedIn. Configure a LINKEDIN_DSN with your LinkedIn access token and user ID to send notifications via LinkedIn through Symfony’s notifier system.
Install the Package (via Composer):
composer require symfony/linked-in-notifier
Note: Laravel may require additional adapters for Symfony dependencies.
Configure DSN in .env:
LINKEDIN_DSN=linkedin://ACCESS_TOKEN:USER_ID@default
ACCESS_TOKEN with your LinkedIn API access token.USER_ID with your LinkedIn profile ID (e.g., 123456789).Set Up Symfony Notifier in Laravel:
Since Laravel lacks native Symfony Notifier support, use a bridge like spatie/laravel-symfony-notifier or manually integrate the transport:
use Symfony\Component\Notifier\Notifier;
use Symfony\Component\Notifier\Transport\LinkedInTransport;
$notifier = new Notifier();
$transport = new LinkedInTransport($_ENV['LINKEDIN_DSN']);
$notifier->send(new Message('Hello from Laravel!'), $transport);
First Use Case: Send a Notification Trigger a notification via a Laravel controller or command:
use Symfony\Component\Notifier\Message\ChatMessage;
$message = new ChatMessage('Your application was viewed!');
$notifier->send($message, $transport);
Authentication Flow:
env or a secrets manager like laravel/vault).Notification Types:
$message = new ChatMessage('Interview scheduled for June 10!');
$notifier->send($message, $transport);
Event-Driven Notifications:
Event system to dispatch notifications:
event(new JobApplicationViewed($user, $recruiter));
Then listen and send via Notifier:
JobApplicationViewed::listen(function ($event) {
$message = new ChatMessage("Recruiter {$event->recruiter->name} viewed your profile!");
$notifier->send($message, $transport);
});
Batch Processing:
$notifier->send(
new ChatMessage('Weekly digest'),
$transport,
['delay' => 3600] // Delay 1 hour
);
Laravel-Symfony Bridge:
HttpClient with Laravel’s Http facade:
use Illuminate\Support\Facades\Http;
Messenger with Laravel Queues by extending the transport:
class LaravelLinkedInTransport extends LinkedInTransport
{
public function __construct(string $dsn)
{
parent::__construct($dsn);
$this->client = Http::withOptions(['timeout' => 10]);
}
}
Webhook Handling:
Route::post('/linkedin/webhook', ...) to verify and process LinkedIn webhooks:
Route::post('/linkedin/webhook', function (Request $request) {
$challenge = $request->input('oauth_challenge');
return response()->json(['oauth_challenge' => $challenge]);
});
Testing:
$transport = $this->createMock(LinkedInTransport::class);
$transport->method('send')->willReturn(true);
$notifier = new Notifier([$transport]);
Symfony Dependency Conflicts:
HttpClient and Messenger. Laravel may throw errors if these are missing.composer require symfony/http-client symfony/messenger
Token Expiry:
// Example: Refresh token via Laravel command
Artisan::command('linkedin:refresh-token', function () {
$token = LinkedIn::refreshAccessToken();
config(['services.linkedin.token' => $token]);
});
Rate Limits:
use Symfony\Component\Notifier\Exception\TransportException;
try {
$notifier->send($message, $transport);
} catch (TransportException $e) {
if ($e->getCode() === 429) {
sleep(10); // Retry after 10 seconds
retry();
}
}
Webhook Challenges:
Route::post('/webhook', function (Request $request) {
$challenge = $request->input('oauth_challenge');
return response()->json(['oauth_challenge' => $challenge]);
});
User ID Format:
USER_ID must be a numeric ID (e.g., 123456789), not an email or vanity URL.$user = Http::withToken($accessToken)->get('https://api.linkedin.com/v2/me')->json();
$userId = $user['id']; // e.g., "123456789"
Enable Notifier Debugging:
$notifier = new Notifier([$transport], [
'debug' => true,
]);
This logs raw API responses to storage/logs/laravel.log.
Check LinkedIn API Status:
Validate DSN Format:
linkedin://ACCESS_TOKEN:USER_ID@default. A malformed DSN will throw:
Symfony\Component\Notifier\Exception\InvalidArgumentException
Custom Message Types:
Extend Symfony\Component\Notifier\Message\MessageInterface for LinkedIn-specific payloads:
class LinkedInJobAlertMessage implements MessageInterface
{
public function __construct(private string $jobId, private string $title) {}
public function getContent(): string
{
return "New job alert: {$this->title} (ID: {$this->jobId})";
}
}
Add Rich Media: LinkedIn supports rich messages with images/buttons. Extend the transport:
class RichLinkedInTransport extends LinkedInTransport
{
public function send(MessageInterface $message, array $failedRecipients = []): void
{
$payload = [
'text' => $message->getContent(),
'attachments' => [
[
'title' => 'Apply Now',
'url' => 'https://example.com/job/{$jobId}',
],
],
];
$this->client->post('/v2/conversations', $payload);
}
}
Queue Notifications: Dispatch notifications to Laravel Queues for async processing:
class SendLinkedInNotification implements ShouldQueue
{
use Dispatchable, InteractsWithQueue, Queueable;
public function handle()
{
$notifier->send($this->message, $this->transport);
}
}
Monitor Deliveries:
Track failed notifications with Laravel’s failed_jobs table:
$notifier->send($message, $transport)->then(
function () { Log::info('Notification sent'); },
function ($e) { Log::error('Notification failed: '.$e->getMessage()); }
);
How can I help you explore Laravel packages today?