كيفية التحقق إذا كان اتصال الإنترنت موجود في جافا ؟

StackOverflow https://stackoverflow.com/questions/1402005

  •  05-07-2019
  •  | 
  •  

سؤال

كيف يمكنك معرفة ما اذا كان يمكنك الاتصال بالإنترنت عن طريق جافا ؟ طريقة واحدة ليكون:

final URL url = new URL("http://www.google.com");
final URLConnection conn = url.openConnection();
... if we got here, we should have net ...

ولكن هل هناك شيء أكثر ملاءمة لأداء هذه المهمة ، خاصة إذا كنت بحاجة إلى القيام به متتالية الشيكات في كثير من الأحيان وفقدان الاتصال بالإنترنت عالية محتمل ؟

هل كانت مفيدة؟

المحلول

يجب عليك الاتصال إلى مكان التطبيق الفعلي الاحتياجات.وإلا أنت اختبار ما إذا كان لديك اتصال إلى مكان غير ذي صلة (جوجل في هذه الحالة).

ولا سيما إذا كنت تحاول التحدث إلى خدمة ويب إذا كنت في السيطرة خدمة ويب ، فإنه سيكون فكرة جيدة أن يكون نوعا من رخيصة "على وضع" الشبكة الأسلوب.بهذه الطريقة يكون لديك فكرة أفضل بكثير من ما إذا كانت "حقيقية" دعوة من المرجح أن تعمل.

في حالات أخرى, مجرد فتح اتصال إلى منفذ ينبغي أن تكون مفتوحة قد تكون كافية - أو إرسال بينغ. InetAddress.isReachable قد تكون API المناسبة لتلبية الاحتياجات الخاصة بك هنا.

نصائح أخرى

الكود أساسا ، بالإضافة إلى الدعوة إلى connect ينبغي أن يكون كافيا.لذا نعم, يمكن أن يكون ذلك فقط من جوجل ليست متوفرة ولكن بعض المواقع الأخرى تحتاج إلى الاتصال على ولكن كيف يحتمل هذا ؟ أيضا, هذا الرمز يجب أن تنفذ فقط عندما كنت في الواقع تفشل في الوصول إلى الموارد الخارجية (في catch كتلة إلى محاولة معرفة ما سبب الفشل كان) لذا أقول إذا كان كل الموارد الخارجية من الفائدة و جوجل لا تتوفر وهناك احتمالات لديك صافي مشكلة في الاتصال.

private static boolean netIsAvailable() {
    try {
        final URL url = new URL("http://www.google.com");
        final URLConnection conn = url.openConnection();
        conn.connect();
        conn.getInputStream().close();
        return true;
    } catch (MalformedURLException e) {
        throw new RuntimeException(e);
    } catch (IOException e) {
        return false;
    }
}

الناس قد اقترح استخدام INetAddress.بهذه الصيغة..المشكلة هي أن بعض المواقع تكوين جدران الحماية لمنع Ping ICMP الرسائل.لذلك "بينغ" قد تفشل على الرغم من خدمة ويب يمكن الوصول إليها.

وبالطبع العكس صحيح كذلك.مجموعة قد يستجيب بينغ على الرغم من خادم الويب إلى أسفل.

وبطبيعة الحال, آلة قد تكون غير قادر على الاتصال مباشرة إلى بعض (أو كل) ملقمات ويب بسبب جدار الحماية المحلي قيود.

المشكلة الأساسية هي أن "الاتصال بالإنترنت" هو سوء الأسئلة المحددة ، وهذا النوع من الشيء الصعب أن هذا الاختبار:

  1. معلومات عن الجهاز المستخدم و "المحلية" بيئة الشبكات ،
  2. معلومات عن التطبيق يحتاج إلى الوصول إليها.

عموما حتى أبسط حل هو التطبيق فقط في محاولة الوصول إلى ما فإنه يحتاج إلى الوصول ، تقع مرة أخرى على الذكاء البشري للقيام التشخيص.

إذا كنت على جافا 6 يمكن استخدام NetworkInterface للتحقق من واجهات شبكة الاتصال المتوفرة.أولا-هاء.شيء من هذا القبيل:

Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces();
while (interfaces.hasMoreElements()) {
  NetworkInterface interf = interfaces.nextElement();
  if (interf.isUp() && !interf.isLoopback())
    return true;
}

لم تكن قد حاولت ذلك بنفسي بعد.

هذا الكود:

"127.0.0.1".equals(InetAddress.getLocalHost().getHostAddress().toString());

يعود - لي - true إذا حاليا ، false, خلاف ذلك.(حسنا, أنا لا أعرف إذا كان هذا صحيحا أن جميع أجهزة الكمبيوتر).

هذا يعمل بشكل أسرع بكثير من الأساليب الأخرى هنا.


تحرير:لقد وجدت هذا يعمل فقط إذا كان "تبديل الوجه" (على الحاسوب) أو نظام تحديد الخيار للاتصال بالإنترنت ، هو خارج.أن النظام نفسه لا يعرف للبحث عن أي عناوين IP.

هذا الرمز ينبغي القيام بهذه المهمة بشكل موثوق.

لاحظ أنه عند استخدام try-with-resources بيان نحن لا نحتاج إلى إغلاق الموارد.

import java.io.IOException;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.net.UnknownHostException;

