A simple Server-Sent Events (SSE) example that sends time updates to clients.
This example demonstrates the basics of SSE:
- Creates an HTTP server with an SSE endpoint at
/events - Sends the current time to connected clients every second
- Uses
Eventtype with ID and type fields - Handles graceful shutdown on Ctrl+C
- Properly closes connections when clients disconnect
go run main.goThe server starts on http://localhost:8080
curl http://localhost:8080/eventsYou should see output like:
: connected
event: time
id: evt-1
data: 2025-01-18T04:30:00Z
event: time
id: evt-2
data: 2025-01-18T04:30:01Z
event: time
id: evt-3
data: 2025-01-18T04:30:02Z
...
Open your browser's developer console and run:
const eventSource = new EventSource('http://localhost:8080/events');
eventSource.addEventListener('time', (e) => {
console.log('Time update:', e.data, 'ID:', e.lastEventId);
});
eventSource.onerror = (err) => {
console.error('EventSource error:', err);
};http --stream GET http://localhost:8080/eventsconn, err := sse.Upgrade(w, r)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
defer conn.Close()This upgrades the HTTP connection to SSE, setting proper headers and preparing for streaming.
event := sse.NewEvent(now).
WithType("time").
WithID(fmt.Sprintf("evt-%d", eventID))Events are built using the builder pattern with optional type and ID.
if err := conn.Send(event); err != nil {
return
}Send events to the client. Errors indicate the client disconnected.
case <-conn.Done():
returnThe Done() channel signals when the connection is closed.
Event IDs enable client reconnection tracking:
- Client stores the last event ID received
- On reconnect, client sends
Last-Event-IDheader - Server can resume from that point
Event types let clients listen for specific events:
- Default type is
"message" - Custom types like
"time"enable targeted handling - Clients use
addEventListener('time', handler)to filter
- Client connects →
Upgrade()sets headers - Server sends events →
Send()writes to stream - Client disconnects →
Done()channel closes - Server cleans up →
defer conn.Close()
See the sse-chat example for broadcasting to multiple clients using Hub[T].
See docs/SSE_GUIDE.md for comprehensive SSE documentation.