Erkennen, dass die Internetverbindung offline ist?

245

Wie erkenne ich, dass die Internetverbindung in JavaScript offline ist?

Daniel Silveira
quelle
Wenn Sie Websockets verwenden können oder bereits verwenden, haben Websockets ein Abschlussereignis, das aufgerufen werden muss, wenn der Benutzer die Verbindung zum Server verloren hat.
Simon

Antworten:

134

Sie können feststellen, dass die Verbindung unterbrochen wird, indem Sie fehlgeschlagene XHR-Anforderungen stellen .

Der Standardansatz besteht darin, die Anforderung einige Male zu wiederholen . Wenn dies nicht der Fall ist, benachrichtigen Sie den Benutzer , um die Verbindung zu überprüfen, und schlagen Sie ordnungsgemäß fehl .

Nebenbemerkung: Wenn Sie die gesamte Anwendung in den "Offline" -Zustand versetzen, kann dies zu einer Menge fehleranfälliger Bearbeitungszustände führen. Drahtlose Verbindungen können kommen und gehen usw. Daher ist es möglicherweise am besten, wenn Sie nur ordnungsgemäß ausfallen und die Daten und alarmieren Sie den Benutzer. So können Sie das Verbindungsproblem, falls vorhanden, eventuell beheben und Ihre App mit einigem Maß an Vergebung weiter verwenden.

Nebenbemerkung: Sie könnten eine zuverlässige Website wie Google auf Konnektivität überprüfen. Dies ist jedoch möglicherweise nicht ganz nützlich, da Sie nur versuchen, eine eigene Anfrage zu stellen, da Google möglicherweise verfügbar ist, Ihre eigene Anwendung jedoch möglicherweise nicht verfügbar ist und Sie dies immer noch tun müssen Ihr eigenes Verbindungsproblem behandeln. Der Versuch, einen Ping an Google zu senden, ist eine gute Möglichkeit, um zu bestätigen, dass die Internetverbindung selbst unterbrochen ist. Wenn diese Informationen für Sie nützlich sind, lohnt sich möglicherweise die Mühe.

Nebenbemerkung : Das Senden eines Pings kann auf die gleiche Weise erfolgen, wie Sie eine bidirektionale Ajax -Anfrage stellen würden. Das Senden eines Pings an Google in diesem Fall wäre jedoch in diesem Fall mit einigen Herausforderungen verbunden. Erstens hätten wir dieselben domänenübergreifenden Probleme, die normalerweise bei der Ajax-Kommunikation auftreten. Eine Möglichkeit besteht darin, einen serverseitigen Proxy einzurichten, bei dem wir tatsächlich pinggoogeln (oder auf einer anderen Website) und die Ergebnisse des Pings an die App zurückgeben. Das ist ein Catch-22Denn wenn die Internetverbindung tatsächlich das Problem ist, können wir nicht zum Server gelangen, und wenn das Verbindungsproblem nur auf unserer eigenen Domain liegt, können wir den Unterschied nicht erkennen. Es könnten auch andere domänenübergreifende Techniken ausprobiert werden, z. B. das Einbetten eines Iframes in Ihre Seite, die auf google.com verweist, und das anschließende Abfragen des Iframes auf Erfolg / Misserfolg (Überprüfen des Inhalts usw.). Das Einbetten eines Bildes sagt uns möglicherweise nichts, da wir eine nützliche Antwort des Kommunikationsmechanismus benötigen, um eine gute Schlussfolgerung darüber zu ziehen, was vor sich geht. Daher kann es schwieriger sein, den Status der Internetverbindung als Ganzes zu bestimmen, als es wert ist. Sie müssen diese Optionen für Ihre spezifische App abwägen.

