Broadcast Channel API: Comunicación entre Pestañas del Mismo Origen
Aprende a comunicar entre múltiples pestañas y ventanas del mismo origen usando la Broadcast Channel API para sincronizar estado en tiempo real.
TL;DR - Resumen rápido
- Broadcast Channel comunica entre pestañas del mismo origen (protocolo, dominio y puerto idénticos)
- Crea canales con new BroadcastChannel('nombre') usando el mismo nombre en todas las pestañas
- postMessage() envía datos serializables a todos los listeners del canal
- El evento 'message' recibe mensajes enviados por otros contextos
- El contexto emisor NO recibe su propio mensaje (evita bucles)
- close() cierra el canal - crítico para evitar memory leaks
Introducción a Broadcast Channel
La Broadcast Channel API permite la comunicación entre diferentes contextos de navegación del mismo origen, como pestañas, ventanas o iframes. A diferencia de localStorage que usa eventos de almacenamiento, Broadcast Channel proporciona una API más directa y eficiente para enviar mensajes arbitrarios entre contextos.
Esta API es ideal para aplicaciones que necesitan sincronizar estado entre múltiples pestañas, como aplicaciones de chat, editores colaborativos, o cualquier situación donde necesites que cambios en una pestaña se reflejen inmediatamente en otras.
- Comunicación bidireccional entre pestañas del mismo origen
- Envío de cualquier tipo de dato serializable (objetos, arrays, strings)
- No requiere servidor intermedio - comunicación directa en el navegador
- Más eficiente que localStorage events para comunicación compleja
- Soporta múltiples listeners en el mismo canal
Mismo Origen
Broadcast Channel solo funciona entre contextos con el mismo origen (protocolo, dominio y puerto idénticos). Por ejemplo, https://example.com y https://app.example.com NO pueden comunicarse porque tienen diferentes dominios, aunque estén relacionados.
Crear un Broadcast Channel
Para crear un Broadcast Channel, simplemente usa el constructor con un nombre único que identificará el canal. Todos los contextos que quieran comunicarse deben crear un canal con el mismo nombre. El nombre del canal es sensible a mayúsculas y minúsculas.
Cuando creas un Broadcast Channel, automáticamente te unes a ese canal. Puedes crear múltiples canales con diferentes nombres para diferentes propósitos de comunicación. Es importante cerrar los canales cuando ya no se necesiten para evitar memory leaks.
Nombres de Canales
Usa nombres descriptivos para tus canales que reflejen su propósito. Por ejemplo, 'chat-messages', 'user-auth', 'theme-sync'. Esto facilita el mantenimiento y evita conflictos con otros canales que puedas crear en el futuro.
Enviar Mensajes
Para enviar mensajes a través del Broadcast Channel, usa el método postMessage(). Este método acepta cualquier dato que pueda ser clonado por el algoritmo de clonación estructurada de JavaScript, lo que incluye objetos, arrays, strings, números, y más.
Cuando envías un mensaje con postMessage(), todos los demás contextos que estén escuchando el canal recibirán el mensaje. El contexto que envía el mensaje NO recibe su propio mensaje, lo que evita bucles infinitos de comunicación.
- Crea el canal con el mismo nombre en todas las pestañas
- Envía mensajes con postMessage() desde cualquier pestaña
- Los listeners 'message' reciben el mensaje en otras pestañas
- Valida la estructura del mensaje antes de procesarlo
- Cierra el canal con close() al desmontar componentes
Limitaciones de postMessage
No puedes enviar funciones, Promises, ni objetos con referencias circulares a través de postMessage(). Estos tipos de datos no pueden ser clonados por el algoritmo de clonación estructurada. Si necesitas enviar datos complejos, serialízalos primero.
Recibir Mensajes
Para recibir mensajes enviados por otros contextos, añade un event listener para el evento 'message'. Este evento se dispara cada vez que otro contexto envía un mensaje al canal. El evento contiene la propiedad 'data' con el mensaje enviado.
Puedes añadir múltiples listeners para el evento 'message' en el mismo canal, lo que permite que diferentes partes de tu aplicación reaccionen a los mensajes de diferentes maneras. Es importante limpiar los listeners cuando ya no se necesiten para evitar memory leaks.
Mejor Práctica: Type Checking
Siempre verifica el tipo y estructura de los datos recibidos antes de procesarlos. Esto previene errores cuando mensajes de diferentes partes de tu aplicación tienen formatos diferentes. Usa typeof y instanceof para validar los datos.
Ejemplo Completo
Este ejemplo completo muestra cómo usar Broadcast Channel para sincronizar el tema (claro/oscuro) entre múltiples pestañas. Cuando un usuario cambia el tema en una pestaña, todas las demás pestañas del mismo origen se actualizan automáticamente.
Este patrón es muy común en aplicaciones modernas donde la preferencia del usuario debe persistir y sincronizarse entre múltiples pestañas. Broadcast Channel hace esto mucho más eficiente que usar localStorage events, ya que no hay necesidad de escribir en el almacenamiento para cada cambio.
Sincronización Inicial
Cuando una nueva pestaña se abre, puede preguntar por el estado actual enviando un mensaje de "request-state". Las pestañas existentes pueden responder con su estado actual, permitiendo que la nueva pestaña se sincronice inmediatamente.
Errores Comunes
Al trabajar con Broadcast Channel, hay varios errores comunes que puedes encontrar. Conocer estos errores y cómo evitarlos te ayudará a escribir código más robusto.
Los errores más comunes incluyen no cerrar los canales cuando ya no se necesitan, enviar datos no serializables, y no validar los mensajes recibidos. Estos problemas pueden causar memory leaks, errores en tiempo de ejecución y comportamiento inesperado.
Memory Leaks
Olvidar cerrar los canales de Broadcast Channel es una causa común de memory leaks en aplicaciones SPA. Siempre cierra los canales en el evento beforeunload o cuando el componente se desmonta. Esto es especialmente importante en aplicaciones con muchas pestañas abiertas.
Resumen: Broadcast Channel API
Conceptos principales:
- •Broadcast Channel permite comunicación entre contextos del mismo origen
- •Usa el mismo nombre de canal para conectar múltiples contextos
- •postMessage() envía mensajes a todos los listeners del canal
- •El evento 'message' recibe los mensajes enviados por otros contextos
- •close() cierra el canal y desconecta del broadcast
Mejores prácticas:
- •Cierra siempre los canales cuando ya no se necesiten para evitar memory leaks
- •Valida el tipo y estructura de los mensajes recibidos antes de procesarlos
- •Usa nombres descriptivos para los canales que reflejen su propósito
- •Envía solo datos serializables (objetos, arrays, strings, números)
- •Considera el patrón request-response para sincronización inicial