java InetAddress.getLocalHost ()؛ يعود 127.0.0.1 ... كيفية الحصول على IP الحقيقي؟


Answers

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

// output on my machine: "192.168.1.102"
Socket s = new Socket("192.168.1.1", 80);
System.out.println(s.getLocalAddress().getHostAddress());
s.close();

// output on my machine: "127.0.1.1"
System.out.println(InetAddress.getLocalHost().getHostAddress());

لست متأكدا ما إذا كان من الممكن القيام بذلك دون إنشاء اتصال بالرغم من ذلك. أعتقد أنني تمكنت ذات مرة من فعل ذلك مع بيرل (أو سي؟) ، ولكن لا تسألني عن جافا. أعتقد أنه قد يكون من الممكن إنشاء مأخذ توصيل UDP (DatagramSocket) دون توصيله بالفعل.

إذا كان هناك جهاز توجيه NAT على الطريقة التي لن تتمكن من الحصول على IP سوف ترى ذلك المضيف البعيد. ومع ذلك ، كما أعطيت 192. * كمثال ، أعتقد أنك لا تهتم.

Question

أنا اكتب تطبيقًا بسيطًا للتواصل ... أحتاج إلى معرفة الملكية الفكرية الحقيقية لجهازي على الشبكة ، مثل 192.168.1.3. getLocalHost يعود 127.0.0.1 (على لينكس ، دونو إذا كان هو نفسه على النوافذ) كيف نفعل ذلك؟




احصل على الطلب الحالي من المثيل الحالي

HttpServletRequest httpServletRequest = (HttpServletRequest) FacesContext.getCurrentInstance().getExternalContext().getRequest();

ثم الحصول على العنوان من الطلب

ip = httpServletRequest.getRemoteAddr();



فيما يلي طريقة لتجنب نتائج IPv6 و Loopback.

public InetAddress getCurrentIp() {
            try {
                Enumeration<NetworkInterface> networkInterfaces = NetworkInterface
                        .getNetworkInterfaces();
                while (networkInterfaces.hasMoreElements()) {
                    NetworkInterface ni = (NetworkInterface) networkInterfaces
                            .nextElement();
                    Enumeration<InetAddress> nias = ni.getInetAddresses();
                    while(nias.hasMoreElements()) {
                        InetAddress ia= (InetAddress) nias.nextElement();
                        if (!ia.isLinkLocalAddress() 
                         && !ia.isLoopbackAddress()
                         && ia instanceof Inet4Address) {
                            return ia;
                        }
                    }
                }
            } catch (SocketException e) {
                LOG.error("unable to get current IP " + e.getMessage(), e);
            }
            return null;
        }



بدلاً من استخدام InetAddress.getHostAddress () ، يمكنني استدعاء روتين getHost4Address الذي كتبته للحصول على العنوان الأول غير الاسترجاع ...

/**
 * Returns this host's non-loopback IPv4 addresses.
 * 
 * @return
 * @throws SocketException 
 */
private static List<Inet4Address> getInet4Addresses() throws SocketException {
    List<Inet4Address> ret = new ArrayList<Inet4Address>();

    Enumeration<NetworkInterface> nets = NetworkInterface.getNetworkInterfaces();
    for (NetworkInterface netint : Collections.list(nets)) {
        Enumeration<InetAddress> inetAddresses = netint.getInetAddresses();
        for (InetAddress inetAddress : Collections.list(inetAddresses)) {
            if (inetAddress instanceof Inet4Address && !inetAddress.isLoopbackAddress()) {
                ret.add((Inet4Address)inetAddress);
            }
        }
    }

    return ret;
}

/**
 * Returns this host's first non-loopback IPv4 address string in textual
 * representation.
 * 
 * @return
 * @throws SocketException
 */
private static String getHost4Address() throws SocketException {
    List<Inet4Address> inet4 = getInet4Addresses();
    return !inet4.isEmpty()
            ? inet4.get(0).getHostAddress()
            : null;
}



Links