Keparo
quelle
84
Die wiederholte "Sidenote" klingt wie Dwight Schrute, der "Frage ..." sagt :-)
Brian Kelly
19
Warum ist "catch-22" fett gedruckt?
Codingbear
33
Jetzt im Jahr 2012 können Sie die Variable navigator.onLine überprüfen;)
João Pinto Jerónimo
13
navigator.online/offline ist aus den gleichen Gründen ebenfalls unzuverlässig. Siehe stackoverflow.com/questions/3181080/…
Efran Cobisi
17
Vielleicht möchten Sie sich Offline.js ansehen , eine Open-Source-Bibliothek, die genau für diesen Zweck entwickelt wurde.
Adam
51

IE 8 unterstützt die Eigenschaft window.navigator.onLine .

Aber das hilft natürlich nicht bei anderen Browsern oder Betriebssystemen. Ich gehe davon aus, dass andere Browser-Anbieter diese Eigenschaft ebenfalls bereitstellen werden, da es wichtig ist, den Online- / Offline-Status in Ajax-Anwendungen zu kennen.

Bis dies passiert, kann entweder XHR oder eine Image()oder <img>Anfrage etwas bereitstellen, das der gewünschten Funktionalität nahe kommt.

Update (16.11.2014)

Die gängigen Browser unterstützen diese Eigenschaft jetzt, aber Ihre Ergebnisse variieren.

Zitat aus der Mozilla-Dokumentation :

Wenn der Browser in Chrome und Safari keine Verbindung zu einem lokalen Netzwerk (LAN) oder einem Router herstellen kann, ist er offline. Alle anderen Bedingungen kehren zurück true. Sie können also davon ausgehen, dass der Browser offline ist, wenn er a zurückgibtfalse Wert , können Sie nicht davon ausgehen, dass ein echter Wert zwangsläufig bedeutet, dass der Browser auf das Internet zugreifen kann. Möglicherweise werden Fehlalarme angezeigt, z. B. in Fällen, in denen auf dem Computer eine Virtualisierungssoftware ausgeführt wird, die über virtuelle Ethernet-Adapter verfügt, die immer "verbunden" sind. Wenn Sie den Online-Status des Browsers wirklich ermitteln möchten, sollten Sie daher zusätzliche Mittel zur Überprüfung entwickeln.

Wenn Sie in Firefox und Internet Explorer den Browser in den Offline-Modus schalten, wird ein falseWert gesendet. Alle anderen Bedingungen geben einen trueWert zurück.

Grant Wagner
quelle
5
navigator.onLine ist Teil von HTML5 - andere Browser haben bereits Entwicklungsversionen, die es bereitstellen - es ist bereits heute in Firefox 3 verfügbar.
olliej
-aber leider nicht verfügbar in früheren Versionen von IE, die wir oft unterstützen müssen.
Keparo
22
navigator.onLine zeigt den Status des Browsers und nicht die tatsächliche Verbindung an. Sie können also Ihren Browser so einstellen, dass er online ist, aber es würde tatsächlich fehlschlagen, weil die Verbindung unterbrochen ist. navigator.onLine ist nur dann falsch, wenn der Browser auf Offline-Browsing eingestellt ist.
5
Wenn ich WI-FI auf meinem Nexus7 ausschalte, wird auf der Seite immer noch angezeigt, dass navigator.onLine TRUE ist. Schlecht ...
Walv
42

Fast alle gängigen Browser unterstützen jetzt die window.navigator.onLineEigenschaft sowie die entsprechenden onlineund offlineFensterereignisse:

window.addEventListener('online', () => console.log('came online'));
window.addEventListener('offline', () => console.log('came offline'));

Versuchen Sie, Ihr System oder Ihren Browser in den Offline- / Online-Modus zu versetzen, und überprüfen Sie die Konsole oder die window.navigator.onLineEigenschaft auf Wertänderungen. Sie können es auch auf dieser Website testen .

Beachten Sie jedoch dieses Zitat aus Mozilla-Dokumentation :

