2

I'm running a ratchet websocket server. Due to some complicated circumstances I need to be able to talk to this websocket server via my PHP Server in realtime not Javascript to be able to send it information that will then be passed on later to any clients connected to it.

I did some looking around on stackoverflow but everything is about how to create a websocket server with PHP which is not what I'm looking for.

Below is a visual of what I'm trying to achieve.

enter image description here

The key here is how to connect to a Websocket server like ratchet using PHP?


Things I have tried/considered:

I've considered using the serialization approach. This would be serializing in the database and unserializing. I'm not sure if this is better than this approach, please advise.

This is where I started : Ratchet Store Connection of User & Send Message Outside of Server Instance

Community
  • 1
  • 1
Joseph Astrahan
  • 8,659
  • 12
  • 83
  • 154
  • Please let me know why the downvote please so I can give a better detailed question. I believe I met all the criteria for a good question, I'll further change my question to refer to another this is based on. – Joseph Astrahan Mar 30 '17 at 04:33
  • I recently stumbled upon this, https://github.com/paragi/PHP-websocket-client, but I can't seem to get it to work never wants to connect to my websocket server? – Joseph Astrahan Mar 30 '17 at 05:02

1 Answers1

2

I would suggest using REST as API layer for communication between your Symfony app and Ratchet app. Because it doesn't make much sense to use Websocket from your Symfony app. Websockets are used for bidirectional real-time communication, whereas you only need to send a piece of data from your Symfony app. For this purpose, HTTP REST API would be more convenient. To wrap it up, in your Ratchet app you use 2 servers (Ratchet allows creating as many servers as you want within a single app): web-socket server and http-server. In your Symfony app, you send traditional HTTP requests to your Ratchet server.

enter image description here

You can create multiple Ratchet servers in a single app like so:

// 1. Create the event loop
$loop = React\EventLoop\Factory::create();

// 2. Create servers
// websocket
$webSock = new React\Socket\Server($loop);
new Ratchet\Server\IoServer(
    new Ratchet\Http\HttpServer(
        new Ratchet\WebSocket\WsServer( $wsConnectionsHandler )
    ),
    $webSock
);
$webSock->listen($portWS, '0.0.0.0');

// http
$httpSock = new React\Socket\Server($loop);
new Ratchet\Server\IoServer(
    new Ratchet\Http\HttpServer(
        $HTTPConnectionsHandler
    ),
    $httpSock
);
$httpSock->listen($portHTTP, '0.0.0.0');

// 3. Run the loop
$loop->run();

How do I pass the information from the http server to the websocket server?

React/Ratchet app is an event-driven app, like a typical NodeJS app. So the best way for the components of the app to communicate with each other is to dispatch/subscribe events. For example, you create $eventDispatcher object, pass it to every component (http-handler & ws-handler), and then use $eventDispatcher->subscibe(eventName, func) and $eventDispatcher->emit(eventName, data) to subscribe to events and dispatch them accordingly.


If you are not convinced, then you need to use a Websocket Client library to connect to Websocket server. There are a few of them, just google it. I personally never used a PHP websocket-client library, so I can't recommend any.

pumbo
  • 3,646
  • 2
  • 25
  • 27
  • I think I finally get what you are saying, how do I send traditional http requests to the ratchet server? If I can do this, this will work also and be better I agree. Will my HTTP server still be able to reference the connections from the webSocket server though? – Joseph Astrahan Mar 30 '17 at 05:08
  • How do I pass the information from the http server to the websocket server? Thanks for the image by the way – Joseph Astrahan Mar 30 '17 at 05:38
  • I need to do this so I can update the client in realtime of the change from my symfony app – Joseph Astrahan Mar 30 '17 at 05:39
  • I think I see how this works then. The trick will be creating a global reference to the clients variable used to store connections for websockets then somewhere so the http server can respond correctly to the websocket server. I'll give this a try, and further examples of course would help showing this process, but I think I can do this. Give me an hour to experiment. – Joseph Astrahan Mar 30 '17 at 05:46
  • Just got your message about event subscribers, do you have any actual examples of using them in code by chance? In meantime I'll try guessing from the documentation. – Joseph Astrahan Mar 30 '17 at 06:05
  • Quick other question how would my symfony app send the HTTP response to the server we just made with ratchet? should I use cURL? Thanks again for all your detailed answers – Joseph Astrahan Mar 30 '17 at 06:07
  • >> how would my symfony app send the HTTP request to the server It's up to you. You can use CURL, or a library like `GuzzleHTTP` if you like – pumbo Mar 30 '17 at 06:11
  • Unfortunately I don't have code example. I developed a similar app, but it was a private project. – pumbo Mar 30 '17 at 06:15
  • Ok give me some time to try this out, I just got the http server working at same time now as the other, so trying some stuff out :). Anything about that event dispatcher will help though, I'll see if I can find more info on that. That is only part I'm stuck on now. – Joseph Astrahan Mar 30 '17 at 06:17
  • How do I pass the event dispatcher object to the http and websocket resources? – Joseph Astrahan Mar 30 '17 at 06:45
  • I'm reading this now in meantime, still new to event subscribers but very interesting (http://symfony.com/doc/current/components/event_dispatcher.html) – Joseph Astrahan Mar 30 '17 at 07:14
  • I got it working! thanks so much :), your ideas were perfect. I'll show how I implemented this in my other answer making sure to give you credit here. – Joseph Astrahan Mar 30 '17 at 09:58