2016-04-20 5 views
1

Client-Seite sieht wie folgt aus:Warum löst diese EventSource wiederholt eine Nachricht und einen Fehler aus?

var es = new EventSource("http://localhost:8080"); 
es.addEventListener("message", function(e) { 
    alert("e.data") //Alerts "" every couple seconds 
}) 
es.addEventListener("error", function(e) { 
    alert("error") //Also fires every couple of seconds 
}) 
var post_request = new XMLHttpRequest(); 
post_request.open("POST", "http://localhost:8080"); 
post_request.setRequestHeader("Content-Type", "text/plain"); 
post_request.addEventListener("readystatechange", function() { 
    if (post_request.readyState == 4 && post_request.status == 200) { 
     alert(post_request.responseText); //This works 
    } 
}) 
post_request.send("This is a test") 

Server-Seite node.js Anfrage POST Umgang mit dieser wie folgt aussieht:

function process_request(request, response) { 
    var request_body = [] 
    request.on("data", function(chunk) { 
     request_body.push(chunk) 
    }) 
    request.on("end", function() { 
     request_body = Buffer.concat(request_body).toString()+"\n" 
     response.writeHead(200, {"Access-Control-Allow-Origin": "*", 
           "Content-Type": "text/event-stream", 
           "Connection": "keep-alive" 
           }); 

     response.end("data: " + request_body + "\n"); 
    }) 
} 

Wenn ich POST-Anforderungsdaten von der Client-Seite zu senden, es mir zurückgegeben wird mit response.end() wie erwartet, aber es löst alle paar Sekunden einen Fehler aus, zusätzlich zu einem message Ereignis alle paar Sekunden. Wenn das Ereignis message ausgelöst wird, wird jedoch gemeldet "", und ich bin mir nicht sicher warum? Kann mir jemand helfen, dieses Verhalten herauszufinden?

EDIT: Nur die es.readyState auf den message und error Ereignisse überprüft. readyState ist 0 auf der error, so scheint es, als könnte es ein Ergebnis der Trennung sein. Warum würde diese wiederholte Trennung passieren? Und warum wiederholte Verbindung und Trennung wiederholt message Ereignisse verursachen?

+0

Für eine Sache, '" Dies ist ein Test "' ist kein gültiger Inhalt in 'text/event-stream'. Hast du versucht, eine gültige Antwortstelle zu schreiben? – mscdex

+0

@mscdex Ich habe es bearbeitet, um es zu einem gültigen 'text/event-stream' Inhalt zu machen. Was nun passiert, ist, dass die 'es' alle paar Sekunden sowohl ein 'Nachricht'-Ereignis als auch ein' Fehler'-Ereignis auslöst. Beim 'Nachricht'-Ereignis alert 'alert (e.data)' jedoch eine leere Zeichenkette? – digglemister

Antwort

1

Was geschieht, wenn Sie die SSE-Anfrage des Benutzers bearbeiten, Daten zurücksenden und dann die Verbindung schließen. Der Client erkennt, dass die Verbindung unterbrochen wurde, und verbindet sich einige Sekunden später erneut (diese Wiederverbindung ist eine Funktion von SSE).

Also, stattdessen sollten Sie nie beenden. Das bedeutet, dass Sie sicherstellen müssen, dass request.on("end", ... nie erreicht wird.

Hier ist ein grundlegender SSE-Server in node.js die ich verwendet habe vor:

var http = require("http"); 
var port = parseInt(process.argv[2] || 8080); 

http.createServer(function(request,response){ 
    console.log("Client connected:" + request.url); 
    response.writeHead(200, { "Content-Type": "text/event-stream" }); 
    var timer = setInterval(function(){ 
    var content = "data:" + new Date().toISOString() + "\n\n"; 
    response.write(content); 
    }, 1000); 
    request.connection.on("close", function(){ 
    response.end(); 
    clearInterval(timer); 
    console.log("Client closed connection. Aborting."); 
    }); 
    }).listen(port); 
console.log("Server running at http://localhost:" + port); 

D.h. Wir benutzen eine setInterval um weiter zu laufen. Das einzige Ereignis, auf das Sie achten müssen, ist der Client, der die Verbindung schließt.

+0

Danke, das macht Sinn. Können Sie erklären, was "Connection": "keep-alive" 'im Antwort-Header dann tut? – digglemister

+1

Es gibt ein ganzes StackOverflow-Tag auf Keep-Alive: http://StackOverflow.com/questions/tagged/keep-alive Ich glaube nicht, dass Sie es mit SSE verwenden müssen. –

Verwandte Themen