مكتبة PHP للتفاعل مع Pusher Channels HTTP API.
قم بالتسجيل على https://pusher.com واستخدم بيانات اعتماد التطبيق داخل تطبيقك كما هو موضح أدناه.
للإبلاغ عن المشكلات والأخطاء وطلبات الميزات، فلا تتردد في فتح طلب سحب أو فتح مشكلة. إذا لم تتلق ردًا في الوقت المناسب، فلا تتردد في مراجعة بوابة الدعم الخاصة بنا.
يمكنك الحصول على مكتبة Pusher Channels PHP عبر حزمة مؤلفة تسمى pusher-php-server
. راجع https://packagist.org/packages/pusher/pusher-php-server
$ composer require pusher/pusher-php-server
أو قم بإضافة ملف composer.json
:
"require" : {
"pusher/pusher-php-server" : " ^7.2 "
}
ثم قم بتشغيل composer update
.
استخدم بيانات الاعتماد من تطبيق Pusher Channels الخاص بك لإنشاء مثيل PusherPusher
جديد.
$ app_id = ' YOUR_APP_ID ' ;
$ app_key = ' YOUR_APP_KEY ' ;
$ app_secret = ' YOUR_APP_SECRET ' ;
$ app_cluster = ' YOUR_APP_CLUSTER ' ;
$ pusher = new Pusher Pusher ( $ app_key , $ app_secret , $ app_id , [ ' cluster ' => $ app_cluster ]);
المعلمة الرابعة هي مصفوفة $options
. الخيارات الإضافية هي:
scheme
- على سبيل المثال http أو httpshost
- المضيف، على سبيل المثال api.pusherapp.com. لا يوجد شرطة مائلة للأمامport
- منفذ httppath
- بادئة لإلحاق كافة مسارات الطلب. يكون هذا مفيدًا فقط إذا كنت تقوم بتشغيل المكتبة مقابل نقطة نهاية تتحكم فيها بنفسك (على سبيل المثال، وكيل يقوم بالتوجيه بناءً على بادئة المسار).timeout
- مهلة HTTPuseTLS
- خيار سريع لاستخدام نظام https والمنفذ 443.cluster
- حدد المجموعة التي يعمل منها التطبيق.encryption_master_key_base64
- مفتاح طويل مكون من 32 حرفًا. يُستخدم هذا المفتاح، بالإضافة إلى اسم القناة، لاشتقاق مفاتيح التشفير لكل قناة. يتم استخدام المفاتيح لكل قناة لتشفير بيانات الأحداث على القنوات المشفرة.على سبيل المثال، سيتم إجراء المكالمات افتراضيًا عبر HTTPS. لاستخدام HTTP العادي، يمكنك ضبط useTLS على false:
$ options = [
' cluster ' => $ app_cluster ,
' useTLS ' => false
];
$ pusher = new Pusher Pusher ( $ app_key , $ app_secret , $ app_id , $ options );
الأسلوب الموصى به للتسجيل هو استخدام مسجل متوافق مع PSR-3 ينفذ PsrLogLoggerInterface
. يقوم كائن Pusher
بتنفيذ PsrLogLoggerAwareInterface
، مما يعني أنه يمكنك استدعاء setLogger(LoggerInterface $logger)
لتعيين مثيل المسجل.
// where $logger implements `LoggerInterface`
$ pusher -> setLogger ( $ logger );
تستخدم هذه المكتبة Guzzle داخليًا لإجراء مكالمات HTTP. يمكنك تمرير مثيل Guzzle الخاص بك إلى مُنشئ Pusher:
$ custom_client = new GuzzleHttp Client ();
$ pusher = new Pusher Pusher (
$ app_key ,
$ app_secret ,
$ app_id ,
[],
$ custom_client
);
يتيح لك هذا تمرير البرامج الوسيطة الخاصة بك، راجع الاختبارات للحصول على مثال.
لتشغيل حدث على قناة واحدة أو أكثر، استخدم وظيفة trigger
.
$ pusher -> trigger ( ' my-channel ' , ' my_event ' , ' hello world ' );
$ pusher -> trigger ([ ' channel-1 ' , ' channel-2 ' ], ' my_event ' , ' hello world ' );
من الممكن أيضًا إرسال أحداث متعددة باستخدام استدعاء واجهة برمجة التطبيقات (API) واحد (بحد أقصى 10 أحداث لكل مكالمة على مجموعات متعددة المستأجرين):
$ batch = [];
$ batch [] = [ ' channel ' => ' my-channel ' , ' name ' => ' my_event ' , ' data ' => [ ' hello ' => ' world ' ]];
$ batch [] = [ ' channel ' => ' my-channel ' , ' name ' => ' my_event ' , ' data ' => [ ' myname ' => ' bob ' ]];
$ pusher -> triggerBatch ( $ batch );
يحتوي كل من trigger
و triggerBatch
على نظيرات غير متزامنة في triggerAsync
و triggerBatchAsync
. تُرجع هذه الوظائف وعود Guzzle التي يمكن ربطها بـ ->then
:
$ promise = $ pusher -> triggerAsync ([ ' channel-1 ' , ' channel-2 ' ], ' my_event ' , ' hello world ' );
$ promise -> then ( function ( $ result ) {
// do something with $result
return $ result ;
});
$ final_result = $ promise -> wait ();
يتم تحويل المصفوفات تلقائيًا إلى تنسيق JSON:
$ array [ ' name ' ] = ' joe ' ;
$ array [ ' message_count ' ] = 23 ;
$ pusher -> trigger ( ' my_channel ' , ' my_event ' , $ array );
سيكون ناتج هذا:
" {'name': 'joe', 'message_count': 23} "
لتجنب التكرارات، يمكنك اختياريًا تحديد معرف مأخذ التوصيل للمرسل أثناء تشغيل الحدث:
$ pusher -> trigger ( ' my-channel ' , ' event ' , ' data ' , [ ' socket_id ' => $ socket_id ]);
$ batch = [];
$ batch [] = [ ' channel ' => ' my-channel ' , ' name ' => ' my_event ' , ' data ' => [ ' hello ' => ' world ' ], [ ' socket_id ' => $ socket_id ]];
$ batch [] = [ ' channel ' => ' my-channel ' , ' name ' => ' my_event ' , ' data ' => [ ' myname ' => ' bob ' ], [ ' socket_id ' => $ socket_id ]];
$ pusher -> triggerBatch ( $ batch );
من الممكن طلب سمات حول القنوات التي تم النشر عليها باستخدام معلمة info
:
$ result = $ pusher -> trigger ( ' my-channel ' , ' my_event ' , ' hello world ' , [ ' info ' => ' subscription_count ' ]);
$ subscription_count = $ result -> channels [ ' my-channel ' ]-> subscription_count ;
$ batch = [];
$ batch [] = [ ' channel ' => ' my-channel ' , ' name ' => ' my_event ' , ' data ' => [ ' hello ' => ' world ' ], ' info ' => ' subscription_count ' ];
$ batch [] = [ ' channel ' => ' presence-my-channel ' , ' name ' => ' my_event ' , ' data ' => [ ' myname ' => ' bob ' ], ' info ' => ' user_count,subscription_count ' ];
$ result = $ pusher -> triggerBatch ( $ batch );
foreach ( $ result -> batch as $ i => $ attributes ) {
echo " channel: { $ batch [ $ i ][ ' channel ' ]} , name: { $ batch [ $ i ][ ' name ' ]}" ;
if ( isset ( $ attributes -> subscription_count )) {
echo " , subscription_count: { $ attributes -> subscription_count }" ;
}
if ( isset ( $ attributes -> user_count )) {
echo " , user_count: { $ attributes -> user_count }" ;
}
echo PHP_EOL ;
}
إذا كانت بياناتك مشفرة بالفعل بتنسيق JSON، فيمكنك تجنب خطوة التشفير الثانية عن طريق تعيين الوسيط السادس على أنه صحيح، كما يلي:
$ pusher -> trigger ( ' my-channel ' , ' event ' , ' data ' , [], true );
لمصادقة المستخدمين على قنوات Pusher في تطبيقك، يمكنك استخدام وظيفة authenticateUser
:
$ pusher -> authenticateUser ( ' socket_id ' , ' user-id ' );
لمزيد من المعلومات، راجع مصادقة المستخدمين.
للسماح للمستخدمين بالوصول إلى القنوات الخاصة على Pusher، يمكنك استخدام وظيفة authorizeChannel
:
$ pusher -> authorizeChannel ( ' private-my-channel ' , ' socket_id ' );
لمزيد من المعلومات، راجع تفويض المستخدمين.
يشبه استخدام قنوات الحضور القنوات الخاصة، ولكن يمكنك تحديد بيانات إضافية لتحديد هذا المستخدم المحدد:
$ pusher -> authorizePresenceChannel ( ' presence-my-channel ' , ' socket_id ' , ' user_id ' , ' user_info ' );
لمزيد من المعلومات، راجع تفويض المستخدمين.
توفر هذه المكتبة طريقة للتحقق من أن خطافات الويب التي تتلقاها من Pusher هي في الواقع خطافات ويب أصلية من Pusher. كما يوفر هيكلًا لتخزينها. هناك طريقة مساعدة تسمى webhook
تمكنك من ذلك. قم بتمرير رؤوس الطلب ونصه، وسيقوم بإرجاع كائن Webhook مع الأحداث التي تم التحقق منها. إذا لم تتمكن المكتبة من التحقق من صحة التوقيع، فسيتم طرح استثناء بدلاً من ذلك.
$ webhook = $ pusher -> webhook ( $ request_headers , $ request_body );
$ number_of_events = count ( $ webhook -> get_events ());
$ time_received = $ webhook -> get_time_ms ();
تدعم هذه المكتبة التشفير الشامل لقنواتك الخاصة. وهذا يعني أنك أنت وعملائك المتصلين فقط هم من سيتمكنون من قراءة رسائلك. لا يمكن للدافع فك تشفيرها. ويمكنك تفعيل هذه الميزة باتباع الخطوات التالية:
يجب عليك أولاً إعداد القنوات الخاصة. يتضمن ذلك إنشاء نقطة نهاية ترخيص على الخادم الخاص بك.
بعد ذلك، قم بإنشاء مفتاح التشفير الرئيسي المكون من 32 بايت، ثم قم بتشفيره باستخدام Base64 وتخزينه بشكل آمن. هذا سر ويجب ألا تشاركه مع أي شخص أبدًا. ولا حتى انتهازي.
لإنشاء مفتاح مناسب من مصدر عشوائي جيد، يمكنك استخدام الأمر openssl
:
openssl rand -base64 32
حدد مفتاح التشفير الرئيسي الخاص بك عند إنشاء عميل Pusher الخاص بك:
$ pusher = new Pusher Pusher (
$ app_key ,
$ app_secret ,
$ app_id ,
[
' cluster ' => $ app_cluster ,
' encryption_master_key_base64 ' => " <your base64 encoded master key> "
]
);
القنوات التي ترغب في استخدام التشفير من طرف إلى طرف يجب أن تكون مسبوقة بـ private-encrypted-
.
اشترك في هذه القنوات في عميلك، وقد انتهيت! يمكنك التحقق من أنه يعمل عن طريق التحقق من وحدة تصحيح الأخطاء على https://dashboard.pusher.com/ ورؤية النص المشفر.
ملاحظة هامة: لن يؤدي هذا إلى تشفير الرسائل على القنوات التي لم يسبقها private-encrypted-
.
القيود : لا يمكنك تشغيل حدث واحد على مزيج من القنوات غير المشفرة والمشفرة في استدعاء trigger
، على سبيل المثال
$ data [ ' name ' ] = ' joe ' ;
$ data [ ' message_count ' ] = 23 ;
$ pusher -> trigger ([ ' channel-1 ' , ' private-encrypted-channel-2 ' ], ' test_event ' , $ data );
الأساس المنطقي: يتم تعيين الأساليب الموجودة في هذه المكتبة مباشرة لطلبات واجهة برمجة تطبيقات HTTP للقنوات الفردية. إذا سمحنا بتشغيل حدث واحد على قنوات متعددة (بعضها مشفر، وبعضها غير مشفر)، فسوف يتطلب الأمر طلبين من واجهة برمجة التطبيقات: أحدهما يتم فيه تشفير الحدث للقنوات المشفرة، والآخر حيث يكون الحدث غير مشفر للقنوات غير المشفرة.
قم أولاً بتعيين نقطة نهاية ترخيص القناة في تطبيق JS الخاص بك عند إنشاء كائن Pusher:
var pusher = new Pusher ( "app_key" ,
// ...
channelAuthorization : {
endpoint : "/presenceAuth.php" ,
} ,
) ;
بعد ذلك، قم بإنشاء ما يلي في الوجودAuth.php:
<?php
header ( ' Content-Type: application/json ' );
if ( isset ( $ _SESSION [ ' user_id ' ])) {
$ stmt = $ pdo -> prepare ( " SELECT * FROM `users` WHERE id = :id " );
$ stmt -> bindValue ( ' :id ' , $ _SESSION [ ' user_id ' ], PDO :: PARAM_INT );
$ stmt -> execute ();
$ user = $ stmt -> fetch ();
} else {
die ( json_encode ( ' no-one is logged in ' ));
}
$ pusher = new Pusher Pusher ( $ key , $ secret , $ app_id );
$ presence_data = [ ' name ' => $ user [ ' name ' ]];
echo $ pusher -> authorizePresenceChannel ( $ _POST [ ' channel_name ' ], $ _POST [ ' socket_id ' ], $ user [ ' id ' ], $ presence_data );
ملاحظة: يفترض هذا أنك تقوم بتخزين المستخدمين في جدول يسمى users
وأن هؤلاء المستخدمين لديهم عمود name
. ويفترض أيضًا أن لديك آلية تسجيل دخول تخزن user_id
الخاص بالمستخدم الذي قام بتسجيل الدخول في الجلسة.
$ pusher -> getChannelInfo ( $ name );
من الممكن أيضًا الحصول على معلومات حول القناة من Channels HTTP API.
$ info = $ pusher -> getChannelInfo ( ' channel-name ' );
$ channel_occupied = $ info -> occupied ;
بالنسبة لقنوات الحضور، يمكنك أيضًا الاستعلام عن عدد المستخدمين المتميزين المشتركين حاليًا في هذه القناة (قد يشترك مستخدم واحد عدة مرات، ولكن سيتم احتسابه كمستخدم واحد فقط):
$ info = $ pusher -> getChannelInfo ( ' presence-channel-name ' , [ ' info ' => ' user_count ' ]);
$ user_count = $ info -> user_count ;
إذا قمت بتمكين القدرة على الاستعلام عن عدد subscription_count
(عدد الاتصالات المشتركة حاليًا في هذه القناة)، فيمكنك الاستعلام عن هذه القيمة على النحو التالي:
$ info = $ pusher -> getChannelInfo ( ' presence-channel-name ' , [ ' info ' => ' subscription_count ' ]);
$ subscription_count = $ info -> subscription_count ;
$ pusher -> getChannels ();
من الممكن أيضًا الحصول على قائمة القنوات لأحد التطبيقات من Channels HTTP API.
$ result = $ pusher -> getChannels ();
$ channel_count = count ( $ result -> channels ); // $channels is an Array
$ pusher -> getChannels ([ ' filter_by_prefix ' => ' some_filter ' ]);
من الممكن أيضًا الحصول على قائمة بالقنوات بناءً على بادئة اسمها. للقيام بذلك، تحتاج إلى توفير معلمة $options
للمكالمة. في المثال التالي، سوف تقوم المكالمة بإرجاع قائمة بجميع القنوات ذات بادئة presence-
. هذه فكرة لجلب قائمة بجميع قنوات التواجد.
$ results = $ pusher -> getChannels ([ ' filter_by_prefix ' => ' presence- ' ]);
$ channel_count = count ( $ result -> channels ); // $channels is an Array
ويمكن تحقيق ذلك أيضًا باستخدام وظيفة pusher->get
العامة:
$ pusher -> get ( ' /channels ' , [ ' filter_by_prefix ' => ' presence- ' ]);
لا تدعم HTTP API التي تعرض قائمة القنوات إعادة عدد الاشتراكات مع كل قناة. وبدلاً من ذلك، يمكنك جلب هذه البيانات بالتكرار على كل قناة وتقديم طلب آخر. كن حذرًا: هذا الأسلوب يستهلك (عدد القنوات + 1) من الرسائل!
<?php
$ subscription_counts = [];
foreach ( $ pusher -> getChannels ()-> channels as $ channel => $ v ) {
$ subscription_counts [ $ channel ] =
$ pusher -> getChannelInfo (
$ channel , [ ' info ' => ' subscription_count ' ]
)-> subscription_count ;
}
var_dump ( $ subscription_counts );
$ results = $ pusher -> getPresenceUsers ( ' presence-channel-name ' );
$ users_count = count ( $ results -> users ); // $users is an Array
ويمكن تحقيق ذلك أيضًا باستخدام وظيفة pusher->get
العامة:
$ response = $ pusher -> get ( ' /channels/presence-channel-name/users ' );
$response
بالتنسيق:
Array (
[body] => { " users " :[{ " id " :"a_user_id"}]}
[status] => 200
[result] => Array (
[users] => Array (
[ 0 ] => Array (
[id] => a_user_id
),
/* Additional users */
)
)
)
$ pusher -> get ( $ path , $ params );
يُستخدم لإجراء استعلامات GET
مقابل Channels HTTP API. يعالج المصادقة.
الاستجابة عبارة عن مصفوفة ترابطية مع فهرس result
. تعتمد محتويات هذا الفهرس على طريقة HTTP التي تم استدعاؤها. ومع ذلك، فإن خاصية status
التي تسمح برمز حالة HTTP موجودة دائمًا وسيتم تعيين خاصية result
إذا كان رمز الحالة يشير إلى استدعاء ناجح لواجهة برمجة التطبيقات (API).
$ response = $ pusher -> get ( ' /channels ' );
$ http_status_code = $ response [ ' status ' ];
$ result = $ response [ ' result ' ];
يتطلب فبونيت.
composer install
tests
config.example.php
إلى config.php
واستبدل القيم ببيانات اعتماد القنوات الصالحة أو قم بإنشاء متغيرات البيئة.composer exec phpunit
لتشغيل كافة الاختبارات. حقوق الطبع والنشر 2014، انتهازي. مرخص بموجب ترخيص MIT: https://www.opensource.org/licenses/mit-license.php
حقوق الطبع والنشر 2010، سكويكس. مرخص بموجب ترخيص MIT: https://www.opensource.org/licenses/mit-license.php