Event Bus ونمط Observer في PHP: التنفيذ والأمثلة

مدرب بايثون أونلاين للمبتدئين

تعلم Python بسهولة دون إرهاق نظري. حل مهام عملية مع التحقق التلقائي واكتب الكود مباشرة في المتصفح.

ابدأ الدورة

Event Bus ونمط Observer في PHP



في تطوير تطبيقات الويب الحديثة باستخدام PHP، غالبًا ما تنشأ الحاجة إلى الاستجابة بمرونة للأحداث المختلفة: إرسال البريد الإلكتروني بعد التسجيل، تسجيل إجراءات المستخدم، تحديث ذاكرة التخزين المؤقت عند تغيير البيانات. لهذه الأغراض، يعتبر نمط Observer وتوسعته - Event Bus (ناقل الأحداث) مثاليين.



نمط Observer: الأساسيات



نمط Observer (المراقب) - هو نمط تصميم سلوكي ينشئ آلية اشتراك تسمح للكائنات بمراقبة الأحداث التي تحدث في كائنات أخرى والتفاعل معها. المكونات الأساسية:



  • Subject (الموضوع) - الكائن الذي يولد الأحداث
  • Observer (المراقب) - الكائن الذي يستجيب للأحداث
  • Event (الحدث) - معلومات حول الإجراء الذي حدث


Event Bus: تطور Observer



Event Bus - هو ناقل مركزي يدير جميع الأحداث في التطبيق. على عكس Observer التقليدي حيث يكون الاشتراك مرتبطًا بشكل صارم بالموضوع، يوفر Event Bus:



  • ربط ضعيف بين المرسلين والمستقبلين
  • إمكانية إضافة/إزالة المعالجات أثناء التنفيذ
  • وصول عالمي إلى الناقل من أي جزء من التطبيق
  • اختبار وتصحيح أسهل


مثال على تنفيذ Event Bus في PHP



لنقم بإنشاء تنفيذ بسيط ولكنه وظيفي لـ Event Bus، متوافق مع PSR-14 (Event Dispatcher).



<?php// واجهة الحدثinterface EventInterface{    public function getName(): string;}

// حدث أساسيclass UserRegisteredEvent implements EventInterface{ public function __construct( private string $email, private string $username ) {}

public function getName(): string { return 'user.registered'; }

public function getEmail(): string { return $this->email; }

public function getUsername(): string { return $this->username; }}

// واجهة المعالجinterface EventHandlerInterface{ public function handle(EventInterface $event): void;}

// Event Busclass EventBus{ private array $listeners = [];

public function addListener(string $eventName, EventHandlerInterface $handler): void { $this->listeners[$eventName][] = $handler; }

public function removeListener(string $eventName, EventHandlerInterface $handler): void { if (!isset($this->listeners[$eventName])) { return; }

$this->listeners[$eventName] = array_filter( $this->listeners[$eventName], fn($h) => $h !== $handler ); }

public function dispatch(EventInterface $event): void { $eventName = $event->getName();

if (!isset($this->listeners[$eventName])) { return; }

foreach ($this->listeners[$eventName] as $handler) { $handler->handle($event); } }}?>


الاستخدام العملي



الآن لنقم بإنشاء معالجات ونوضح عمل الناقل:



<?php// معالج إرسال البريد الإلكترونيclass SendWelcomeEmailHandler implements EventHandlerInterface{    public function handle(EventInterface $event): void    {        if (!$event instanceof UserRegisteredEvent) {            return;        }

echo "إرسال بريد ترحيبي إلى {$event->getEmail()}"; // mail($event->getEmail(), 'مرحبًا بك!', '...'); }}

// معالج التسجيلclass LogUserRegistrationHandler implements EventHandlerInterface{ public function handle(EventInterface $event): void { if (!$event instanceof UserRegisteredEvent) { return; }

توصيات