4 years ago

Server sent events combined with XHR requests, help! :V


I've discovered Sever Sent Events yesterday, I made a quick demo for myself, however I got stuck.

I don't exactly know if what I want to do is possible. I'd like to create a notification system, where you can interact with the server, send XHR/AJAX requests, but at the same time being able to poll the notifications from the server.

It doesn't work, I can't find much info on this combo

I've heard that SSE are only one way, you can't use the connection as a web-socket to communicate back and forth. Does the one way mean that I won't be able to execute any XHR commands in the meantime?

Here's my front-end code, pretty poopy code:

		
			#html
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Server Side Events Test</title>
</head>
<body>
    
    <p>Start the connection</p>
    <button id="btn_connect">Connect SSE</button>
    <button id="btn_end">Close conn</button>

    <h3>Notifications: <span id="notif_res">(disconnected)</span></h3>

    <p>Notification actions</p>
    <button id="btn_incr">Add notif</button>
    <button id="btn_clear">Clear notifs</button>

    <script>

        let source = new EventSource("sse.php");
        console.log(source.withCredentials);
        console.log(source.readyState);
        console.log(source.url);

        source.onopen = function() {
            console.log("Connection establshed");
        }

        source.onmessage = function(e) {
            console.log("Recieved message:" + e.data);
            // Change notif number
            document.getElementById("notif_res").innerHTML = e.data;
        }

        source.onerror = function(e) {
            console.log("Connection encountered an error", e);
        }

        document.getElementById("btn_end").addEventListener("click", function() {
            console.log("Connection temrinated");
            source.close();
        });
        

        // Increment notifications
        document.getElementById("btn_incr").addEventListener("click", function(e){
            let xhr = new XMLHttpRequest();
            xhr.open("POST", "add_notification.php");
            xhr.send();
        });
        
        // Delete all notifications
        document.getElementById("btn_clear").addEventListener("click", function(e){
            let xhr = new XMLHttpRequest();
            xhr.open("POST", "clear_notification.php");
            xhr.send();
        });

    </script>

</body>
</html>
		
	

Here's the sse.php code

		
			#php
<?php
session_start();
header('Content-Type: text/event-stream');

// Setup
if (!isset($_SESSION['notif'])) {
    $_SESSION['notif'] = 0;
}

while(1){
    session_start();
    echo "data: ".$_SESSION['notif']."\n\n";

   // flush the output buffer and send echoed messages to the browser
    while (ob_get_level() > 0) {
        ob_end_flush();
    }
    flush();
    
    // session_write_close(); 
    
    if (Connection_aborted()) break;

    sleep(1);
    echo "data: HEYO\n\n";
    while (ob_get_level() > 0) {
        ob_end_flush();
    }
    flush();
    sleep(1);
}

?>
		
	

The add an clear notifs just update the $_SESSION['notif'] variable. The response of sse.php is just a data oscillating between the number of notifications and the text "HEYO".

Two observations:

  • When I execute the code above, the add_notification.php POSTs will never get sent.

    screenshot_2021-11-09_at_80043_pm.png
  • SO, I googled a bit, and found this: when I add the session_write_close(); line (in sse.php), the POSTs will get executed, but weirdly it doesn't affect the response by the sse.php

    screenshot_2021-11-09_at_80930_pm.png

    Here's a demo, the notifications count only changes when I reload the page, whereas the response of add_notification.php is clearly the incremented number of notifs, and at the same time the sse.php code is clearly still running on the server!

    f5fe3dcb0cb264480fc635596c680f06.gif

Does the code I'm making make sense? Are you even able to combine these 2 tricks to create a subscription to a server for notifications, and at the same time being able to interact with the site's API through other xhr requests?



1 comment

Loading...

Next up

Me: "Hey! Can you sing this?"

Singer:

We made a game for GMTK's 2025 Game Jam with a friend! (my first game jam btw)

Check it out here! :)

itch.io/jam/gmtk-2025/rate/3779449

Welcome to 'Mytherland' - a brand new interactive community website which will open very soon: https://myther.land

Heyo!

Check out this sneak peek for the Briar Original Game Soundtrack I've worked on! I'm planning a proper video when the game releases, but it looks like Streaming Services got ahead of us...

youtube.com/watch?v=yrOTiqwqzzc&list=OLAK5uy_nLayYYMpXpBZqMWE9Gd…

Stickit' Truddy, web-project introduction

A website where you can Collect and Swap stickers with friends and fill up your collector's albums!

Join dev journey at gamejolt.com/c/stickit-kt5adm

#webdev #art

Maybe Louis song? #beastars

Lyrics:

I feel this rotting number burning on my leg again, Fears of a past I can't erase set my whole world up in flames I'll use the pain to wake the wolf you keep inside of you, Please help me start anew

I am super happy to see that my favourite song of my OST Album for Briar has the most plays of all!

It's not a lot but still it means a ton! :D Thank you

open.spotify.com/track/3MmOnOP5GwisxS7gRBR65M

Well would you look at this, I voiced this character hehe

@Raccoonicorn