PHP WebSockets integration

Intro

Probably you heard about low performance with PHP Websockets implementation. That is why most developers decided to use NodeJS or C++ implementation. However, since PHP7 has been released we have many improvements. The most improvement is performance. And finally, we can use PHP to build our WebSockets server.

This screenshot demonstrates real production server resources used by WebSocket server on a website with more than 3000 users online at one time.

Integration scheme

Here is the steps that you have to do:

  1. Create WebSocket server
  2. Specify unix socket. What is unix socket? UNIX socket is some kind of local communication link. You can read and write some stream info into it. In our case, we will write data into the socket from PHP (in our case Laravel) application.
  3. Write an event listener on the backend. For example, you can write to a socket that the user connected to the website.
  4. Write frontend part (WebSocket client) for processing received data from the WebSocket server.

Deep into Ollyxar WebSockets

We already have a WebSockets-server component with the most common methods. So you can use it without diving into the code understandings. But if you want to know how it’s work – here is an explanation:

The component WebSockets use pctnl_fork function to split the main process into structure above. The main process, called Master, does not handle connections. It just dispatches routes and signals between Workers – processes that handle connections with clients and Connector – Unix socket server that can accept data from external sources.

We’ve implemented a Laravel chat based on WebSockets. You can try it by yourself.

Warning! If your clients have unstable connections – you have to wrap all methods with checker-method. The checker method has to check the connection. Because operation fwrite will fail if the connection was closed.

There is a simple hack to avoid exception with fwrite: you can use @ symbol before fwrite and remove Laravel’s exception handler with set_exception_handler(null);