Wenn der Browser in Chrome und Safari keine Verbindung zu einem lokalen Netzwerk (LAN) oder einem Router herstellen kann, ist er offline. Alle anderen Bedingungen kehren zurück true. Während Sie also davon ausgehen können, dass der Browser offline ist, wenn er einen falseWert zurückgibt , Sie nicht davon ausgehen, dass ein trueWert zwangsläufig bedeutet, dass der Browser auf das Internet zugreifen kann . Möglicherweise werden Fehlalarme angezeigt, z. B. in Fällen, in denen auf dem Computer eine Virtualisierungssoftware ausgeführt wird, die über virtuelle Ethernet-Adapter verfügt, die immer "verbunden" sind. Wenn Sie den Online-Status des Browsers wirklich ermitteln möchten, sollten Sie daher zusätzliche Mittel zur Überprüfung entwickeln.

Wenn Sie in Firefox und Internet Explorer den Browser in den Offline-Modus schalten, wird ein falseWert gesendet. Bis Firefox 41 geben alle anderen Bedingungen a zurücktrue Wert zurück. Seit Firefox 41 unter OS X und Windows folgt der Wert der tatsächlichen Netzwerkkonnektivität.

(Betonung ist meine eigene)

Dies bedeutet, dass wenn window.navigator.onLineist false(oder Sie erhalten eineoffline Veranstaltung erhalten), garantiert keine Internetverbindung haben.

Wenn es trueaber ist (oder du bekommst eineonline Fall Ereignis erhalten), bedeutet dies nur, dass das System bestenfalls mit einem Netzwerk verbunden ist. Dies bedeutet nicht, dass Sie beispielsweise über einen Internetzugang verfügen. Um dies zu überprüfen, müssen Sie weiterhin eine der in den anderen Antworten beschriebenen Lösungen verwenden.

Ich hatte ursprünglich vor, dies als Update für Grant Wagners Antwort zu veröffentlichen , aber es schien zu viel Bearbeitung zu sein, insbesondere angesichts der Tatsache, dass das Update 2014 bereits nicht von ihm stammte .

Didier L.
quelle
Beste Antwort. Vielen Dank.
Vibs2006
1
Ich hatte kürzlich die Gelegenheit, ein wenig am Offline-Verhalten zu arbeiten. Die Veranstaltungen sind großartig zu nutzen, ABER ios Safari wird Probleme verursachen. Wenn Sie das Internet auf Ihrem Telefon ausschalten, werden die Offline- / Online-Ereignisse um bis zu 2 Sekunden verzögert. Dies kann aus Gründen des visuellen Renderns problematisch sein, da Sie die Zukunft nicht vorhersagen können. Das wollte ich nur erwähnen und könnte jemandem helfen.
TeeJaay
38

Es gibt verschiedene Möglichkeiten, dies zu tun:

  • AJAX-Anfrage an Ihre eigene Website. Wenn diese Anforderung fehlschlägt, besteht eine gute Chance, dass die Verbindung fehlerhaft ist. Die JQuery- Dokumentation enthält einen Abschnitt zur Behandlung fehlgeschlagener AJAX-Anforderungen . Achten Sie auf die gleiche Herkunftsrichtlinie , die Sie möglicherweise daran hindern, auf Websites außerhalb Ihrer Domain zuzugreifen.
  • Sie könnten eine onerrorin eine img, wie setzen

    <img src='http://www.example.com/singlepixel.gif' 
          onerror='alert("Connection dead");' />

    Diese Methode kann auch fehlschlagen, wenn das Quellbild verschoben / umbenannt wird, und ist im Allgemeinen der Ajax-Option unterlegen.

Es gibt also verschiedene Möglichkeiten, dies zu erkennen, keine ist perfekt, aber da es nicht möglich ist, aus der Browser-Sandbox zu springen und direkt auf den Netzverbindungsstatus des Benutzers zuzugreifen, scheinen sie die besten Optionen zu sein.

ConroyP
quelle
36
 if(navigator.onLine){
  alert('online');
 } else {
  alert('offline');
 }
