Uzyskiwanie adresu IP bieżącego komputera za pomocą Java

291

Usiłuję opracować system, w którym istnieją różne węzły działające w innym systemie lub na różnych portach w tym samym systemie.

Teraz wszystkie węzły tworzą gniazdo z docelowym adresem IP jako adresem IP specjalnego węzła zwanego węzłem ładowania początkowego. Węzły następnie tworzą własne ServerSocketi zaczynają nasłuchiwać połączeń.

Węzeł ładowania początkowego utrzymuje listę węzłów i zwraca je po zapytaniu.

Teraz potrzebuję, aby węzeł zarejestrował swój adres IP w węźle ładowania początkowego. Próbowałem użyć, cli.getInetAddress()gdy klient łączy się ServerSocketz węzłem ładowania początkowego, ale to nie działało.

  1. Potrzebuję klienta do zarejestrowania jego adresu IP PPP, jeśli jest dostępny;
  2. W przeciwnym razie adres IP sieci LAN, jeśli jest dostępny;
  3. W przeciwnym razie musi zarejestrować 127.0.0.1, zakładając, że jest to ten sam komputer.

Za pomocą kodu:

System.out.println(Inet4Address.getLocalHost().getHostAddress());

lub

System.out.println(InetAddress.getLocalHost().getHostAddress());

Mój adres IP połączenia PPP to: 117.204.44.192, ale powyższe zwraca mi 192.168.1.2

EDYTOWAĆ

Korzystam z następującego kodu:

Enumeration e = NetworkInterface.getNetworkInterfaces();
while(e.hasMoreElements())
{
    NetworkInterface n = (NetworkInterface) e.nextElement();
    Enumeration ee = n.getInetAddresses();
    while (ee.hasMoreElements())
    {
        InetAddress i = (InetAddress) ee.nextElement();
        System.out.println(i.getHostAddress());
    }
}

Jestem w stanie uzyskać wszystkie adresy IP powiązane wszystkie NetworkInterface, ale jak je rozróżnić? To jest wynik, który otrzymuję:

127.0.0.1
192.168.1.2
192.168.56.1
117.204.44.19
sasidhar
źródło
Inet4Address.getLocalHost () powinien działać poprawnie?
Sears India
3
Jeśli dodam n.isPointToPoint (), czy to zadziała? Moim pomysłem jest zwrócenie „127.0.0.1”, jeśli nie zostanie znaleziona sieć Point to Point. Czy to będzie działało??
sasidhar
3
@sasidhar: Nie publikuj swojego prawdziwego adresu IP. napisz 117.xxx.xxx.xxx, dla prywatnego adresu IP jest w porządku.
NICe COW
@GagandeepBali Dzięki za radę, ale mój adres IP to dynamiczny adres IP i otrzymuję nowy adres IP za każdym razem, gdy rozłączam się i łączę z Internetem. Chyba nie powinno to stanowić problemu.
sasidhar
2
Powiązane: stackoverflow.com/questions/6064510/…
AlikElzin-kilaka

Odpowiedzi:

115
import java.net.DatagramSocket;
import java.net.InetAddress;

try(final DatagramSocket socket = new DatagramSocket()){
  socket.connect(InetAddress.getByName("8.8.8.8"), 10002);
  ip = socket.getLocalAddress().getHostAddress();
}

Ten sposób działa dobrze, gdy istnieje wiele interfejsów sieciowych. Zawsze zwraca preferowane wychodzące IP. Miejsce docelowe 8.8.8.8nie musi być osiągalne.

Connectna gnieździe UDP ma następujący efekt: ustawia miejsce docelowe dla Send / Recv, odrzuca wszystkie pakiety z innych adresów i - co właśnie używamy - przenosi gniazdo do stanu „podłączonego”, ustawia odpowiednie pola. Obejmuje to sprawdzenie istnienia trasy do miejsca docelowego zgodnie z tablicą routingu systemu i odpowiednie ustawienie lokalnego punktu końcowego. Ostatnia część wydaje się być nieudokumentowana oficjalnie, ale wygląda na integralną cechę API gniazd Berkeley (efekt uboczny stanu „podłączonego” UDP), który działa niezawodnie zarówno w systemie Windows, jak i Linux w różnych wersjach i dystrybucjach.

Tak więc ta metoda da adres lokalny, który będzie używany do łączenia się z określonym hostem zdalnym. Nie ustanowiono rzeczywistego połączenia, dlatego określony zdalny adres IP może być nieosiągalny.

Edytować:

Jak mówi @macomgil , w MacOS możesz to zrobić:

Socket socket = new Socket();
socket.connect(new InetSocketAddress("google.com", 80));
System.out.println(socket.getLocalAddress());
Mr.Wang z Next Door
źródło
7
Działa to dla mnie na Linuksie, ale na OsX otrzymuję: „0.0.0.0”
Radu Toader
@Jeef, odpowiedź została zaktualizowana. Jeśli to nie działa na OsX, musisz wybrać inny sposób.
Mr.Wang z Next Door
1
Znakomity! Do twojej wiadomości, gdy masz do czynienia z zamkniętą siecią wewnętrzną, po prostu zamień 8.8.8.8 na coś, co każdy host może osiągnąć
Murphy Ng
Działa w systemie Windows; czy możemy potwierdzić, czy OSX nadal stanowi problem?
trylogia
4
@ Trylogia Nadal dostaję 0.0.0.0 na OSX
Peter Tutervai
273