public class InternetAvailabilityChecker
{
    public static boolean isInternetAvailable() throws IOException
    {
        return isHostAvailable("google.com") || isHostAvailable("amazon.com")
                || isHostAvailable("facebook.com")|| isHostAvailable("apple.com");
    }

    private static boolean isHostAvailable(String hostName) throws IOException
    {
        try(Socket socket = new Socket())
        {
            int port = 80;
            InetSocketAddress socketAddress = new InetSocketAddress(hostName, port);
            socket.connect(socketAddress, 3000);

            return true;
        }
        catch(UnknownHostException unknownHost)
        {
            return false;
        }
    }
}

وعادة ما كسر عليه في ثلاث خطوات.

  1. أولا أنا أرى إن كنت أستطيع حل اسم النطاق إلى عنوان IP.
  2. ثم محاولة الاتصال عبر TCP (المنفذ 80 أو 443) وإغلاق بأمان.
  3. أخيرا, سوف مسألة طلب HTTP والتحقق من 200 رد.

إذا فشلت في أي لحظة ، أنا عند ظهور رسالة خطأ للمستخدم.

URL url=new URL("http://[any domain]");
URLConnection con=url.openConnection();

/*now errors WILL arise here, i hav tried myself and it always shows "connected" so we'll open an InputStream on the connection, this way we know for sure that we're connected to d internet */

/* Get input stream */
con.getInputStream();

وضع البيانات المذكورة أعلاه في محاولة قبض كتل إذا كان استثناء في القبض يعني أنه لا يوجد اتصال إنترنت المنشأة.:-)

رمز باستخدام NetworkInterface الانتظار الشبكة عملت بالنسبة لي حتى تحولت من الشبكة الثابتة عنوان DHCP.تحسن طفيف يجعل العمل أيضا مع DHCP:

Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces();
while (interfaces.hasMoreElements()) {
    NetworkInterface interf = interfaces.nextElement();
    if (interf.isUp() && !interf.isLoopback()) {
    List<InterfaceAddress> adrs = interf.getInterfaceAddresses();
    for (Iterator<InterfaceAddress> iter = adrs.iterator(); iter.hasNext();) {
        InterfaceAddress adr = iter.next();
        InetAddress inadr = adr.getAddress();
        if (inadr instanceof Inet4Address) return true;
            }
    }
}

هذا يعمل على جافا 7 في openSuse 13.1 على الشبكة IPv4.مشكلة مع رمز الأصلي هو أنه على الرغم من أن واجهة المستخدم حتى بعد استئناف من تعليق IPv4 عنوان الشبكة لم يتم تعيينها حتى الآن.بعد انتظار هذه المهمة, البرنامج يمكن الاتصال إلى ملقمات.ولكن ليس لدي أي فكرة ما يجب القيام به في حالة IPv6.

InetAddress.isReachable في وقت ما return false إذا كان اتصال إنترنت موجود.

طريقة بديلة للتحقق من توفر خدمة الإنترنت في جافا :هذه الوظيفة تجعل الحقيقي ICMP ECHO بينغ.

public static boolean isReachableByPing(String host) {
     try{
                String cmd = "";
                if(System.getProperty("os.name").startsWith("Windows")) {   
                        // For Windows
                        cmd = "ping -n 1 " + host;
                } else {
                        // For Linux and OSX
                        cmd = "ping -c 1 " + host;
                }

                Process myProcess = Runtime.getRuntime().exec(cmd);
                myProcess.waitFor();

                if(myProcess.exitValue() == 0) {

                        return true;
                } else {

                        return false;
                }

        } catch( Exception e ) {

                e.printStackTrace();
                return false;
        }
}

1) معرفة أين التطبيق الخاص بك يحتاج إلى أن تكون متصلا.

2) إعداد عامل عملية التحقق InetAddress.بهذه الصيغة. رصد اتصال إلى هذا العنوان.

هذا الرمز هو الوارد في غضون jUnit اختبار الصف الأول استخدامها لاختبار إذا كان اتصال متوفرة.وأنا دائما الحصول على اتصال ، ولكن إذا كان يمكنك التحقق من المحتوى طول ينبغي -1 إذا كان لا يعرف :

  try {
    URL url = new URL("http://www.google.com");
    URLConnection connection = url.openConnection();

    if(connection.getContentLength() == -1){
          fail("Failed to verify connection");
    }
  } 
  catch (IOException e) {
      fail("Failed to open a connection");
      e.printStackTrace();
  }
public boolean checkInternetConnection()
{
     boolean status = false;
     Socket sock = new Socket();
     InetSocketAddress address = new InetSocketAddress("www.google.com", 80);

     try
     {
        sock.connect(address, 3000);
        if(sock.isConnected()) status = true;
     }
     catch(Exception e)
     {
         status = false;       
     }
     finally
     {
        try
         {
            sock.close();
         }
         catch(Exception e){}
     }

     return status;
}

وهناك أيضا gradle الخيار --offline التي ربما نتائج في السلوك تريد.

الجزء التالي من التعليمات البرمجية يسمح لنا للحصول على وضع الشبكة على جهاز الروبوت لدينا

public class MainActivity extends AppCompatActivity {
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            TextView mtv=findViewById(R.id.textv);
            ConnectivityManager connectivityManager=
                  (ConnectivityManager) this.getSystemService(Context.CONNECTIVITY_SERVICE);
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                if(((Network)connectivityManager.getActiveNetwork())!=null)
                    mtv.setText("true");
                else
                    mtv.setText("fasle");
            }
        }
    }
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top