ATENCIÓN OBSOLETO Con Chrome 35, lanzado en mayo de 2014, todo lo explicado en este artículo ha dejado de ser funcionar ya que se ha eliminado el soporte para esta API. Ahora existe una API nueva, estándar, basada en la que dicta la W3C y que además funciona en varios navegadores. Tienes todos los detalles en este artículo.

NotifEjemploGoogle Chrome posee una característica sensacional que le permite mostrar notificaciones en el escritorio desde código JavaScript.

Lo estupendo de estas notificaciones es que se ven en el escritorio y las puedes mostrar en cualquier momento, aunque el navegador no esté en primer plano o esté minimizado. Si tu aplicación comprueba información en segundo plano con AJAX (como hace GMail con los nuevos correos) el usuario puede dejar el navegador minimizado y aún así recibirá notificaciones cuando haya algo nuevo que atender. Como vemos las posibilidades son muchas

Nota: Internet Explorer dispone de un método createPopup disponible desde la versión 7 análogo al método window.open de JavaScript de toda la vida, y desde la versión 9 es posible mostrar iconos superpuestos en el botón de la barra de tareas de la Web si esta se “engancha” allí, pero no son de lejos tan potentes como los de Google Chrome. El W3C tiene un borrador para crear notificaciones Web desde el año 2006 (última versión de este año), pero nadie lo ha implementado (lo cual me parece incomprensible), por lo que en la práctica sólo Google Chrome ofrece esta funcionalidad, y es la que voy a reflejar en este artículo.

Toda la funcionalidad de las notificaciones de Chrome se encuentra en el objeto webkitNotifications que posee la ventana del navegador. Vamos a ver lo que nos ofrece.

Pidiendo permiso

Lo primero que tenemos que hacer para poder mostrar notificaciones en el escritorio es pedir permiso al usuario. Sin este paso previo las notificaciones fallarán.

Para pedir permiso necesitamos usar la función requestPermission, a la que llamaremos sin argumentos (línea 4) con un código similar a este:

   1: function setNotificationsPermissions()
   2: {
   3:     if (window.webkitNotifications)
   4:         window.webkitNotifications.requestPermission();
   5:     else
   6:         alert("Tu navegador no soporta notificaciones Web de escritorio");
   7: }

Lo que se hace es comprobar si el navegador soporta las notificaciones de Chrome, en cuyo caso se llama a la función, mostrando un aviso en caso contrario.

El navegador muestra un barra en la parte superior para reclamar ese permiso:

SolicitarPermiso_Notif

MUY IMPORTANTE: La función requestPermission sólo funcionará si es llamada como resultado de una acción directa del usuario, es decir, al pulsar un botón o un enlace. No podemos llamarla directamente desde cualquier sitio, por ejemplo al cargar la página. El motivo es evitar que páginas malintencionadas nos puedan estar incordiando todo el tiempo pidiéndonos este permiso para que al final se lo acabemos dando para que nos dejen tranquilo. Es algo parecido a lo que ocurre con la apertura de ventanas: si no queremos que el bloqueador de pop-ups las bloquee tenemos que hacerlo como consecuencia de la acción de un usuario. En el ejemplo descargable al final se hace desde un botón específico, como muestra la figura anterior, pero puede ser de cualquier otra manera. Por ejemplo GMail lo hace a través de unos botones de radio en la configuración:

PermisoGMail

Tú hazlo como quieras, pero siempre debes asegurarte de pedir ese permiso antes de intentar mostrar notificaciones nuevas.

Generando notificaciones

Una vez que tenemos permiso podemos generar notificaciones con dos funciones:

  • createNotification: crea una notificación en la que especificamos el icono a mostrar en el lateral, un título y un texto plano. Es la más común y la que utilizaremos más frecuentemente.
  • createHTMLNotification: toma como único argumento una URL que contiene el HTML a mostrar en la ventana de notificación. Debemos tener cuidado con no mostrar nada demasiado grande o no se verá correctamente.

Estas dos funciones crean un objeto de notificación, pero para mostrarla tendremos que llamar a su método show. Mientras no lo hagamos no se verá.