W najbardziej ogólnym przypadku może to być nieco trudne.

Na pierwszy rzut oka InetAddress.getLocalHost()powinien podać adres IP tego hosta. Problem polega na tym, że host może mieć wiele interfejsów sieciowych, a interfejs może być powiązany z więcej niż jednym adresem IP. Co więcej, nie wszystkie adresy IP będą dostępne poza urządzeniem lub siecią LAN. Mogą to być na przykład adresy IP wirtualnych urządzeń sieciowych, adresy IP prywatnych sieci i tak dalej.

Oznacza to, że adres IP został zwrócony przez InetAddress.getLocalHost() może być niewłaściwy do użycia.

Jak sobie z tym poradzić?

  • Jednym z podejść jest użycie NetworkInterface.getNetworkInterfaces()wszystkich znanych interfejsów sieciowych na hoście, a następnie iteracja po adresach każdego NI.
  • Innym podejściem jest (jakoś) uzyskanie reklamowanej zewnętrznie nazwy FQDN dla hosta i użycie InetAddress.getByName()do wyszukania podstawowego adresu IP. (Ale jak to zdobyć i jak radzić sobie z modułem równoważenia obciążenia opartym na DNS?)
  • Wariantem poprzedniego jest uzyskanie preferowanej nazwy FQDN z pliku konfiguracyjnego lub parametru wiersza polecenia.
  • Inną odmianą jest uzyskanie preferowanego adresu IP z pliku konfiguracyjnego lub parametru wiersza poleceń.

Podsumowując, InetAddress.getLocalHost()zazwyczaj działa, ale może być konieczne podanie alternatywnej metody dla przypadków, w których kod jest uruchamiany w środowisku z „skomplikowanymi” sieciami.


Jestem w stanie uzyskać wszystkie adresy IP powiązane ze wszystkimi interfejsami sieciowymi, ale jak je odróżnić?

  • Każdy adres z zakresu 127.xxx.xxx.xxx jest adresem „pętli zwrotnej”. Jest widoczny tylko dla „tego” hosta.
  • Dowolny adres z zakresu 192.168.xxx.xxx jest prywatnym adresem (lokalnie lokalnym). Są one zastrzeżone do użytku w organizacji. To samo dotyczy adresów 10.xxx.xxx.xxx i 172.16.xxx.xxx do 172.31.xxx.xxx.
  • Adresy z zakresu 169.254.xxx.xxx to lokalne adresy IP łącza. Są one zastrzeżone do użytku w jednym segmencie sieci.
  • Adresy z zakresu od 224.xxx.xxx.xxx do 239.xxx.xxx.xxx to adresy multiemisji.
  • Adres 255.255.255.255 to adres rozgłoszeniowy.
  • Wszystko inne powinno być prawidłowym publicznym adresem IPv4 typu punkt-punkt.

W rzeczywistości interfejs API InetAddress zapewnia metody testowania adresów pętli zwrotnej, linków lokalnych, lokalnych witryn, adresów multiemisji i rozgłaszania. Możesz ich użyć, aby ustalić, który z odzyskanych adresów IP jest najbardziej odpowiedni.

Stephen C.
źródło
3
Jeśli ktoś jest ciekawy, getLocalHost zasadniczo sprawdza DNS na nazwie hosta serwera. Jeśli pobierze adres IP z tego wyszukiwania, przeszukuje dostępne interfejsy, aby zobaczyć, który interfejs ma ten adres IP, i zwraca ten interfejs. Oznacza to, że getLocalHost będzie działał w środowisku „serwera”, w którym wychodzące IP jest tym, które mapuje nazwę hosta serwera.
Tempo
1
W Ubuntu 14.04 ten interfejs zwraca 127.0.1.1, nawet jeśli ifconfig zgłasza tylko dwa interfejsy, ten, którego chcę (publicznie dostępny adres IP) i sprzężenie zwrotne (127.0.0.1). Dziwne, że zwraca inny alias pętli zwrotnej.
ctpenrose
Dodam, że jeśli use getLocalHost().getHostAddress()coś opublikujesz, możesz to zobaczyć 0.0.0.0, patrząc z innego komputera w sieci. Jest to wyjaśnione tutaj to jest to, co się ze mną stało, kiedy używałem Gazebo na dwóch komputerach
Peter Mitrano
57

Opublikowanie tutaj przetestowanego kodu obejścia niejednoznaczności IP z https://issues.apache.org/jira/browse/JCS-40 (InetAddress.getLocalHost () niejednoznaczne w systemach Linux):