Edmhs
quelle
11
Im Browser wird immer TRUE zurückgegeben.
Slavcho
2
Nun, zuerst habe ich versucht, NUR LAN zu deaktivieren, aber es gab immer WAHR zurück. Als ich alle Netzwerke (LAN2, Virtual Box usw.) deaktivierte, gab es FALSE zurück.
Slavcho
3
Diese Antwort dupliziert mehrere vorhandene Antworten aus 3 Jahren zuvor.
JasonMArcher
2
Es überprüft nicht die Internetverbindung, sondern nur die LAN-Verbindung
Suganth G
Arbeitete für mich in HTML 5, JavaScript, in Mac Book (mit WLAN) sogar in mobilen. Aber das Problem ist - wenn WLAN aktiviert ist, wird jedes Mal TRUE zurückgegeben, selbst wenn ich das WLAN deaktiviere, und umgekehrt.
S.Yadav
11

Die HTML5-Anwendungscache-API gibt navigator.onLine an, die derzeit in den IE8-Betas, WebKit-Nightlies (z. B. Safari) verfügbar ist und bereits in Firefox 3 unterstützt wird

olliej
quelle
11

Sie können mit $ Schnipsel () ‚s errorRückruf, das Feuer , wenn die Anforderung fehlschlägt. Wenn dies textStatusder Zeichenfolge "timeout" entspricht, bedeutet dies wahrscheinlich, dass die Verbindung unterbrochen ist:

function (XMLHttpRequest, textStatus, errorThrown) {
  // typically only one of textStatus or errorThrown 
  // will have info
  this; // the options for this ajax request
}

Aus dem Dokument :

Fehler : Eine Funktion, die aufgerufen werden soll, wenn die Anforderung fehlschlägt. Der Funktion werden drei Argumente übergeben: Das XMLHttpRequest-Objekt, eine Zeichenfolge, die den aufgetretenen Fehlertyp beschreibt, und ein optionales Ausnahmeobjekt, falls eines aufgetreten ist. Mögliche Werte für das zweite Argument (neben null) sind "timeout", "error", "notmodified" und "parsererror". Dies ist ein Ajax-Ereignis

Also zum Beispiel:

 $.ajax({
   type: "GET",
   url: "keepalive.php",
   success: function(msg){
     alert("Connection active!")
   },
   error: function(XMLHttpRequest, textStatus, errorThrown) {
       if(textStatus == 'timeout') {
           alert('Connection seems dead!');
       }
   }
 });
karim79
quelle
9

Wie olliej sagte, ist die Verwendung der navigator.onLineBrowsereigenschaft dem Senden von Netzwerkanforderungen vorzuziehen und wird dementsprechend mit developer.mozilla.org/En/Online_and_offline_events sogar von alten Versionen von Firefox und IE unterstützt.

Vor kurzem hat die WHATWG das Hinzufügen der onlineund -Ereignisse festgelegt offline, falls Sie auf navigator.onLineÄnderungen reagieren müssen .

Bitte beachten Sie auch den von Daniel Silveira geposteten Link, der darauf hinweist, dass es nicht immer eine gute Idee ist, sich bei der Synchronisierung mit dem Server auf dieses Signal / diese Eigenschaft zu verlassen.


quelle
UPDATE: Ab 2015 scheint es in den meisten Browsern zu funktionieren, siehe Caniuse-Tabelle und Artikel
Olga
7

Ich musste eine Web-App (Ajax-basiert) für einen Kunden erstellen, der viel mit Schulen arbeitet. Diese Schulen haben oft eine schlechte Internetverbindung. Ich benutze diese einfache Funktion, um festzustellen, ob eine Verbindung besteht. Funktioniert sehr gut!

Ich benutze CodeIgniter und Jquery:

function checkOnline() {
    setTimeout("doOnlineCheck()", 20000);
}

