Skip to content

Latest commit

 

History

History
276 lines (208 loc) · 9.21 KB

index.md

File metadata and controls

276 lines (208 loc) · 9.21 KB

Getting started with Woketo

Installation

Checkout the README to learn about installation.

Usage

Server

How it works

Basically, you just need to create a class that will handle websocket messages and process them. You give this an instance of this class to Woketo that call onMessage method. This class must implements the MessageHandlerInterface.

Here is how your class may look:

<?php
use Nekland\Woketo\Message\MessageHandlerInterface;
use Nekland\Woketo\Core\AbstractConnection;
use Nekland\Woketo\Exception\WebsocketException;

class MyMessageHandler implements MessageHandlerInterface
{
    public function onConnection(AbstractConnection $connection)
    {
        // This method is called when a new client is connected to your server
    }
    
    public function onMessage(string $data, AbstractConnection $connection)
    {
        // This method is called when a text message is sent
    }
    
    public function onBinary(string $data, AbstractConnection $connection)
    {
        // This method is called when a binary message is sent
    }
    
    public function onError(WebsocketException $e, AbstractConnection $connection)
    {
        // This method is called when an error occurs
    }
}

The behavior of any of this methods is up to you.

To use your class it's pretty easy:

<?php

$server = new WebSocketServer(1337, '127.0.0.1', []);
$server->setMessageHandler(new YourMessageHandler(), '/path');
$server->start();

The WebSocketServer instantiation takes the following parameters:

  • 1337: the port you want to bind your server on (notice that for low ports you need root rights)
  • "127.0.0.1": the host you bind on, this is the default value and what you need most part of the time
  • []: an (optional) array of configuration option documented in the configuration reference

The setMessageHandler method takes 2 parameters:

  • Your message handler
  • The path on the websocket server it will be trigger ws://127.0.0.1:1337/path

The Connection object has the following methods you can use:

  • write($message, $opCode = Frame::OP_TEXT), you may change to Frame::OP_BINARY if you want to send binary data
  • getIp(), that returns the current IP
  • getLogger(), that returns the logger of woketo

Client

The client usage is as simple as is the server usage. First you create your message handler:

<?php
use Nekland\Woketo\Message\MessageHandlerInterface;
use Nekland\Woketo\Core\AbstractConnection;
use Nekland\Woketo\Exception\WebsocketException;

class MyMessageHandler implements MessageHandlerInterface
{
    public function onConnection(AbstractConnection $connection)
    {
        // This method is called when a new client is connected to your server
    }
    
    public function onMessage(string $data, AbstractConnection $connection)
    {
        // This method is called when a text message is sent
    }
    
    public function onBinary(string $data, AbstractConnection $connection)
    {
        // This method is called when a binary message is sent
    }
    
    public function onError(WebsocketException $e, AbstractConnection $connection)
    {
        // This method is called when an error occurs
    }

    public function onDisconnect(AbstractConnection $connection)
    {
        // This method is called on server disconnection
    }
}

You can then run your client:

$client = new WebSocketClient('wss://echo.websocket.org:443/echo', []);
$client->start(new MyMessageHandler);

The WebSocketClient instantiation takes the following parameters:

  • "wss://echo.websocket.org:443/echo": a WebSocket URL: the protocol (ws or wss), the host (echo.websocket.org), the port (443), the URI (echo)
  • []: an (optional) array of configuration option documented in the configuration reference

Use it your way

Here are some helpers you can use depending on your use-case:

  • You want to create a server that only supports text messages: extends the TextMessageHandler class
  • You want to create a server that only supports binary messages: extends the BinaryMessageHandler class
  • You want to supports both message types without care about the connection or error events: extends the SimpleMessageHandler class

Of course you can redefine the method you want from MessageHandlerInterface on any of your message handler as they implement it.

Configuration Reference

Server configuration

The configuration is split in some parts:

  • The frame key configures the way Frames are managed
  • The message key configures the way Frames are stacked
  • The messageHandlers key contains your custom message handler, checkout the message handler doc
  • The prod key defines if your running environment is prod or not (similar to debug parameter in some environment)
<?php

$defaultConfiguration = [
    'frame'           => [
        'maxPayloadSize' => 524288,   // 0.5 MiB per Frame
    ],
    'message'         => [
        'maxMessagesBuffering' => 100 // 100 * 0.5 MiB max in memory
    ],
    'messageHandlers' => [],          // Empty by default, you can add some
    'prod' => true,                   // When set to false, it allows you to launch woketo with xdebug
    'ssl' => true,                    // to use wss
    'certFile' => '',                 // pem file, see ssl doc section for more details
    'sslContextOptions' => [],        // PHP SSL configuration see http://php.net/manual/fr/context.ssl.php
];

Client configuration

The configuration is split in some parts:

  • The frame key configures the way Frames are managed
  • The message key configures the way Frames are stacked
  • The prod key defines if your running environment is prod or not (similar to debug parameter in some environment)
<?php

$defaultConfiguration = [
    'frame'           => [
        'maxPayloadSize' => 524288,   // 0.5 MiB per Frame
    ],
    'message'         => [
        'maxMessagesBuffering' => 100 // 100 * 0.5 MiB max in memory
    ],
    'prod' => true,                   // When set to false, it allows you to launch woketo with xdebug
    'dns' => '',                      // Server address for DNS resolution (google by default)
    'ssl' => [],                      // PHP SSL configuration see http://php.net/manual/fr/context.ssl.php
];

Cookbooks

Logs

Woketo provides a custom logger but you may want to log with yours. It's easy as Woketo uses psr-3 log system.

<?php

$server = new WebSocketServer(1337);
$server->setLogger($myLogger);
$server->run();

Notice that the logger you give will be accessible from Connection::getLogger().

Message Handlers

A message handler is an object you can re-use that handle a specific type of message and throw a specific related exception or answer a close message if needed. This class must implement Nekland\Woketo\Rfc6455\MessageHandler\Rfc6455MessageHandlerInterface.

Please consider that Woketo only catches WebsocketException which mean that if you need to throw an exception, that needs to be catch, it must have this type.

WebSocket Secured (alias WSS)

In new apps you often use https. So you should use wss with WebSockets to secure data exchange. Woketo supports wss out of the box, you just need to add the related options (ssl and certFile).

You should instanciate woketo like this:

$server = new \Nekland\Woketo\Server\WebSocketServer(9001, '127.0.0.1', [
    'ssl' => true,
    'certFile' => 'path/to/certificate/cert.pem',
    'sslContextOptions' => [
        'verify_peer' => false,
        'allow_self_signed' => true
    ]
]);

❓ Why is there only one cert file required while I have 2 files (cert and private key) ?

PHP uses a PEM formatted certificate that contains the certificate and the private key.

Here is a way to generate your PEM formatted certificate for a local usage:

openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout acme.key -out acme.crt
cat acme.key > acme.pem
cat acme.crt >> acme.pem

Optimization

Libevent

Woketo is based on ReactPHP and as ReactPHP is able to run a loop by itself, so woketo is. But something good to note is that you can install the PHP extension libevent to get better performance for your event loop. You use Woketo exactly the same with libevent, it will just be faster and safer.

Learn more about libevent

Contributing to the development of Woketo

There is some documentation about how to contribute in CONTRIBUTE.md and some help for developers in dev.md.