We have been waiting a while for web socket support to get added but it looks like it won’t be ready for a while.
I was looking into alternative use cases, and I realised that maybe SSE works with workers and that could be utilised for unidirectional message flow from the edge. I did a quick POC and it seems like it does work.
I was wondering are there any restrictions of using workers like this? I noticed that on the limits page it says “There is no limit on the real runtime for a Workers script. As long as the client that sent the request remains connected…”.
I was thinking that maybe something like this could be used in combination with global variables, to create some sort of pub sub model.
Thanks in advance
This is the POC code:
addEventListener('fetch', event => {
event.respondWith(fetchAndApply(event.request))
})
async function fetchAndApply(request) {
let { readable, writable } = new TransformStream()
var headers = new Headers();
headers.append('Content-Type', 'text/event-stream');
headers.append('Cache-Control', 'no-cache');
headers.append('Connection', 'keep-alive');
headers.append('Access-Control-Allow-Origin', '*');
headers.append('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
var init = { "status": 200, "statusText": "ok", "headers": headers };
writeToStream(writable)
return new Response(readable, init)
}
async function writeToStream(writable) {
let writer = writable.getWriter()
var id = "id-test"
// send first message
await constructSSE(writer, id, "first message");
// send message every 5 second
setInterval(function () {
constructSSE(writer, id, "repeated message");
}, 5000);
}
async function constructSSE(writer, id, data) {
let encoder = new TextEncoder()
await writer.write(encoder.encode('id: ' + id + '\n'));
await writer.write(encoder.encode("data: " + " - SSE Server - " + '\n\n'));
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>demo</title>
<link rel="stylesheet" type="text/css" href="app.css">
<script src="vendor/eventsource.min-yaffle.js"></script>
</head>
<body>
<script>
const fn = function (e) {
console.log(e.data);
};
const src = new EventSource("https://devdomain.workers.dev",);
src.onmessage = fn;
</script>
</body>
</html>