Al construir una aplicación web, rápidamente te verás en la necesidad de comprobar la conexión a internet. Por ejemplo, una PWA (Progressive Web Application), por definición, debe funcionar offline y comprobar la conectividad es una tarea de rutina.
Esto no significa necesariamente que se pueda acceder al contenido de forma offline, significa que la aplicación maneje la situación, no el navegador. En otras palabras, el mensaje de error por falta de conexión en el navegador se sustituye por un mensaje de error en la propia aplicación. En este contexto, se puede decir que la aplicación funciona offline, aunque no se pueda acceder al contenido. A partir de aquí, la aplicación puede implementar o no el almacenamiento de contenido para acceso offline.
navigator.onLine es una propiedad de la interfaz Navigator (window.navigator) de tipo lógico que devuelve true si el navegador se encuentra conectado a la red y false en caso contrario.Un pequeño detalle: online no es igual a Internet
Según la información que aparece en MDN, no todos los navegadores han implementado esta propiedad de la misma forma. En general, Chrome y Safari devuelven true si el navegador se puede conectar a una red de área local (LAN) o a un router, lo cual no significa necesariamente que el navegador pueda acceder a Internet, ya que puede estar conectado a una intranet sin acceso a internet.
La solución a este problema es no asumir que hay acceso a internet si navigator.onLine devuelve true. Si devuelve false es seguro que no hay acceso a Internet, pero no al contrario. Algunas bibliotecas, como Offline.js, hacen una solicitud a un archivo remoto para comprobar si hay acceso a Internet o no, y esta es una práctica bastante común y que funciona bien.
Pero el hecho de hacer una solicitud a Internet para comprobar si hay conexión no siempre es lo más aconsejable.
Por ejemplo, imagina hacer esta comprobación para decidir si hacer o no un fetch o un ajax. Estaríamos añadiendo un retraso considerable. Si navigator.onLine es false si podríamos evitar el fetch o el ajax de forma segura ahorrando la espera hasta el timeout. Pero si es true, tendríamos que seguir manejando los posibles timeouts y códigos de estado en las respuestas HTTP, por ejemplo:
Esto no significa necesariamente que se pueda acceder al contenido de forma offline, significa que la aplicación maneje la situación, no el navegador. En otras palabras, el mensaje de error por falta de conexión en el navegador se sustituye por un mensaje de error en la propia aplicación. En este contexto, se puede decir que la aplicación funciona offline, aunque no se pueda acceder al contenido. A partir de aquí, la aplicación puede implementar o no el almacenamiento de contenido para acceso offline.
navigator.onLine
navigator.onLine es una propiedad de la interfaz Navigator (window.navigator) de tipo lógico que devuelve true si el navegador se encuentra conectado a la red y false en caso contrario.
// Ver https://developer.mozilla.org/es/docs/Web/API/NavigatorOnLine/onLine
if(navigator.onLine) {
// el navegador está conectado a la red
} else {
// el navegador NO está conectado a la red
}
Además, podemos suscribirnos a los eventos window.offline y window.online. Podríamos, por ejemplo, añadir una clase al body:if(navigator.onLine) {
goOnline();
} else {
goOffile();
}
window.addEventListener('offline', goOffline());
window.addEventListener('online', goOnline());
function goOnline() {
document.body.classList.remove('offline');
document.body.classList.add('online');
// Hacer algo más al ir online
}
function goOffline() {
document.body.classList.remove('online');
document.body.classList.add('online');
// Hacer algo más al ir offline
}
Un pequeño detalle: online no es igual a Internet
Según la información que aparece en MDN, no todos los navegadores han implementado esta propiedad de la misma forma. En general, Chrome y Safari devuelven true si el navegador se puede conectar a una red de área local (LAN) o a un router, lo cual no significa necesariamente que el navegador pueda acceder a Internet, ya que puede estar conectado a una intranet sin acceso a internet.
La solución a este problema es no asumir que hay acceso a internet si navigator.onLine devuelve true. Si devuelve false es seguro que no hay acceso a Internet, pero no al contrario. Algunas bibliotecas, como Offline.js, hacen una solicitud a un archivo remoto para comprobar si hay acceso a Internet o no, y esta es una práctica bastante común y que funciona bien.
Pero el hecho de hacer una solicitud a Internet para comprobar si hay conexión no siempre es lo más aconsejable.
Por ejemplo, imagina hacer esta comprobación para decidir si hacer o no un fetch o un ajax. Estaríamos añadiendo un retraso considerable. Si navigator.onLine es false si podríamos evitar el fetch o el ajax de forma segura ahorrando la espera hasta el timeout. Pero si es true, tendríamos que seguir manejando los posibles timeouts y códigos de estado en las respuestas HTTP, por ejemplo:
// Sólo hacer el fetch si navigator.onLine es true
if( navitagor.onLine ) {
fetch('https://example.com/flowers.webp')
.then(function(response) {
if(!response.ok) {
// Parece que hay acceso a Internet,
// pero la respuesta no ha sido ok
// También se puede comprobar el código de estado con response.status
// Y hacer algo específico según el estado exacto recibido
throw Error(response.statusText);
}
return response;
}).then(function(response) {
// response.ok fue true
console.log('ok');
resolve(response);
}).catch(function(error) {
console.log('Problema al realizar la solicitud: ' + error.message);
reject(error);
});
}
Comentarios