function doOnlineCheck() {
    //if the server can be reached it returns 1, other wise it times out
    var submitURL = $("#base_path").val() + "index.php/menu/online";

    $.ajax({
        url : submitURL,
        type : "post",
        dataType : "msg",
        timeout : 5000,
        success : function(msg) {
            if(msg==1) {
                $("#online").addClass("online");
                $("#online").removeClass("offline");
            } else {
                $("#online").addClass("offline");
                $("#online").removeClass("online");
            }
            checkOnline();
        },
        error : function() {
            $("#online").addClass("offline");
            $("#online").removeClass("online");
            checkOnline();
        }
    });
}
DAS Ö
quelle
7
window.navigator.onLine

ist das, wonach Sie suchen, aber einige Dinge, die Sie hier hinzufügen müssen, zuerst, wenn es sich um etwas in Ihrer App handelt, das Sie ständig überprüfen möchten (z. B. um zu sehen, ob der Benutzer plötzlich offline geht, was in diesem Fall die meiste Zeit korrigiert, dann Sie müssen auch auf Änderungen hören), damit Sie dem Fenster einen Ereignis-Listener hinzufügen, um Änderungen zu erkennen. Um zu überprüfen, ob der Benutzer offline geht, können Sie Folgendes tun:

window.addEventListener("offline", 
  ()=> console.log("No Internet")
);

und um zu überprüfen, ob online:

window.addEventListener("online", 
  ()=> console.log("Connected Internet")
);
Alireza
quelle
2
Du musst vorsichtig sein mit onLine. Browser definieren den Zustand, online zu sein, sehr unterschiedlich. Schauen Sie sich developer.mozilla.org/en-US/docs/Web/API/NavigatorOnLine/onLine an .
Andreas Baumgart
1
Ihre Antwort ist falsch. Die Eigenschaft 'onLine' hat nichts mit Internetkonnektivität zu tun. Siehe die obige Referenz zur Web-API.
Alexandre V.
6

Ein Ajax-Aufruf Ihrer Domain ist der einfachste Weg, um festzustellen, ob Sie offline sind

$.ajax({
      type: "HEAD",
      url: document.location.pathname + "?param=" + new Date(),
      error: function() { return false; },
      success: function() { return true; }
   });

Dies ist nur, um Ihnen das Konzept zu geben, es sollte verbessert werden.

ZB Fehler = 404 sollte immer noch bedeuten, dass Sie online sind

harishr
quelle
4

Ich denke, das ist ein sehr einfacher Weg.

var x = confirm("Are you sure you want to submit?");
if (x) {
  if (navigator.onLine == true) {
    return true;
  }
  alert('Internet connection is lost');
  return false;
}
return false;
Prakash Pazhanisamy
quelle
onLine bedeutet nicht, dass eine Internetverbindung besteht. Laut developer.mozilla.org/en-US/docs/Web/API/NavigatorOnLine/onLine if the browser is not able to connect to a local area network (LAN) or a router, it is offline; all other conditions return true
Shmuel Kamensky
2

Ich suchte nach einer clientseitigen Lösung, um festzustellen, ob das Internet oder mein Server ausgefallen war. Die anderen Lösungen, die ich gefunden habe, schienen immer von einer Skriptdatei oder einem Bild eines Drittanbieters abhängig zu sein, was für mich nicht so aussah, als würde es den Test der Zeit bestehen. Ein extern gehostetes Skript oder Image kann sich in Zukunft ändern und dazu führen, dass der Erkennungscode fehlschlägt.

Ich habe einen Weg gefunden, dies zu erkennen, indem ich nach einem xhrStatus mit einem 404-Code gesucht habe. Außerdem verwende ich JSONP, um die CORS-Einschränkung zu umgehen. Ein anderer Statuscode als 404 zeigt an, dass die Internetverbindung nicht funktioniert.

$.ajax({
    url:      'https://www.bing.com/aJyfYidjSlA' + new Date().getTime() + '.html',
    dataType: 'jsonp',
    timeout:  5000,

    error: function(xhr) {
        if (xhr.status == 404) {
            //internet connection working
        }
        else {
            //internet is down (xhr.status == 0)
        }
    }
});
Weg der Zukunft
quelle
2
Das funktioniert ab dem 05.10.2016 nicht mehr. Ich bin mir nicht sicher, warum ich nicht möchte, dass die Zeit anderer Leute verschwendet wird.
Bren
Ich denke nicht, dass es für verbotene und schlechte Anforderungsfehler funktionieren wird :)
Faisal Naseer
1

