723 Stimmen

Wie prüft man den Internetzugang auf Android? InetAddress schaltet nie ab

Ich habe eine AsyncTask das den Netzzugang zu einem Hostnamen überprüfen soll. Aber die doInBackground() ist nie zeitlich begrenzt. Hat jemand einen Hinweis?

public class HostAvailabilityTask extends AsyncTask<String, Void, Boolean> {

    private Main main;

    public HostAvailabilityTask(Main main) {
        this.main = main;
    }

    protected Boolean doInBackground(String... params) {
        Main.Log("doInBackground() isHostAvailable():"+params[0]);

        try {
            return InetAddress.getByName(params[0]).isReachable(30); 
        } catch (UnknownHostException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return false;       
    }

    protected void onPostExecute(Boolean... result) {
        Main.Log("onPostExecute()");

        if(result[0] == false) {
            main.setContentView(R.layout.splash);
            return;
        }

        main.continueAfterHostCheck();
    }   
}

7 Stimmen

Um zu prüfen, ob eine Internetverbindung besteht, ist es wahrscheinlich am zuverlässigsten, einen der großen Nameserver anzupingen, z. B. mit if(Runtime.getRuntime().exec("/system/bin/ping -c 1 8.8.8.8").waitFor()==0) ... . Siehe meine Antwort für eine schönere Implementierung dieser Funktion. Btw die akzeptierte Antwort (und viele andere hier) einfach nach einem Netzanschluss und nicht das Internet.

0 Stimmen

4 Stimmen

Verwenden Sie nicht die Ping-Methode, sondern eine HTTP-Überprüfung. ICMP wird in einigen Netzen blockiert, so dass Ping nicht funktioniert. Beispiel: Bei mir zu Hause funktioniert es einwandfrei, aber nicht, wenn ich mobile Daten im Netz von Vodafone (in Ungarn) verwende. Sie können die beiden Methoden auch kombinieren, aber seien Sie vorsichtig, denn waitFor() wartet etwa 20 Sekunden, auch wenn -w oder -W verwendet wird.

6voto

Vidar Vestnes Punkte 41974

Ich verwende diesen Code anstelle der InetAddress:

    try {

        URL url = new URL("http://"+params[0]);

        HttpURLConnection urlc = (HttpURLConnection) url.openConnection();
        urlc.setRequestProperty("User-Agent", "Android Application:"+Z.APP_VERSION);
        urlc.setRequestProperty("Connection", "close");
        urlc.setConnectTimeout(1000 * 30); // mTimeout is in seconds
        urlc.connect();
        if (urlc.getResponseCode() == 200) {
            Main.Log("getResponseCode == 200");
            return new Boolean(true);
        }
    } catch (MalformedURLException e1) {
        // TODO Auto-generated catch block
        e1.printStackTrace();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

0 Stimmen

Es wäre toll, wenn Sie geklärt hätten, ob die IOException keine Internetverbindung bedeutet und wie zuverlässig sie sein könnte.

0 Stimmen

Bei mir funktioniert es, aber ich muss "http://" in "https://" umwandeln. Wenn ich nicht konvertiere, tritt der Fehler "Cleartext HTTP traffic to www.yourSite.com not permitted" auf.

6voto

laplasz Punkte 3111

Für mich war es keine gute Praxis, den Verbindungsstatus in der Activity-Klasse zu überprüfen, weil

ConnectivityManager cm =
    (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);

sollte dort aufgerufen werden, oder Sie müssen Ihre Activity-Instanz (Kontext) an die Connection-Handler-Klasse weiterreichen, um den Verbindungsstatus dort überprüfen zu können Wenn keine Verbindung verfügbar ist (Wifi, Netzwerk), fange ich die UnknownHostException Ausnahme:

JSONObject jObj = null;
Boolean responded = false;
HttpGet requestForTest = new HttpGet("http://myserver.com");
try {
    new DefaultHttpClient().execute(requestForTest);
    responded = true;
} catch (UnknownHostException e) {
    jObj = new JSONObject();
    try {
        jObj.put("answer_code", 1);
        jObj.put("answer_text", "No available connection");
    } catch (Exception e1) {}
    return jObj;
} catch (IOException e) {
    e.printStackTrace();
}

Auf diese Weise kann ich diesen Fall zusammen mit den anderen Fällen in der gleichen Klasse behandeln (mein Server antwortet immer mit einem Json-String zurück)

6voto

Lo Juego Punkte 1275

Bester Ansatz:

public static boolean isOnline() {
    try {
    InetAddress.getByName("google.com").isReachable(3);

    return true;
    } catch (UnknownHostException e){
    return false;
    } catch (IOException e){
    return false;
    }
    }

1 Stimmen

Mir gefällt dieser Ansatz, aber ich muss auf einige Dinge hinweisen. isReachable() gibt einen booleschen Wert zurück. Anstatt also im try-Abschnitt true zurückzugeben, könnte man es so machen: boolean connected = InetAddress.getByName("google.com").isReachable(3); dann return connected. Außerdem löst isReacheable die Ausnahmen IOException und IllegalArgumentException aus. Daher ist es eine gute Idee, UnknownHostException durch IllegalArgumentException zu ersetzen und einen dritten Catch einzufügen: catch (Exception E).

2 Stimmen

Aber dann verwendet isReachable ICMP, was Root-Rechte erfordern könnte, und verwendet Port 7, auf dem auf den neuesten Systemen normalerweise keine Dienste laufen. Daher ist der beste Weg, die Route zu einem Online-Dienst zu überprüfen, normales TCP.

5voto

Mahendra Liya Punkte 11992

Nachfolgend ist der Code aus meinem Utils Klasse:

public static boolean isNetworkAvailable(Context context) {
        ConnectivityManager connectivityManager 
              = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo activeNetworkInfo = connectivityManager.getActiveNetworkInfo();
        return activeNetworkInfo != null && activeNetworkInfo.isConnected();
}

5voto

JSupport Punkte 51

Es ist nicht schwer, den Status der Netzwerk-/Internetkonnektivität von Android zu überprüfen. Die unten DetectConnection Klasse hilft Ihnen, diesen Status zu überprüfen:

import android.content.Context;
import android.net.ConnectivityManager;

public class DetectConnection {
    public static boolean checkInternetConnection(Context context) {
        ConnectivityManager con_manager = (ConnectivityManager) context
                                .getSystemService(Context.CONNECTIVITY_SERVICE);

        if (con_manager.getActiveNetworkInfo() != null
            && con_manager.getActiveNetworkInfo().isAvailable()
            && con_manager.getActiveNetworkInfo().isConnected()) {
                return true;
        } else {
            return false;
        }
    }
}

Für weitere Informationen besuchen Sie Wie man den Status der Netzwerk-/Internetverbindung von Android überprüft

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X