SSE vs WebSocket: qué opción de tiempo real usar | We.Inc
Server-sent events vs WebSockets: EventSource y WebSocket lado a lado, reconexión, datos binarios, límites de conexión, un asistente de decisión y servidores Node mínimos para ambos.
Los server-sent events envían texto en streaming del servidor al navegador sobre una respuesta HTTP normal, y la API EventSource se reconecta sola. Un WebSocket convierte la conexión en un canal bidireccional que transporta texto o binario en ambos sentidos. Usa SSE para feeds, notificaciones y progreso; usa WebSockets cuando el navegador deba enviar mensajes frecuentes de vuelta.
Lado a lado
Característica
Server-sent events
WebSocket
Dirección
Solo del servidor al cliente
En ambos sentidos a la vez
API del navegador
EventSource
WebSocket
Protocolo
HTTP normal, text/event-stream
HTTP Upgrade, luego ws:// o wss://
Datos
Solo texto UTF-8
Texto o binario
Reconexión
Automática, se reanuda con Last-Event-ID
La escribes tú
Conexiones abiertas en HTTP/1
6 por navegador y dominio
Límites aparte, fijados por cada navegador
¿No tienes claro cuál necesita tu funcionalidad? Marca en el asistente de abajo las afirmaciones que se cumplen. Aplica las mismas reglas que la tabla de arriba y te dice qué API encaja y por qué.
Marca cada afirmación que describa tu funcionalidad.
Lee la recomendación y el motivo que da.
Copia el código de cliente y de servidor correspondiente de las secciones de más abajo.
Cambia la URL y los nombres de eventos por los tuyos y ejecuta el servidor con Node.
Envía una línea de comentario, dos puntos seguidos de texto, cada 15 a 30 segundos en un stream SSE para que los proxies inactivos no lo corten.
Da un id a cada evento SSE. Cuando el navegador se reconecta, devuelve ese valor en la cabecera Last-Event-ID y tu servidor puede reenviar lo que se perdió.
Sirve SSE sobre HTTP/2 siempre que puedas, porque el límite de seis conexiones de HTTP/1 se comparte entre todas las pestañas abiertas de tu sitio.
Con WebSockets, vigila bufferedAmount antes de enviar ráfagas grandes; la API en sí no tiene backpressure.
Preguntas frecuentes
¿Puede el navegador enviar datos al servidor con SSE?
No por el propio stream. El stream de eventos solo fluye del servidor al cliente, así que el navegador envía sus mensajes con peticiones fetch normales. Para tráfico tipo chat en ambos sentidos, un WebSocket encaja mejor.
¿Cómo evito que EventSource se reconecte?
Invoca close() en el cliente. Desde el servidor, el estándar HTML dice que una respuesta 204 No Content indica al cliente que deje de reconectarse.
¿Puedo enviar una cabecera Authorization con EventSource?
No. El constructor solo acepta una URL y un objeto de opciones cuyo único ajuste es withCredentials. Usa una cookie, un token de corta duración en la URL o un lector basado en fetch si necesitas cabeceras personalizadas.
¿SSE está obsoleto ahora que existen los WebSockets?
No. El formato text/event-stream sigue siendo una buena opción para feeds unidireccionales porque funciona con servidores HTTP, proxies y autenticación normales, sin cambio de protocolo.
¿Cuál consume menos recursos del servidor?
Los dos mantienen una conexión de larga duración por cliente, así que la diferencia es pequeña. Importa más si tu hosting permite respuestas de larga duración o cambios de protocolo, así que revisa primero sus límites de duración de las peticiones.
Cómo funcionan los server-sent events
El servidor responde a un GET normal con Content-Type text/event-stream y mantiene la respuesta abierta. Cada mensaje son unas pocas líneas como event:, data: e id:, terminadas por una línea en blanco. Varias líneas data: en un mismo mensaje se unen con saltos de línea.
El EventSource del navegador analiza ese stream, dispara un evento message para los mensajes sin nombre y un evento con nombre para el resto, y se reconecta por su cuenta tras un corte. Una línea retry: fija la espera en milisegundos antes de volver a intentarlo.
Cómo funcionan los WebSockets
El cliente empieza con una petición HTTP que lleva una cabecera Upgrade, y el servidor responde 101 Switching Protocols. A partir de ahí la conexión transporta frames de WebSocket, no HTTP, y cualquiera de los dos lados puede enviar en cualquier momento.
Esa libertad tiene un precio. Escribes tu propia lógica de reconexión, tu propio formato de mensaje, a menudo JSON con un campo type, y tu propio heartbeat. Un proxy que no reenvíe la cabecera Upgrade también cortará la conexión antes de que empiece.
Una regla rápida
Si el navegador sobre todo escucha, elige SSE. Resultados en directo, logs de compilación, estado de pedidos, notificaciones y texto en streaming encajan ahí.
Si el navegador habla tanto como escucha, o los datos son binarios, elige un WebSocket. Juegos multijugador, editores colaborativos y salas de chat encajan ahí.
Server-sent events: código mínimo
Servidor SSE en Node puro
No hace falta ninguna librería. La respuesta sigue abierta; cada escritura es un evento, y la línea de comentario evita que los proxies inactivos la cierren.
EventSource en el navegador
addEventListener usa el nombre del evento del stream. La reconexión ocurre sin que escribas código.
WebSocket: código mínimo
Servidor WebSocket con el paquete ws
Instálalo con npm install ws. Devuelve cada mensaje en mayúsculas al cliente que lo envió.
WebSocket en el navegador, con una reconexión sencilla
A diferencia de EventSource, nada se reconecta por ti, así que esto espera un momento tras el cierre y abre un socket nuevo.
El navegador envía muchos mensajes de vuelta, varios por segundo o más
Los datos son binarios, como fragmentos de audio o buffers de estado de juego
Los clientes deben recuperar los eventos perdidos tras una conexión caída
El tráfico pasa por proxies o hostings que solo manejan HTTP normal
Encajan los server-sent events. Nada de lo que marcaste necesita un canal bidireccional, y EventSource te da reconexión y reanudación gratis.
Encaja un WebSocket. Necesitas mensajes frecuentes desde el navegador o datos binarios, algo que un stream de eventos no puede transportar.