/**
 * Returns an <code>InetAddress</code> object encapsulating what is most likely the machine's LAN IP address.
 * <p/>
 * This method is intended for use as a replacement of JDK method <code>InetAddress.getLocalHost</code>, because
 * that method is ambiguous on Linux systems. Linux systems enumerate the loopback network interface the same
 * way as regular LAN network interfaces, but the JDK <code>InetAddress.getLocalHost</code> method does not
 * specify the algorithm used to select the address returned under such circumstances, and will often return the
 * loopback address, which is not valid for network communication. Details
 * <a href="http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4665037">here</a>.
 * <p/>
 * This method will scan all IP addresses on all network interfaces on the host machine to determine the IP address
 * most likely to be the machine's LAN address. If the machine has multiple IP addresses, this method will prefer
 * a site-local IP address (e.g. 192.168.x.x or 10.10.x.x, usually IPv4) if the machine has one (and will return the
 * first site-local address if the machine has more than one), but if the machine does not hold a site-local
 * address, this method will return simply the first non-loopback address found (IPv4 or IPv6).
 * <p/>
 * If this method cannot find a non-loopback address using this selection algorithm, it will fall back to
 * calling and returning the result of JDK method <code>InetAddress.getLocalHost</code>.
 * <p/>
 *
 * @throws UnknownHostException If the LAN address of the machine cannot be found.
 */
private static InetAddress getLocalHostLANAddress() throws UnknownHostException {
    try {
        InetAddress candidateAddress = null;
        // Iterate all NICs (network interface cards)...
        for (Enumeration ifaces = NetworkInterface.getNetworkInterfaces(); ifaces.hasMoreElements();) {
            NetworkInterface iface = (NetworkInterface) ifaces.nextElement();
            // Iterate all IP addresses assigned to each card...
            for (Enumeration inetAddrs = iface.getInetAddresses(); inetAddrs.hasMoreElements();) {
                InetAddress inetAddr = (InetAddress) inetAddrs.nextElement();
                if (!inetAddr.isLoopbackAddress()) {

                    if (inetAddr.isSiteLocalAddress()) {
                        // Found non-loopback site-local address. Return it immediately...
                        return inetAddr;
                    }
                    else if (candidateAddress == null) {
                        // Found non-loopback address, but not necessarily site-local.
                        // Store it as a candidate to be returned if site-local address is not subsequently found...
                        candidateAddress = inetAddr;
                        // Note that we don't repeatedly assign non-loopback non-site-local addresses as candidates,
                        // only the first. For subsequent iterations, candidate will be non-null.
                    }
                }
            }
        }
        if (candidateAddress != null) {
            // We did not find a site-local address, but we found some other non-loopback address.
            // Server might have a non-site-local address assigned to its NIC (or it might be running
            // IPv6 which deprecates the "site-local" concept).
            // Return this non-loopback candidate address...
            return candidateAddress;
        }
        // At this point, we did not find a non-loopback address.
        // Fall back to returning whatever InetAddress.getLocalHost() returns...
        InetAddress jdkSuppliedAddress = InetAddress.getLocalHost();
        if (jdkSuppliedAddress == null) {
            throw new UnknownHostException("The JDK InetAddress.getLocalHost() method unexpectedly returned null.");
        }
        return jdkSuppliedAddress;
    }
    catch (Exception e) {
        UnknownHostException unknownHostException = new UnknownHostException("Failed to determine LAN address: " + e);
        unknownHostException.initCause(e);
        throw unknownHostException;
    }
}
Wadzim
źródło
6
Należy zauważyć, że nadal nie rozwiązuje to ambigity w przypadku, gdy host ma wiele podobnych interfejsów nerworkowych.
Vadzim
1
ponowna odpowiedź jest lepsza - stackoverflow.com/questions/9481865/... pobiera lokalny adres IP, który jest używany jako src dla domyślnego Gatway
Radu Toader
Dlaczego adres IP jest dodawany wraz z ukośnikiem ..? jak /10.39.0.17 ..? Czy zawsze tak należy przycinać ..?
Kanagavelu Sugumar,
51

W tym celu można użyć klasy InetAddress języka Java .

InetAddress IP=InetAddress.getLocalHost();
System.out.println("IP of my system is := "+IP.getHostAddress());

Dane wyjściowe dla mojego systemu = IP of my system is := 10.100.98.228

getHostAddress () powraca

Zwraca ciąg adresu IP w prezentacji tekstowej.

LUB możesz też zrobić

InetAddress IP=InetAddress.getLocalHost();
System.out.println(IP.toString());

Wyjście = IP of my system is := RanRag-PC/10.100.98.228

RanRag
źródło
9
Zauważ, że 10.xxx jest prywatnym adresem wskazującym, że twój system jest w sieci NAT. Pojawi się jako inny adres podczas kontaktu ze światem zewnętrznym. Jeśli naprawdę potrzebujesz zewnętrznego adresu IP, musisz skontaktować się z jedną z wielu witryn, która wyśle ​​ci echo adresu IP, z którego pochodzisz. To może, ale nie musi być przydatne. Twój system prawie na pewno nie będzie dostępny z zewnątrz.
Edward Falk,
19