Antes de llamar al método show, aparte de comprobar que el navegador soporta las notificaciones, hay que determinar si tenemos los permisos suficientes, otorgados en el paso anterior. Puede que el usuario no haya solicitado el permiso o puede que lo haya revocado desde el propio menú de herramientas de la notificación:

RevocarPermiso

La existencia de permiso se comprueba mediante la función checkPermission del objeto webkitNotifications. Puede devolver tres valores:

  • PERMISSION_ALLOWED (0): si tenemos permiso
  • PERMISSION_NOT_ALLOWED (1): si no tenemos permiso
  • PERMISSION_DENIED (2): si se ha denegado explícitamente el permiso.

Sólo si devuelve un 0 tenemos permiso, y es cuando mostraremos la notificación.

Nota: Cuando mostramos la notificación ésta generalmente se mostrará de manera inmediata, aunque en realidad lo que ocurre es que se mete en una cola de notificaciones. Chrome mete en la cola las notificaciones y las va mostrando mientras tiene espacio, guardando las demás para cuando pueda. Así, por ejemplo, en mi pantalla lo máximo que muestra son cuatro notificaciones al mismo tiempo, una encima de otra. Las demás están en la cola y hasta que cierre una de las que están visibles no se mostrarán, por lo que no podemos contar con que las notificaciones se verán instantáneamente. Puedes hacer la prueba con el ejemplo del final pulsando el botón varias veces y viendo lo que pasa.

Así, el código para mostrar la notificación quedaría del siguiente modo:

   1: function showNotification(title, msg, icon){
   2:   if (window.webkitNotifications)
   3:   {
   4:       var wkn = window.webkitNotifications;
   5:       var notif;
   6:       if (wkn.checkPermission() == PERMISSION_ALLOWED) {
   7:           notif = wkn.createNotification(icon, title, msg);
   8:           notif.show();
   9:       }
  10:   }
  11: }

También podemos cancelar la notificación (cerrarla por código) llamando al método cancel de las mismas. Por ejemplo, una buena práctica sería usar un temporizador para cerrar automáticamente la notificación al cabo de unos segundos si el usuario no la ha cerrado de forma manual, y quizá dejar abiertas solamente las que sean muy urgentes. Si guardamos una referencia al objeto notificación que se ha creado sólo tenemos que llamar a cancel() sobre éste y listo.

Eventos de las notificaciones

Las dos funciones anteriores devuelven un objeto de notificación que como hemos visto sirve para mostrar (show) y ocultar (cancel) la ventana con el mensaje.

Esta referencia a la notificación se puede utilizar para asignarle manejadores de eventos al objeto y detectar cuatro cuestiones interesantes:

  • ondisplay: este evento se llama en el momento en que se muestra la notificación. Ver la nota anterior para entender porqué eso no tiene que ser en el momento en el que llamamos a show.
  • onclose: se genera cuando la notificación se cierra, bien por código o bien por que lo hace el usuario.
  • onclick: cuando el usuario pulsa sobre la notificación. Muy interesante para enviarlo a una vista concreta de la aplicación o a otra página.
  • onerror: se produce cuando ha habido errores al mostrar la notificación.

Podemos responder a estos eventos para tomar acciones en cada caso. En el ejemplo lo que he hecho es loguear el resultado de la ejecución en cada uno de los eventos:

LogEventos

y así sabremos cuándo se produce cada uno de ellos.

Usando Chrome, prueba el ejemplo que he colgado y, tras haber otorgado permisos muestra varias notificaciones para ver cómo se van mostrando y logueando, y cómo si hay muchas se encolan y tardan en aparecer.

Es una característica muy útil que esperemos que pronto incorporen todos los navegadores´. Teniendo en cuenta la tendencia actual a que la mayor parte de las aplicaciones se ejecuten en un navegador, en detrimento de las tradicionales de escritorio, es algo que cada vez se hará más necesario.

¡Espero que te resulte útil!

💪🏻 ¿Este post te ha ayudado?, ¿has aprendido algo nuevo?
Pues NO te pido que me invites a un café... Te pido algo más fácil y mucho mejor

Escrito por un humano, no por una IA