Did you know ... | Search Documentation: |
Providing Server-Sent Events (sse) |
Server-Sent Events allows for setting up a simple event stream from the server to the client. It can serve roles similar to long polling and web sockets, enabling the server to notify its clients on some event. Long polling uses a normal HTTP (usually) GET request that blocks for a long time on the server. The server finishes the request when it wants to notify the client or after some time (e.g., a minute) to avoid a timeout on the client or some proxy. After receiving an event or timeout, the client repeats the request. Web sockets upgrade a the socket used for a normal HTTP request to create a bi-directional open communication channel that exchanges encapsulated messages in both directions. Server-Sent Events open a normal HTTP channel over which the server can sent simple text messages using a format similar to the HTTP header: a sequence of Name: Value lines followed by two newlines. Unlike long polling, the request does not complete after a message.
Following the MDN documentation above, and SSE request can be served using the simple example below that generates an event, counting every minute. Note the handler declaration that processes the request on a new thread and disables timeout for this location. Note that this implementation uses a thread per client. This design limits the scalability.
:- http_handler(root(events), events, [ spawn([]), time_limit(infinite) ]). events(_Request) :- format('X-Accel-Buffering: no\r\n\c Content-Type: text/event-stream\r\n\c Cache-Control: no-cache\r\n\r\n'), between(1, infinite, Min), format('event: minute~n'), format('data: {"minute": ~d}~n~n', [Min]), flush_output, sleep(60), fail.
Of course, rather than sleep/1 to decide when to fire the next event this thread typically has to wait for events in the application. This can be achieved using thread_wait/2 or message queues.