feat: SSE handler, send y keepalive (issue 0011 fase 2)
This commit is contained in:
@@ -0,0 +1,44 @@
|
||||
package infra
|
||||
|
||||
import "net/http"
|
||||
|
||||
// SSEHandler retorna un http.HandlerFunc que setea los headers SSE,
|
||||
// consume eventos del canal y los envia con flush. Cierra limpiamente
|
||||
// si el cliente se desconecta (context cancelado) o si el canal se cierra.
|
||||
//
|
||||
// Headers seteados:
|
||||
// Content-Type: text/event-stream
|
||||
// Cache-Control: no-cache
|
||||
// Connection: keep-alive
|
||||
// X-Accel-Buffering: no (deshabilita buffering en nginx)
|
||||
func SSEHandler(events <-chan SSEEvent) http.HandlerFunc {
|
||||
return func(w http.ResponseWriter, r *http.Request) {
|
||||
flusher, ok := w.(http.Flusher)
|
||||
if !ok {
|
||||
http.Error(w, "streaming unsupported", http.StatusInternalServerError)
|
||||
return
|
||||
}
|
||||
|
||||
w.Header().Set("Content-Type", "text/event-stream")
|
||||
w.Header().Set("Cache-Control", "no-cache")
|
||||
w.Header().Set("Connection", "keep-alive")
|
||||
w.Header().Set("X-Accel-Buffering", "no")
|
||||
w.WriteHeader(http.StatusOK)
|
||||
flusher.Flush()
|
||||
|
||||
ctx := r.Context()
|
||||
for {
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return
|
||||
case ev, ok := <-events:
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
if err := SSESend(w, ev); err != nil {
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user