Gdy szukasz adresu „lokalnego”, należy pamiętać, że każde urządzenie ma nie tylko jeden interfejs sieciowy, a każdy interfejs może mieć własny adres lokalny. Co oznacza, że ​​twój komputer zawsze posiada kilka „lokalnych” adresów.

Różne adresy „lokalne” zostaną automatycznie wybrane do użycia podczas łączenia się z różnymi punktami końcowymi. Na przykład, kiedy łączysz się google.com, używasz lokalnego adresu „zewnętrznego”; ale kiedy łączysz się z twoim localhost, twój lokalny adres jest zawsze localhostsam, ponieważ localhost jest tylko zapętleniem.

Poniżej pokazano, jak znaleźć adres lokalny podczas komunikacji z google.com:

Socket socket = new Socket();
socket.connect(new InetSocketAddress("google.com", 80));
System.out.println(socket.getLocalAddress());
macomgil
źródło
Niesamowite !! - takie proste :)
smilyface
4
dodaj na końcu socket.close () :)
MC
11

Przykład w scala (przydatny w pliku sbt):

  import collection.JavaConverters._
  import java.net._

  def getIpAddress: String = {

    val enumeration = NetworkInterface.getNetworkInterfaces.asScala.toSeq

    val ipAddresses = enumeration.flatMap(p =>
      p.getInetAddresses.asScala.toSeq
    )

    val address = ipAddresses.find { address =>
      val host = address.getHostAddress
      host.contains(".") && !address.isLoopbackAddress
    }.getOrElse(InetAddress.getLocalHost)

    address.getHostAddress
  }
Andrzej Jozwik
źródło
10

EDYCJA 1: Zaktualizowany kod, ponieważ poprzedni link już nie istnieje

import java.io.*;
import java.net.*;

public class GetMyIP {
    public static void main(String[] args) {
        URL url = null;
        BufferedReader in = null;
        String ipAddress = "";
        try {
            url = new URL("http://bot.whatismyipaddress.com");
            in = new BufferedReader(new InputStreamReader(url.openStream()));
            ipAddress = in.readLine().trim();
            /* IF not connected to internet, then
             * the above code will return one empty
             * String, we can check it's length and
             * if length is not greater than zero, 
             * then we can go for LAN IP or Local IP
             * or PRIVATE IP
             */
            if (!(ipAddress.length() > 0)) {
                try {
                    InetAddress ip = InetAddress.getLocalHost();
                    System.out.println((ip.getHostAddress()).trim());
                    ipAddress = (ip.getHostAddress()).trim();
                } catch(Exception exp) {
                    ipAddress = "ERROR";
                }
            }
        } catch (Exception ex) {
            // This try will give the Private IP of the Host.
            try {
                InetAddress ip = InetAddress.getLocalHost();
                System.out.println((ip.getHostAddress()).trim());
                ipAddress = (ip.getHostAddress()).trim();
            } catch(Exception exp) {
                ipAddress = "ERROR";
            }
            //ex.printStackTrace();
        }
        System.out.println("IP Address: " + ipAddress);
    }
}

AKTUALNA WERSJA: To przestało działać

Mamy nadzieję, że ten fragment pomoże ci to osiągnąć:

