SSE Push Event Hub and Client

Version 1.0.3 (Compatible with OutSystems 11)
Published on 3 Jul (3 weeks ago) by 
5.0
 (1 rating)

SSE Push Event Hub and Client

Documentation

Detailed description

The SSE Server Hub allows for HTTP Client Requests (through a Rest Expose API) to be persisted for Event Streaming as per protocol1. This is accomplished by switching the mime-type response to the appropriate text/event-stream and flushing the messages complying to the event source format2.

The SSE Client implements the Event Source JS Interface containing the Server Sent Event API, also per protocol3.

Effectively, no third parties are required for Server Push/Messaging.

Please refer to the Documentation tab for further details.

1 https://html.spec.whatwg.org/multipage/server-sent-events.html

2 https://developer.mozilla.org/en-US/docs/Web/API/Server-sent_events

3 https://developer.mozilla.org/en-US/docs/Web/API/Server-sent_events/Using_server-sent_events


Notes

  • SSE are not web-sockets (they are a one way channel from server to client), nor polling mechanisms (it is an HTTP protocol implementation). 
  • Further examples will be published
  • This is a work in progress, any help/suggestions are welcomed. Please read the Examples Sections on the Module, and have a look around :)


Current Issues

  • Scaling the Module where the Hub is instantiated is not possible yet. This means that multiple front-end servers will spawn multiple Hub instances which this component does not support(yet). 
  • On Personal Environments(PE), there seems to be a cap of 100 concurrent API live connections per Hub Module. 
  • It is currently not possible to gracefully disconnect a client. Whenever a client disconnects, the Rest API tries to set the status triggering a service studio log error (the SSE stream already sent the headers). Looking for ways to overcome this to avoid polluting the logs.


Hub Hello World

1- Create a new module(service is fine) inside your Application - HelloWorld_Hub.

It is recommended that a single Hub Module serves a single purpose/application, but any combination is possible, even a single SSE Hub for the entire Outsystems Environment.

2- Open the module dependencies (ctrl+q), search for SSE_IS and add both the "Broadcast" and "OpenStream" server actions.

3- Create a new *Service Action* named "Broadcast2HelloWorld" with a Message Input(text) variable. 

Add the imported SSE_IS "Broadcast" to the flow and fill in Message variable, and the Channel - "HelloWorld". 

That's it to Broadcast to every client subscribed to a Channel.

4- Create an Exposed Rest API  named "SSESubscribe". Add a new GET REST API Method - HelloWorldChannel and add the imported SSE_IS "OpenStream" action.

Fill in the Channel variable with "HelloWorld". 

That's it, your Hub is now able to add new Http Clients to the "HelloWorld" channel.

Take note of the Rest's Endpoint URL, e.g: "/HelloWorld_Hub/rest/SSESubscribe/HelloWorldChannel"

5- In your Client Module (React, Mobile) open the module dependencies (ctrl+q), search for the SSE_LIB and add the SSEEventListener WebBlock to your Screen. 

Fill in the SSE URL from above:

"/HelloWorld_Hub/rest/SSESubscribe/HelloWorldChannel". 

Also, create the mandatory event handler for the receiving messages.

That's all for the simplest setup! Whenever the "Broadcast" *Service Action* in the HUB is called by any agent, all clients will receive the issued message.


SSE_IS - HUB Integration Layer

  • An HUB Instance is an independent, isolated, server-sent events (SSE) connection manager. It holds HTTP connections grouped by channels.
  • Whenever an SSE_IS Module (this module) is consumed, a new HUB is created. *This is Important to understand*. 
  • A Typical scenario (recommended) is: 

    * create a new module on the application where the SSE is needed

    * consume the SSE_IS "Broadcast" and "OpenStream" actions

    * wrap and expose the Broadcast via a Service Action with the appropriate auth if applicable

    * expose a new rest endpoint for the OpenStream action with the appropriate auth if applicable

       This will be responsible to add new client http connections to the hub

  • The HUB automatically cleans any disconnected client. If the Hub DLL instance is recycled (on the IIS), the clients will automatically reconnect and the hub will transparently add these connections.
  • The HUB *Does Not* validate any channels. It will create one if it doesn't exist internally so please validate and implement your channel logic when using the hub.
  • The HUB *Does Not* enforce or validate any Auth mechanisms. Please use proper Outsystems mechanisms to apply authentication and authorization to both the REST Expose actions (for the OpenStream action) and the SSE_IS (Broadcast through a wrapped service action).
  • Please refer to the Hello World tutorial and also to the examples module for further examples.


SSE_LIB - SSE Event Listener

  • This block listens to a specific HUB Channel 
  • It is possible to further filter the Channel by its events
  • A Token GUID is issued every time a new connection is established and it uniquely identifies the connection
  • The block is initiated when the SSESubscribeURL is populated. Please refer to further examples @ the SSE examples module
  • Authentication can be implemented by passing a bearer token together with the URL, and implementing the Auth mechanism normally as you would with any REST Expose API. There are several strategies to accomplish this, via api-keys, or jwt. It goes behind the scope of this component to address it but please refer to further examples @ the examples module
  • The SSE EventStream interface ensures resilience through an auto-connect on disconnect, so everything is handled in case of disconnection. Have in mind though, that the same URL will be used.