76 lines
2.3 KiB
PHP
76 lines
2.3 KiB
PHP
<?php
|
|
|
|
namespace Modules\Core\Notification;
|
|
|
|
use Throwable;
|
|
use Illuminate\Support\Facades\Event;
|
|
|
|
class NotificationRegistry
|
|
{
|
|
private static ?self $instance = null;
|
|
|
|
private array $notifications = [];
|
|
|
|
private function __construct() {}
|
|
|
|
public static function get(): static
|
|
{
|
|
if (static::$instance == null) {
|
|
static::$instance = new static();
|
|
}
|
|
|
|
return static::$instance;
|
|
}
|
|
|
|
public function register(array $notifications): void
|
|
{
|
|
foreach ($notifications as $class) {
|
|
$key = $class::getKey();
|
|
$alreadyRegistered = isset($this->notifications[$key]);
|
|
|
|
$this->notifications[$key] = $class;
|
|
|
|
if ($alreadyRegistered) {
|
|
continue;
|
|
}
|
|
|
|
Event::listen($class::listensTo(), function (object $event) use ($key) {
|
|
$class = $this->notifications[$key] ?? null;
|
|
if ($class == null) {
|
|
return;
|
|
}
|
|
try {
|
|
$notification = new $class($event);
|
|
if (isset($event->delaySeconds) && $event->delaySeconds > 0) {
|
|
$notification->delay($event->delaySeconds);
|
|
}
|
|
// Every order-notification event carries ->order, whose
|
|
// ->meta['locale'] was saved at checkout (Checkout\
|
|
// Services\CheckoutService::initiatePayment()) — the
|
|
// request that actually sends this may have no locale of
|
|
// its own (a payment webhook, a queued job, a staff
|
|
// action from Filament), so this is the only reliable
|
|
// source. Falls back to the app default for an order
|
|
// placed before this existed.
|
|
if (isset($event->order) && $locale = $event->order->meta['locale'] ?? null) {
|
|
$notification->locale($locale);
|
|
}
|
|
$notification->notifiable()->notify($notification);
|
|
} catch (Throwable $e) {
|
|
report($e);
|
|
}
|
|
});
|
|
}
|
|
}
|
|
|
|
public function unregister(string $key): void
|
|
{
|
|
unset($this->notifications[$key]);
|
|
}
|
|
|
|
public function all(): array
|
|
{
|
|
return $this->notifications;
|
|
}
|
|
}
|