Skip to content

uzdevid/yii-runner-centrifugo

Yii

Yii RoadRunner Centrifugo


Latest Stable Version Total Downloads Build status Code Coverage Mutation testing badge Static analysis type-coverage psalm-level

The package is designed to process web sockets on the basis of Centrifugo and Roadrunner

Requirements

  • PHP 8.1 or higher.

Installation

The package could be installed with Composer:

composer require uzdevid/yii-runner-centrifugo

General usage

Centrifugo

Download binary file

Generate Centrifugo config file: config.json

./centrifugo genconfig

Example config

{
  "log": {
    "level": "debug"
  },
  "client": {
    "token": {
      "hmac_secret_key": "<secret>"
    },
    "allowed_origins": [
      "*"
    ],
    "proxy": {
      "connect": {
        "enabled": true,
        "endpoint": "grpc://127.0.0.1:30000",
        "timeout": "10s"
      },
      "refresh": {
        "enabled": true,
        "endpoint": "grpc://127.0.0.1:30000",
        "timeout": "3s"
      }
    }
  },
  "channel": {
    "namespaces": [
      {
        "name": "<channel>",
        "allow_subscribe_for_client": true,
        "allow_publish_for_client": true,
        "subscribe_proxy_enabled": true,
        "publish_proxy_enabled": true
      }
    ],
    "proxy": {
      "subscribe": {
        "endpoint": "grpc://127.0.0.1:30000",
        "timeout": "3s"
      },
      "publish": {
        "endpoint": "grpc://127.0.0.1:30000",
        "timeout": "3s"
      },
      "sub_refresh": {
        "endpoint": "grpc://127.0.0.1:30000",
        "timeout": "3s"
      }
    }
  },
  "admin": {
    "enabled": true,
    "password": "<password>",
    "secret": "<secret>"
  },
  "grpc_api": {
    "address": "127.0.0.1",
    "port": 30000
  }
}

We set up the proxy for all requests for our Roadrunner server at grpc://127.0.0.1:30000, according to the gRPC protocol

See also: https://centrifugal.dev/docs/server/proxy


RoadRunner

Download roadrunner binary file

Road runner example config: .rr.yaml

version: '3'

rpc:
    listen: tcp://127.0.0.1:6001

server:
    command: "php ./worker.php"
    relay: pipes

centrifuge:
    proxy_address: tcp://127.0.0.1:30000
    grpc_api_address: tcp://127.0.0.1:30000
    use_compressor: true

service:
    centrifuge:
        service_name_in_log: true
        remain_after_exit: true
        restart_sec: 1
        command: "./centrifugo"

We listen to the proxies in the address tcp://127.0.0.1:30000 from the Centrifugo server


Runner file

Create /worker.php file

use RoadRunner\Centrifugo\Request\RequestFactory;
use Spiral\RoadRunner\Worker;
use UzDevid\Yii\Runner\Centrifugo\CentrifugoApplicationRunner;
use Yiisoft\ErrorHandler\ErrorHandler;
use Yiisoft\ErrorHandler\Renderer\PlainTextRenderer;
use Yiisoft\Log\Logger;
use Yiisoft\Log\Target\File\FileTarget;

ini_set('display_errors', 'stderr');

require_once dirname(__DIR__) . '/vendor/autoload.php';

$logger = new Logger([new FileTarget(sprintf('%s/runtime/logs/centrifugo.log', __DIR__))]);
$errorHandler = new ErrorHandler($logger, new PlainTextRenderer());

$worker = Worker::create(logger: $logger);

$application = new CentrifugoApplicationRunner(
    rootPath: __DIR__,
    temporaryErrorHandler: $errorHandler,
    worker: $worker,
    requestFactory: new RequestFactory($worker),
    debug: true
);

$application->run();

Handlers

Handling connect request and response with specific payload

use UzDevid\Yii\Runner\Centrifugo\Handler\ConnectHandlerInterface;
use RoadRunner\Centrifugo\Payload\ConnectResponse;

class ConnectHandler implements ConnectHandlerInterface {
    public function handle(RequestInterface $request): void {
        // ...
        
        $request->respond(new ConnectResponse('user-id', null, ['ok' => true]))
    }
}

In the same way, implement the rest of the handlers:

  • ConnectHandlerInterface - called when a client connects to Centrifugo, so it's possible to authenticate user, return custom initial data to a client, subscribe connection to server-side channels, attach meta information to the connection, and so on. This proxy hook available for both bidirectional and unidirectional transports.
  • RefreshHandlerInterface - called when a client session is going to expire, so it's possible to prolong it or just let it expire. Can also be used as a periodical connection liveness callback from Centrifugo to the app backend. Works for bidirectional and unidirectional transports.
  • SubscribeHandlerInterface - called when clients try to subscribe on a channel, so it's possible to check permissions and return custom initial subscription data. Works for bidirectional transports only.
  • PublishHandlerInterface - called when a client tries to publish into a channel, so it's possible to check permissions and optionally modify publication data. Works for bidirectional transports only.
  • SubRefreshHandlerInterface - called when a client subscription is going to expire, so it's possible to prolong it or just let it expire. Can also be used just as a periodical subscription liveness callback from Centrifugo to app backend. Works for bidirectional and unidirectional transports.
  • InvalidRequestInterface - Handle invalid request
  • RpcHandlerInterface - called when a client sends RPC, you can do whatever logic you need based on a client-provided RPC method and data. Works for bidirectional transports only (and bidirectional emulation), since data is sent from client to the server in this case.

See also: https://centrifugal.dev/docs/server/proxy

Run RoadRunner

./rr serve

You can test the WebSocketing service or use the Client SDK

Documentation

If you need help or have a question, the Yii Forum is a good place for that. You may also check out other Yii Community Resources.

Maintained by UzDevid.

Follow updates

Official website Twitter Telegram Facebook Slack

About

No description, website, or topics provided.

Resources

License

Code of conduct

Contributing

Security policy

Stars

Watchers

Forks

Releases

No releases published

Sponsor this project

  •  

Packages

 
 
 

Contributors

Languages

Generated from yiisoft/package-template