Meine Art.

<!-- the file named "tt.jpg" should exist in the same directory -->

<script>
function testConnection(callBack)
{
    document.getElementsByTagName('body')[0].innerHTML +=
        '<img id="testImage" style="display: none;" ' +
        'src="tt.jpg?' + Math.random() + '" ' +
        'onerror="testConnectionCallback(false);" ' +
        'onload="testConnectionCallback(true);">';

    testConnectionCallback = function(result){
        callBack(result);

        var element = document.getElementById('testImage');
        element.parentNode.removeChild(element);
    }    
}
</script>

<!-- usage example -->

<script>
function myCallBack(result)
{
    alert(result);
}
</script>

<a href=# onclick=testConnection(myCallBack);>Am I online?</a>
unxed
quelle
1

Das Problem einiger Methoden wie navigator.onLineist, dass sie nicht mit einigen Browsern und mobilen Versionen kompatibel sind. Eine Option, die mir sehr geholfen hat, war die Verwendung der klassischen XMLHttpRequestMethode und auch die Möglichkeit, dass die Datei im Cache gespeichert wurde und die Antwort XMLHttpRequest.statusgrößer ist als 200 und weniger als 304.

Hier ist mein Code:

 var xhr = new XMLHttpRequest();
 //index.php is in my web
 xhr.open('HEAD', 'index.php', true);
 xhr.send();

 xhr.addEventListener("readystatechange", processRequest, false);

 function processRequest(e) {
     if (xhr.readyState == 4) {
         //If you use a cache storage manager (service worker), it is likely that the
         //index.php file will be available even without internet, so do the following validation
         if (xhr.status >= 200 && xhr.status < 304) {
             console.log('On line!');
         } else {
             console.log('Offline :(');
         }
     }
}
Vladimir Salguero
quelle
0

Es gibt zwei Antworten für zwei verschiedene Szenarien: -

  1. Wenn Sie JavaScript auf einer Website (dh einem Front-End-Teil) verwenden, ist dies am einfachsten:

    <h2>The Navigator Object</h2>
    
    <p>The onLine property returns true if the browser is online:</p>
    
    <p id="demo"></p>
    
    <script>
      document.getElementById("demo").innerHTML = "navigator.onLine is " + navigator.onLine;
    </script>

  2. Wenn Sie jedoch js auf der Serverseite verwenden (z. B. Knoten usw.), können Sie feststellen, dass die Verbindung unterbrochen wird, indem Sie fehlgeschlagene XHR-Anforderungen stellen.

    Der Standardansatz besteht darin, die Anforderung einige Male zu wiederholen. Wenn dies nicht der Fall ist, benachrichtigen Sie den Benutzer, um die Verbindung zu überprüfen, und schlagen Sie ordnungsgemäß fehl.

Rishabh Anand
quelle
0

Anforderungskopf im Anforderungsfehler

$.ajax({
    url: /your_url,
    type: "POST or GET",
    data: your_data,
    success: function(result){
      //do stuff
    },
    error: function(xhr, status, error) {

      //detect if user is online and avoid the use of async
        $.ajax({
            type: "HEAD",
            url: document.location.pathname,
            error: function() { 
              //user is offline, do stuff
              console.log("you are offline"); 
              }
         });
    }   
});
Kareem
quelle
-1

Hier ist ein Ausschnitt eines Hilfsprogramms, das ich habe. Dies ist Javascript mit Namespace:

network: function() {
    var state = navigator.onLine ? "online" : "offline";
    return state;
}

Sie sollten dies mit der Methodenerkennung verwenden, da sonst eine alternative Methode ausgelöst wird. Die Zeit rückt immer näher, wenn dies alles ist, was benötigt wird. Die anderen Methoden sind Hacks.

Peter Mortensen
quelle