// Method to get the IP Address of the Host.
private String getIP()
{
    // This try will give the Public IP Address of the Host.
    try
    {
        URL url = new URL("http://automation.whatismyip.com/n09230945.asp");
        BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream()));
        String ipAddress = new String();
        ipAddress = (in.readLine()).trim();
        /* IF not connected to internet, then
         * the above code will return one empty
         * String, we can check it's length and
         * if length is not greater than zero, 
         * then we can go for LAN IP or Local IP
         * or PRIVATE IP
         */
        if (!(ipAddress.length() > 0))
        {
            try
            {
                InetAddress ip = InetAddress.getLocalHost();
                System.out.println((ip.getHostAddress()).trim());
                return ((ip.getHostAddress()).trim());
            }
            catch(Exception ex)
            {
                return "ERROR";
            }
        }
        System.out.println("IP Address is : " + ipAddress);

        return (ipAddress);
    }
    catch(Exception e)
    {
        // This try will give the Private IP of the Host.
        try
        {
            InetAddress ip = InetAddress.getLocalHost();
            System.out.println((ip.getHostAddress()).trim());
            return ((ip.getHostAddress()).trim());
        }
        catch(Exception ex)
        {
            return "ERROR";
        }
    }
}
NIcE COW
źródło
2
Rozwiązanie zadziałałoby, mam nadzieję, że jeśli zawsze będę mieć połączenie z Internetem, ale nie mam gwarancji, że to. Poza tym, gdy system nie jest podłączony do Internetu, a następnie muszę zwrócić adres IP LAN systemu, jeśli taki istnieje, w przeciwnym razie lokalny host. Więc nie jest to dla mnie możliwa opcja. Jakikolwiek inny sposób?
sasidhar
@sasidhar: Gdy jesteś podłączony do Internetu, tylko wtedy masz publiczny adres IP, chyba, że ​​nie jesteś podłączony, ta metoda da ci, twój lokalny adres IP lub adres IP sieci LAN i dla ostatniego warunku określonego przez ciebie możesz zwrócić „127.0.0.1”, zamiast zwracać Błąd.
NICe COW
1
Podoba mi się twoje podejście, ale ten link wydaje się już nie działać !! Czy mogę umieścić kontroler w swoim własnym systemie, aby działał zamiast tego zewnętrznego łącza, aby być bardziej niezawodnym?
azerafati
1
@Bludream: Dziękuję bardzo za poinformowanie mnie o tym, że link już nie działa. Zaktualizowałem post, wprowadzając nowe informacje. Mam nadzieję, że to zadziała dla twojej skrzynki użytkownika. Jeśli chodzi o twoje pytanie, naprawdę nie wiem, jak skonfigurować kontroler we własnym systemie, aby działał. Więc nie będę w stanie przedstawić wglądu w ten temat, MY BAD.
Jeszcze
1
Chociaż jest to fajne rozwiązanie, jest bardzo zawodne. Jeśli miałbyś zablokować główny wątek (powiedzmy) i z jakiegoś powodu whatismyip.combył wyłączony przez pewien czas, twoja aplikacja również byłaby wyłączona :(. Albo zwróci śmieciowe dane i spowoduje nieoczekiwane zachowanie. Zwraca to również outter większość adresów IP wykrywanych przez whatismyip.com, niekoniecznie adres IP maszyny, której używasz
Dekodowano
6

najpierw zaimportuj klasę

import java.net.InetAddress;

w klasie

  InetAddress iAddress = InetAddress.getLocalHost();
  String currentIp = iAddress.getHostAddress();
  System.out.println("Current IP address : " +currentIp); //gives only host address
Gautam
źródło
2
daje tylko pierwszy adres IP, nawet jeśli nie jest używany!
Yahya
6

Możesz użyć java.net.InetAddressAPI. Spróbuj tego :

InetAddress.getLocalHost().getHostAddress();
Ved
źródło
5
po prostu zwróci 127.0.0.1
HCarrasko
5
private static InetAddress getLocalAddress(){
        try {
            Enumeration<NetworkInterface> b = NetworkInterface.getNetworkInterfaces();
            while( b.hasMoreElements()){
                for ( InterfaceAddress f : b.nextElement().getInterfaceAddresses())
                    if ( f.getAddress().isSiteLocalAddress())
                        return f.getAddress();
            }
        } catch (SocketException e) {
            e.printStackTrace();
        }
        return null;
    }
JR
źródło
1
rozważ dodanie wyjaśnienia na temat tego, co robi Twój kod.
HCarrasko
4

To jest działający przykład AKCEPTOWANEJ odpowiedzi powyżej! Ta klasa NetIdentity będzie przechowywać zarówno wewnętrzny adres IP hosta, jak i lokalną pętlę zwrotną. Jeśli korzystasz z serwera opartego na systemie DNS, jak wspomniano powyżej, konieczne może być dodanie dodatkowych kontroli lub przejście do pliku konfiguracji trasy.

import java.net.InetAddress;
import java.net.NetworkInterface;
import java.net.SocketException;
import java.net.UnknownHostException;
import java.util.Enumeration;

/**
 * Class that allows a device to identify itself on the INTRANET.
 * 
 * @author Decoded4620 2016
 */
public class NetIdentity {

    private String loopbackHost = "";
    private String host = "";

    private String loopbackIp = "";
    private String ip = "";
    public NetIdentity(){

        try{
            Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces();

            while(interfaces.hasMoreElements()){
                NetworkInterface i = interfaces.nextElement();
                if(i != null){
                    Enumeration<InetAddress> addresses = i.getInetAddresses();
                    System.out.println(i.getDisplayName());
                    while(addresses.hasMoreElements()){
                        InetAddress address = addresses.nextElement();
                        String hostAddr = address.getHostAddress();

                        // local loopback
                        if(hostAddr.indexOf("127.") == 0 ){
                            this.loopbackIp = address.getHostAddress();
                            this.loopbackHost = address.getHostName();
                        }

                        // internal ip addresses (behind this router)
                        if( hostAddr.indexOf("192.168") == 0 || 
                                hostAddr.indexOf("10.") == 0 || 
                                hostAddr.indexOf("172.16") == 0 ){
                            this.host = address.getHostName();
                            this.ip = address.getHostAddress();
                        }


                        System.out.println("\t\t-" + address.getHostName() + ":" + address.getHostAddress() + " - "+ address.getAddress());
                    }
                }
            }
        }
        catch(SocketException e){

        }
        try{
            InetAddress loopbackIpAddress = InetAddress.getLocalHost();
            this.loopbackIp = loopbackIpAddress.getHostName();
            System.out.println("LOCALHOST: " + loopbackIp);
        }
        catch(UnknownHostException e){
            System.err.println("ERR: " + e.toString());
        }
    }

    public String getLoopbackHost(){
        return loopbackHost;
    }

    public String getHost(){
        return host;
    }
    public String getIp(){
        return ip;
    }
    public String getLoopbackIp(){
        return loopbackIp;
    }
}

Kiedy uruchamiam ten kod, faktycznie otrzymuję taki wydruk:

    Software Loopback Interface 1
        -127.0.0.1:127.0.0.1 - [B@19e1023e
        -0:0:0:0:0:0:0:1:0:0:0:0:0:0:0:1 - [B@7cef4e59
Broadcom 802.11ac Network Adapter
        -VIKING.yourisp.com:192.168.1.142 - [B@64b8f8f4
        -fe80:0:0:0:81fa:31d:21c9:85cd%wlan0:fe80:0:0:0:81fa:31d:21c9:85cd%wlan0 - [B@2db0f6b2
Microsoft Kernel Debug Network Adapter
Intel Edison USB RNDIS Device
Driver for user-mode network applications
Cisco Systems VPN Adapter for 64-bit Windows
VirtualBox Host-Only Ethernet Adapter
        -VIKING:192.168.56.1 - [B@3cd1f1c8
        -VIKING:fe80:0:0:0:d599:3cf0:5462:cb7%eth4 - [B@3a4afd8d
LogMeIn Hamachi Virtual Ethernet Adapter
        -VIKING:25.113.118.39 - [B@1996cd68
        -VIKING:2620:9b:0:0:0:0:1971:7627 - [B@3339ad8e
        -VIKING:fe80:0:0:0:51bf:994d:4656:8486%eth5 - [B@555590
Bluetooth Device (Personal Area Network)
        -fe80:0:0:0:4c56:8009:2bca:e16b%eth6:fe80:0:0:0:4c56:8009:2bca:e16b%eth6 - [B@3c679bde
Bluetooth Device (RFCOMM Protocol TDI)
Intel(R) Ethernet Connection (2) I218-V
        -fe80:0:0:0:4093:d169:536c:7c7c%eth7:fe80:0:0:0:4093:d169:536c:7c7c%eth7 - [B@16b4a017
Microsoft Wi-Fi Direct Virtual Adapter
        -fe80:0:0:0:103e:cdf0:c0ac:1751%wlan1:fe80:0:0:0:103e:cdf0:c0ac:1751%wlan1 - [B@8807e25
VirtualBox Host-Only Ethernet Adapter-HHD Software NDIS 6.0 Filter Driver-0000
VirtualBox Host-Only Ethernet Adapter-WFP Native MAC Layer LightWeight Filter-0000
VirtualBox Host-Only Ethernet Adapter-HHD Software NDIS 6.0 Filter Driver-0001
VirtualBox Host-Only Ethernet Adapter-HHD Software NDIS 6.0 Filter Driver-0002
VirtualBox Host-Only Ethernet Adapter-VirtualBox NDIS Light-Weight Filter-0000
VirtualBox Host-Only Ethernet Adapter-HHD Software NDIS 6.0 Filter Driver-0003
VirtualBox Host-Only Ethernet Adapter-QoS Packet Scheduler-0000
VirtualBox Host-Only Ethernet Adapter-HHD Software NDIS 6.0 Filter Driver-0004
VirtualBox Host-Only Ethernet Adapter-WFP 802.3 MAC Layer LightWeight Filter-0000
VirtualBox Host-Only Ethernet Adapter-HHD Software NDIS 6.0 Filter Driver-0005
Intel(R) Ethernet Connection (2) I218-V-HHD Software NDIS 6.0 Filter Driver-0000
Intel(R) Ethernet Connection (2) I218-V-WFP Native MAC Layer LightWeight Filter-0000
Intel(R) Ethernet Connection (2) I218-V-HHD Software NDIS 6.0 Filter Driver-0001
Intel(R) Ethernet Connection (2) I218-V-Shrew Soft Lightweight Filter-0000
Intel(R) Ethernet Connection (2) I218-V-HHD Software NDIS 6.0 Filter Driver-0002
Intel(R) Ethernet Connection (2) I218-V-VirtualBox NDIS Light-Weight Filter-0000
Intel(R) Ethernet Connection (2) I218-V-HHD Software NDIS 6.0 Filter Driver-0003
Intel(R) Ethernet Connection (2) I218-V-QoS Packet Scheduler-0000
Intel(R) Ethernet Connection (2) I218-V-HHD Software NDIS 6.0 Filter Driver-0004
Intel(R) Ethernet Connection (2) I218-V-WFP 802.3 MAC Layer LightWeight Filter-0000
Intel(R) Ethernet Connection (2) I218-V-HHD Software NDIS 6.0 Filter Driver-0005
Broadcom 802.11ac Network Adapter-WFP Native MAC Layer LightWeight Filter-0000
Broadcom 802.11ac Network Adapter-Virtual WiFi Filter Driver-0000
Broadcom 802.11ac Network Adapter-Native WiFi Filter Driver-0000
Broadcom 802.11ac Network Adapter-HHD Software NDIS 6.0 Filter Driver-0003
Broadcom 802.11ac Network Adapter-Shrew Soft Lightweight Filter-0000
Broadcom 802.11ac Network Adapter-HHD Software NDIS 6.0 Filter Driver-0004
Broadcom 802.11ac Network Adapter-VirtualBox NDIS Light-Weight Filter-0000
Broadcom 802.11ac Network Adapter-HHD Software NDIS 6.0 Filter Driver-0005
Broadcom 802.11ac Network Adapter-QoS Packet Scheduler-0000
Broadcom 802.11ac Network Adapter-HHD Software NDIS 6.0 Filter Driver-0006
Broadcom 802.11ac Network Adapter-WFP 802.3 MAC Layer LightWeight Filter-0000
Broadcom 802.11ac Network Adapter-HHD Software NDIS 6.0 Filter Driver-0007
Microsoft Wi-Fi Direct Virtual Adapter-WFP Native MAC Layer LightWeight Filter-0000
Microsoft Wi-Fi Direct Virtual Adapter-Native WiFi Filter Driver-0000
Microsoft Wi-Fi Direct Virtual Adapter-HHD Software NDIS 6.0 Filter Driver-0002
Microsoft Wi-Fi Direct Virtual Adapter-Shrew Soft Lightweight Filter-0000
Microsoft Wi-Fi Direct Virtual Adapter-HHD Software NDIS 6.0 Filter Driver-0003
Microsoft Wi-Fi Direct Virtual Adapter-VirtualBox NDIS Light-Weight Filter-0000
Microsoft Wi-Fi Direct Virtual Adapter-HHD Software NDIS 6.0 Filter Driver-0004
Microsoft Wi-Fi Direct Virtual Adapter-QoS Packet Scheduler-0000
Microsoft Wi-Fi Direct Virtual Adapter-HHD Software NDIS 6.0 Filter Driver-0005
Microsoft Wi-Fi Direct Virtual Adapter-WFP 802.3 MAC Layer LightWeight Filter-0000
Microsoft Wi-Fi Direct Virtual Adapter-HHD Software NDIS 6.0 Filter Driver-0006

Na mój użytek konfiguruję serwer Upnp, co pomogło zrozumieć „wzorzec”, którego szukałem. Niektóre zwracane obiekty to Adaptery Ethernet, Adaptery sieciowe, Adaptery Sieci Wirtualnej, Sterowniki i Adaptery Klienta VPN. Nie wszystko też ma adres. Więc będziesz chciał pominąć obiekty interfejsu, które tego nie robią.

Możesz również dodać to do pętli dla prądu NetworkInterface i

while(interfaces.hasMoreElements()){
    Enumeration<InetAddress> addresses = i.getInetAddresses();
    System.out.println(i.getDisplayName());
    System.out.println("\t- name:" + i.getName());
    System.out.println("\t- idx:" + i.getIndex());
    System.out.println("\t- max trans unit (MTU):" + i.getMTU());
    System.out.println("\t- is loopback:" + i.isLoopback());
    System.out.println("\t- is PPP:" + i.isPointToPoint());
    System.out.println("\t- isUp:" + i.isUp());
    System.out.println("\t- isVirtual:" + i.isVirtual());
    System.out.println("\t- supportsMulticast:" + i.supportsMulticast());
}

W wynikach zobaczysz informacje podobne do następujących:

Software Loopback Interface 1
    - name:lo
    - idx:1
    - max trans unit (MTU):-1
    - is loopback:true
    - is PPP:false
    - isUp:true
    - isVirtual:false
    - supportsMulticast:true
        -ADRESS: [127.0.0.1(VIKING-192.168.56.1)]127.0.0.1:127.0.0.1 - [B@19e1023e
        -ADRESS: [0:0:0:0:0:0:0:1(VIKING-192.168.56.1)]0:0:0:0:0:0:0:1:0:0:0:0:0:0:0:1 - [B@7cef4e59
Broadcom 802.11ac Network Adapter
    - name:wlan0
    - idx:2
    - max trans unit (MTU):1500
    - is loopback:false
    - is PPP:false
    - isUp:true
    - isVirtual:false
    - supportsMulticast:true
        -ADRESS: [VIKING.monkeybrains.net(VIKING-192.168.56.1)]VIKING.monkeybrains.net:192.168.1.142 - [B@64b8f8f4
        -ADRESS: [fe80:0:0:0:81fa:31d:21c9:85cd%wlan0(VIKING-192.168.56.1)]fe80:0:0:0:81fa:31d:21c9:85cd%wlan0:fe80:0:0:0:81fa:31d:21c9:85cd%wlan0 - [B@2db0f6b2
Microsoft Kernel Debug Network Adapter
    - name:eth0
    - idx:3
    - max trans unit (MTU):-1
    - is loopback:false
    - is PPP:false
    - isUp:false
    - isVirtual:false
    - supportsMulticast:true
Dekodowane
źródło
3

Użyj InetAddress.getLocalHost (), aby uzyskać adres lokalny

import java.net.InetAddress;

try {
  InetAddress addr = InetAddress.getLocalHost();            
  System.out.println(addr.getHostAddress());
} catch (UnknownHostException e) {
}
vdeantoni
źródło
Mój adres IP połączenia PPP to: 117.204.44.192 Ale powyższe zwraca mi 192.168.1.2
sasidhar
Musisz zaindeksować wszystkie dostępne instancje InetAddress i dowiedzieć się, która jest właściwa.
Odszyfrowano
1
import java.net.InetAddress;
import java.net.NetworkInterface;
import java.util.Enumeration;

public class IpAddress {

NetworkInterface ifcfg;
Enumeration<InetAddress> addresses;
String address;

public String getIpAddress(String host) {
    try {
        ifcfg = NetworkInterface.getByName(host);
        addresses = ifcfg.getInetAddresses();
        while (addresses.hasMoreElements()) {
            address = addresses.nextElement().toString();
            address = address.replace("/", "");
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
    return ifcfg.toString();
}
}
twatson0990
źródło
1

Raczej uproszczone podejście, które wydaje się działać ...

String getPublicIPv4() throws UnknownHostException, SocketException{
    Enumeration<NetworkInterface> e = NetworkInterface.getNetworkInterfaces();
    String ipToReturn = null;
    while(e.hasMoreElements())
    {
        NetworkInterface n = (NetworkInterface) e.nextElement();
        Enumeration<InetAddress> ee = n.getInetAddresses();
        while (ee.hasMoreElements())
        {
            InetAddress i = (InetAddress) ee.nextElement();
            String currentAddress = i.getHostAddress();
            logger.trace("IP address "+currentAddress+ " found");
            if(!i.isSiteLocalAddress()&&!i.isLoopbackAddress() && validate(currentAddress)){
                ipToReturn = currentAddress;    
            }else{
                System.out.println("Address not validated as public IPv4");
            }

        }
    }

    return ipToReturn;
}

private static final Pattern IPv4RegexPattern = Pattern.compile(
        "^(([01]?\\d\\d?|2[0-4]\\d|25[0-5])\\.){3}([01]?\\d\\d?|2[0-4]\\d|25[0-5])$");

public static boolean validate(final String ip) {
    return IPv4RegexPattern.matcher(ip).matches();
}
Pantelis Natsiavas
źródło
1

Otrzyma adres IP twojej sieci, jeśli twoje urządzenie jest częścią sieci

try {
    System.out.println(InetAddress.getLocalHost().getHostAddress());
} catch (UnknownHostException e) {
    e.printStackTrace();
}
kod 511788465541441
źródło
0

Zwykle, gdy próbuję znaleźć mój publiczny adres IP, taki jak cmyip.com lub www.iplocation.net , używam tego sposobu:

public static String myPublicIp() {

    /*nslookup myip.opendns.com resolver1.opendns.com*/
    String ipAdressDns  = "";
    try {
        String command = "nslookup myip.opendns.com resolver1.opendns.com";
        Process proc = Runtime.getRuntime().exec(command);

        BufferedReader stdInput = new BufferedReader(new InputStreamReader(proc.getInputStream()));

        String s;
        while ((s = stdInput.readLine()) != null) {
            ipAdressDns  += s + "\n";
        }
    } catch (IOException e) {
        e.printStackTrace();
    }

    return ipAdressDns ;
}
YCF_L
źródło
0

Ponieważ mój system (podobnie jak wiele innych systemów) miał różne interfejsy sieciowe. InetAddress.getLocalHost()lub Inet4Address.getLocalHost()po prostu zwrócił taki, którego nie chciałem. Dlatego musiałem zastosować to naiwne podejście.

InetAddress[] allAddresses = Inet4Address.getAllByName("YourComputerHostName");
        InetAddress desiredAddress;
        //In order to find the desired Ip to be routed by other modules (WiFi adapter)
        for (InetAddress address :
                allAddresses) {
            if (address.getHostAddress().startsWith("192.168.2")) {
                desiredAddress = address;
            }
        }
// Use the desired address for whatever purpose.

Uważaj tylko, aby w tym podejściu wiedziałem już, że mój pożądany adres IP znajduje się w 192.168.2podsieci.

SepJaPro2.4
źródło
-1
public static String getIpAddress() {

    String ipAddress = null;

    try {
        Enumeration<NetworkInterface> networkInterfaces = NetworkInterface.getNetworkInterfaces();

        while (networkInterfaces.hasMoreElements()) {

            NetworkInterface networkInterface = networkInterfaces.nextElement();

            byte[] hardwareAddress = networkInterface.getHardwareAddress();
            if (null == hardwareAddress || 0 == hardwareAddress.length || (0 == hardwareAddress[0] && 0 == hardwareAddress[1] && 0 == hardwareAddress[2])) continue;

            Enumeration<InetAddress> inetAddresses = networkInterface.getInetAddresses();

            if (inetAddresses.hasMoreElements()) ipAddress = inetAddresses.nextElement().toString();

            break;
        }
    } catch (SocketException e) {
        e.printStackTrace();
    }

    return ipAddress;
}
Maxple
źródło
dodaj wyjaśnienie dotyczące działania kodu.
HCarrasko