Fix Server Side Event Interrupted while the page was loading error message
Description
I love HTMX, it's for me the return of the good old way of think and I'm so glad to be here.
But nothing is perfect, there is an annoying bug in Firefox with the Server Side Event Extension.
There is an issue with the way the EventSource is closed on Firefox. When you have a currently connected EventSource and you refresh the page without closing it, you got those errors :
The connection to http://localhost:5000/stream was interrupted while the page was loading. htmx.org:1:1349
error { target: EventSource, isTrusted: true, srcElement: EventSource, currentTarget: EventSource, eventPhase: 2, bubbles: false, cancelable: false, returnValue: true, defaultPrevented: false, composed: false, … }
htmx.org:1:25781
With some search on the internet I found this is an old bug from Firefox and this is not fixed yet. https://bugzilla.mozilla.org/show_bug.cgi?id=833462
By chance a workaround was found, if the JavaScript close the EventSource before the page unload. There is no more error on the page unload.
Note : There is a bug very similar on Chromium where the is also a similar error message except it appear for a fraction of time before vanish to the oblivion ! Closing the EventSource solve this too.
Testing
I know it's bad but I didn't manage a way to test my change. What my PR do is I close the EventSource on the windows beforeunload, this event make me force in my test to close the window. But if I close the window my test stop...
I don't know how I can still use beforeunload but simulate a window close in my test.
So I no my PR is not conform yet to the standard of PR but if someone can suggest a way to test beforeunload, I will update this PR to include a test to verify the EventSource is closed when the window close.
Replicate
I didn't create an Issue since It's written in the review guideline "Correspondingly, it is fine to directly PR bugfixes for behavior that htmx already guarantees", but I will still write here a small example to get those error I show in Firefox.
You need a server with SSE. (here an example in python with Flask)
from flask import Flask, render_template, Response
import time
app = Flask(__name__)
def generate_sse():
count = 0
while True:
time.sleep(0.001)
count += 1
yield f"data: {count}\n\n"
@app.route('/stream')
def stream():
return Response(generate_sse(), mimetype='text/event-stream')
@app.route('/')
def home():
return render_template('index.html')
if __name__ == '__main__':
app.run(debug=True)
And you need to use the HTMX SSE extension.
<!DOCTYPE html>
<html lang="fr">
<head>
<meta charset="UTF-8">
<title>Exemple HTMX SSE</title>
<script src="https://unpkg.com/htmx.org"></script>
<script src="https://unpkg.com/htmx.org/dist/ext/sse.js"></script>
</head>
<body>
<h1>Compteur SSE avec HTMX</h1>
<div hx-ext="sse" sse-connect="/stream" sse-swap="message">
Waiting for data...
</div>
</body>
</html>
When you reload the page, you got those errors in Firefox
@benpate @Renerick please review
Blah at chasing down an error that's not actually an issue but that happens every time you refresh in just one browser. Hope y'all figure out a nice way to solve it here soon.
Here's a hack workaround that I'm using for my project until this is fixed properly.
globalThis.addEventListener("beforeunload", () => document.querySelectorAll("[sse-connect]").forEach((elt) => elt['htmx-internal-data'].sseEventSource.close()))