HTML5 Event Source API and node.js | How to send the stream to the correct client?

1.9k Views Asked by At

For some reason, which I think there is no point mentioning, i can't use socket.io and i decided to use HTML5 Event Source API (Server-sent events) to sent a message to the client. The message tells the client that his payments has been received via a third-party callback.

I've got an ID that identifies each client and it is also received in the callback. I've got two questions so far:

  1. I suppose every message sent is broadcasted to all the clients. Is there a way to select a specific client by his ID?

    Currently i am implementing this functionality in the client using an if sentence, but if i could sent the message directly form server to the client to improve performance would be great

  2. When i close the connection on the client i guess i am not closing all the connections stablished, isn't it?

My code:

Node.js

app.get('/payments', function(req, res) {
    res.header("Access-Control-Allow-Origin", "*");
    res.header("Access-Control-Allow-Headers", "X-Requested-With");
    
    res.writeHead(200, {
        'Content-Type': 'text/event-stream',
        'Connection': 'keep-alive',
        'Cache-Control': 'no-cache',
    });

    ee.on("payment", function (data) {
            res.write("data: "
                + JSON.stringify({'wallet': data.address, 'refund_address': data.refund_address,'payment_status': 'paid'})    
                + "\n\n"
            );
    });
});

Client

              var source = new EventSource("/payments");
              source.addEventListener('message', function(e) { 
              if (e.origin == 'http://localhost:3000') {
                      var data = JSON.parse(e.data);
                          if (btcwalletdir == data.wallet) { //each client filter  
                                  // do whatever here                                    
                                  source.close();
                           }   
                      return;
                     }  
                  }, false);

Is it a valid solution for a production environment?

Regards,

1

There are 1 best solutions below

1
On BEST ANSWER

Regarding EventSource each client has its own connection. Each time someone access that endpoint it will have a request/response assigned to it, so when you do res.write you are only writing to one client.

But of course if you broadcast the event "payment" to every connection, each one will send the json message to the respective client. So you need to find a way to only send the data to the correct connection (ex adding a user/connection id to the data you emit and storing the res objects in an array/object)