Wie kann ich lokale IP-Adressen (dh 192.168.xx oder 10.0.xx) in der Python-Plattform unabhängig und nur unter Verwendung der Standardbibliothek finden?
python
networking
ip-address
UnkwnTech
quelle
quelle
ifconfig -a
und benutze die Ausgabe von dort ...ip addr
ist weitaus besser geeignet (und einfacher zu analysieren, zu booten).bind
einen Socket zu einer bestimmten Schnittstelle benötigt wird, ist dies eine Richtlinienangelegenheit. Wenn die lokale IP-Adresse benötigt wird, um sie an einen Peer zu übergeben, damit der Peer "zurückrufen" kann, dh um eine Verbindung zum lokalen Computer wiederherzustellen, hängt die Situation davon ab, ob NAT (Network Address Translation) vorhanden ist. Kisten dazwischen. Wenn es keine NATs gibt,getsockname
ist dies eine gute Wahl.Antworten:
Dies funktioniert nicht immer (kehrt
127.0.0.1
auf Computern mit dem Hostnamen/etc/hosts
as zurück127.0.0.1
). Ein Paliative wäre das, was Gimel zeigt. Verwenden Siesocket.getfqdn()
stattdessen. Natürlich benötigt Ihr Computer einen auflösbaren Hostnamen.quelle
socket.gethostbyname_ex(socket.gethostname())[-1]
Ich habe das gerade gefunden, aber es scheint ein bisschen hackisch zu sein, aber sie sagen, ich habe es auf * nix versucht und ich habe es unter Windows gemacht und es hat funktioniert.
Dies setzt voraus, dass Sie über einen Internetzugang verfügen und kein lokaler Proxy vorhanden ist.
quelle
Diese Methode gibt die "primäre" IP auf der lokalen Box zurück (die mit einer Standardroute) .
Python 3 oder 2:
Dies gibt eine einzelne IP zurück, die die primäre ist (die mit einer Standardroute). Wenn Sie stattdessen alle IP-Adressen benötigen, die an alle Schnittstellen (einschließlich localhost usw.) angeschlossen sind, lesen Sie diese Antwort .
Wenn Sie sich zu Hause hinter einer NAT-Firewall wie Ihrer WLAN-Box befinden, wird hier nicht Ihre öffentliche NAT-IP angezeigt, sondern Ihre private IP-Adresse im lokalen Netzwerk, das eine Standardroute zu Ihrem lokalen WLAN-Router hat. Um die externe IP-Adresse Ihres WLAN-Routers zu erhalten, müssen Sie diese entweder auf DIESER Box ausführen oder eine Verbindung zu einem externen Dienst wie whatismyip.com/whatismyipaddress.com herstellen, der die IP-Adresse wiedergeben könnte. Dies unterscheidet sich jedoch grundlegend von der ursprünglichen Frage. :) :)
quelle
socket.gethostbyname(socket.gethostname())
gibt schreckliche Ergebnisse.Wie ein Alias heißt
myip
, sollte das überall funktionieren:Wie oben, aber nur der Python-Code:
Version, die auch in LANs ohne Internetverbindung funktioniert:
(danke @ccpizza )
Hintergrund :
Die Verwendung
socket.gethostbyname(socket.gethostname())
hat hier nicht funktioniert, da einer der Computer, auf denen ich war, einen/etc/hosts
mit doppelten Einträgen und Verweisen auf sich selbst hatte.socket.gethostbyname()
Gibt nur den letzten Eintrag in zurück/etc/hosts
.Dies war mein erster Versuch, bei dem alle Adressen ausgesondert wurden, beginnend mit
"127."
:Dies funktioniert mit Python 2 und 3 unter Linux und Windows, jedoch nicht mit mehreren Netzwerkgeräten oder IPv6. Es funktionierte jedoch nicht mehr mit den neuesten Linux-Distributionen, daher habe ich stattdessen diese alternative Technik ausprobiert. Es wird versucht, eine Verbindung zum Google DNS-Server
8.8.8.8
an folgendem Port herzustellen53
:Dann kombinierte ich die beiden oben genannten Techniken zu einem Einzeiler, der überall funktionieren sollte, und erstellte den
myip
Alias und das Python-Snippet oben in dieser Antwort.Mit der zunehmenden Beliebtheit von IPv6 und für Server mit mehreren Netzwerkschnittstellen ist die Verwendung eines Python-Moduls eines Drittanbieters zum Ermitteln der IP-Adresse wahrscheinlich sowohl robuster als auch zuverlässiger als jede der hier aufgeführten Methoden.
quelle
socket.getaddrinfo()
sollte plattformübergreifend konsistent funktionieren - aber ich habe es nur unter Linux überprüft, mich nicht um andere Betriebssysteme gekümmert./etc/resolve.conf: No such file or directory
und ich habe lokale IPv4-Adresse von angezeigtifconfig
.Sie können das Netifaces- Modul verwenden. Tippe einfach:
in Ihrer Befehlsshell und es wird sich bei der Standard-Python-Installation selbst installieren.
Dann können Sie es so verwenden:
Auf meinem Computer wurde gedruckt:
Der Autor dieses Moduls behauptet, es sollte unter Windows, UNIX und Mac OS X funktionieren.
quelle
Socket-API-Methode
Siehe https://stackoverflow.com/a/28950776/711085
Nachteile:
Reflektormethode
(Beachten Sie, dass dies nicht die Frage des OP nach der lokalen IP-Adresse beantwortet, z. B. 192.168 ...; Sie erhalten Ihre öffentliche IP-Adresse, die je nach Anwendungsfall möglicherweise wünschenswerter ist.)
Sie können eine Site wie whatismyip.com (jedoch mit einer API) abfragen, z.
oder wenn Sie python2 verwenden:
Vorteile:
Nachteile (und Problemumgehungen):
bearbeiten : Obwohl ich anfangs dachte, dass diese Methoden wirklich schlecht sind (wenn Sie nicht viele Fallbacks verwenden, kann der Code in vielen Jahren irrelevant sein), stellt sich die Frage "Was ist das Internet?". Ein Computer kann viele Schnittstellen haben, die auf viele verschiedene Netzwerke verweisen. Für eine ausführlichere Beschreibung des Themas gehen Sie auf Google für
gateways and routes
. Ein Computer kann möglicherweise über ein internes Gateway auf ein internes Netzwerk zugreifen oder über ein Gateway auf beispielsweise einem Router (normalerweise der Fall) auf das World Wide Web zugreifen. Die lokale IP-Adresse, nach der das OP fragt, ist nur in Bezug auf eine einzelne Verbindungsschicht genau definiert. Sie müssen dies also angeben ("Handelt es sich um die Netzwerkkarte oder das Ethernet-Kabel?"). . Es kann mehrere nicht eindeutige Antworten auf diese Frage geben. Die globale IP-Adresse im World Wide Web ist jedoch wahrscheinlich genau definiert (ohne massive Netzwerkfragmentierung): wahrscheinlich der Rückweg über das Gateway, das auf die TLDs zugreifen kann.quelle
Wenn der Computer eine Route zum Internet hat, funktioniert dies immer , um die bevorzugte lokale IP-Adresse zu erhalten, auch wenn / etc / hosts nicht richtig eingestellt ist.
quelle
8.8.8.8
Ist ein Google - DNS - Server können wir es mit einem lokalen DNS - Server zu tun?Unter Linux:
quelle
ioctl
) kommunizieren kann . Der Socket ist nicht an die Schnittstelle gebunden, für die Sie Adr-Informationen benötigen - es handelt sich lediglich um einen Kommunikationsmechanismus zwischen dem Benutzerbereich und dem Kernel. en.wikipedia.org/wiki/Ioctl lxr.free-electrons.com/source/net/socket.cstruct.pack('16sH14s', iface, socket.AF_INET, '\x00'*14)
sollte durchstruct.pack('16sH14s', iface.encode('utf-8'), socket.AF_INET, b'\x00'*14)
ioctl
ist eine Legacy-Schnittstelle, von der ich nicht glaube, dass sie IPv6 unterstützt und wahrscheinlich niemals unterstützt. Ich denke, der "richtige" Weg führt über Netlink, was in Python nicht sehr einfach ist. Ich denke, libc sollte die Funktion haben, aufgetifaddrs
die überctypes
das Python-Ich benutze folgendes Modul:
Getestet mit Windows und Linux (und erfordert keine zusätzlichen Module für diese), die für die Verwendung auf Systemen vorgesehen sind, die sich in einem einzelnen IPv4-basierten LAN befinden.
Die feste Liste der Schnittstellennamen funktioniert nicht für neuere Linux-Versionen, die die von Alexander erwähnte Änderung systemd v197 in Bezug auf vorhersagbare Schnittstellennamen übernommen haben . In solchen Fällen müssen Sie die Liste manuell durch die Schnittstellennamen auf Ihrem System ersetzen oder eine andere Lösung wie Netifaces verwenden .
quelle
enp0s25
. Weitere Informationen finden Sie unter wiki.archlinux.org/index.php/Network_Configuration#Device_namesstruct.pack('256s', bytes(ifname[:15]))
Ich benutze dies auf meinen Ubuntu-Maschinen:
Das funktioniert nicht.
quelle
Wenn Sie keine externen Pakete verwenden und sich nicht auf externe Internet-Server verlassen möchten, kann dies hilfreich sein. Es ist ein Codebeispiel, das ich in der Google-Codesuche gefunden und geändert habe, um die erforderlichen Informationen zurückzugeben:
Verwendungszweck:
Da es auf beruht
windll
, wird dies nur unter Windows arbeiten.quelle
Auf Debian (getestet) und ich vermute die meisten Linux ..
Unter MS Windows (getestet)
quelle
hostname: illegal option -- I\nusage: hostname [-fs] [name-of-host]
Eine Version, von der ich nicht glaube, dass sie noch veröffentlicht wurde. Ich habe mit Python 2.7 unter Ubuntu 12.04 getestet.
Diese Lösung finden Sie unter: http://code.activestate.com/recipes/439094-get-the-ip-address-associated-with-a-network-inter/
Beispiel Ergebnis:
quelle
Variation der Antwort von Ninjagecko. Dies sollte in jedem LAN funktionieren, das UDP-Broadcast ermöglicht und keinen Zugriff auf eine Adresse im LAN oder Internet erfordert.
quelle
<broadcast>
ein gültiger Hostname? !! Wie viele dieser verbalen Hostnamen sind gültig?Ich fürchte, es gibt keine guten plattformunabhängigen Möglichkeiten, dies zu tun, außer eine Verbindung zu einem anderen Computer herzustellen und Ihnen Ihre IP-Adresse zu senden. Zum Beispiel: findmyipaddress . Beachten Sie, dass dies nicht funktioniert, wenn Sie eine IP-Adresse benötigen, die sich hinter NAT befindet, es sei denn, der Computer, mit dem Sie eine Verbindung herstellen, befindet sich ebenfalls hinter NAT.
Hier ist eine Lösung, die unter Linux funktioniert: Rufen Sie die IP-Adresse ab, die einer Netzwerkschnittstelle zugeordnet ist .
quelle
Eine einfache Möglichkeit, eine "saubere" Ausgabe über Befehlszeilenprogramme zu erstellen:
Es werden alle IPv4-Adressen auf dem System angezeigt.
quelle
Zu Ihrer Information Ich kann überprüfen, ob die Methode:
Funktioniert unter OS X (10.6.10.5), Windows XP und auf einem gut verwalteten RHEL-Abteilungsserver. Es funktionierte nicht auf einer sehr minimalen CentOS-VM, auf der ich nur Kernel-Hacking mache. In diesem Fall können Sie einfach nach einer 127.0.0.1-Adresse suchen und in diesem Fall Folgendes tun:
Und dann analysieren Sie die IP-Adresse von der Ausgabe. Es sollte beachtet werden, dass ifconfig standardmäßig nicht im PATH eines normalen Benutzers enthalten ist, und deshalb gebe ich den vollständigen Pfad im Befehl an. Ich hoffe das hilft.
quelle
Dies ist eine Variante der Antwort von UnkwnTech - sie bietet eine
get_local_addr()
Funktion, die die primäre LAN-IP-Adresse des Hosts zurückgibt. Ich poste es, weil dies eine Reihe von Dingen hinzufügt: IPv6-Unterstützung, Fehlerbehandlung, Ignorieren von localhost / linklocal-Adressen und Verwenden einer TESTNET-Adresse (rfc5737) zum Herstellen einer Verbindung.quelle
None
get_local_addr(remove="www.google.com")
Rückkehr? Das Protokollieren dessocket.error
von _get_local_addr () ausgelösten Protokolls kann bei der Diagnose hilfreich sein.quelle
['fe80::34e8:fe19:1459:2cde%22','fe80::d528:99fb:d572:e289%12', '192.168.56.1', '192.168.1.2']
auf Windows-Desktop.Dies funktioniert auf den meisten Linux-Boxen:
quelle
Diese Antwort ist mein persönlicher Versuch, das Problem des Abrufs der LAN-IP zu lösen, da
socket.gethostbyname(socket.gethostname())
auch 127.0.0.1 zurückgegeben wurde. Diese Methode erfordert nicht nur eine LAN-Verbindung zum Internet. Code ist für Python 3.x, kann aber leicht für 2.x konvertiert werden. Verwenden von UDP Broadcast:quelle
127.0.1.1
ist Ihre echte IP-Adresse. Allgemeiner kann ein Computer eine beliebige Anzahl von IP-Adressen haben. Sie können sie nach privaten Netzwerken filtern - 127.0.0.0/8, 10.0.0.0/8, 172.16.0.0/12 und 192.168.0.0/16.Es gibt jedoch keine plattformübergreifende Möglichkeit, alle IP-Adressen abzurufen. Unter Linux können Sie das
SIOCGIFCONF
ioctl verwenden.quelle
Eine geringfügige Verfeinerung der Befehlsversion, die den IP-Befehl verwendet und IPv4- und IPv6-Adressen zurückgibt:
quelle
Nun, Sie können den Befehl "ip route" unter GNU / Linux verwenden, um Ihre aktuelle IP-Adresse zu ermitteln.
Hier wird die IP angezeigt, die der DHCP-Server, der auf dem Router / Modem ausgeführt wird, an die Schnittstelle gesendet hat. Normalerweise ist "192.168.1.1/24" die IP für das lokale Netzwerk, wobei "24" den Bereich möglicher IP-Adressen bedeutet, die vom DHCP-Server innerhalb des Maskenbereichs angegeben werden.
Hier ein Beispiel: Beachten Sie, dass PyNotify nur eine Ergänzung ist, um meinen Standpunkt klar zu machen, und überhaupt nicht erforderlich ist
Dies hat den Vorteil, dass Sie die Netzwerkschnittstelle nicht angeben müssen. Das ist ziemlich nützlich, wenn Sie einen Socket-Server ausführen
Sie können PyNotify mit easy_install oder sogar Pip installieren:
oder
oder innerhalb von Python Script / Interpreter
quelle
Wenn Sie nach einer IPV4-Adresse suchen, die sich von Ihrer lokalen Host-IP-Adresse unterscheidet
127.0.0.1
, finden Sie hier einen ordentlichen Python-Code:Was auch in einer einzigen Zeile geschrieben werden kann:
Auch wenn Sie setzen
localhost
in/etc/hostname
Ihrer lokale IP - Adresse, wird der Code immer noch geben.quelle
Für Linux können Sie einfach
check_output
denhostname -I
Systembefehl wie folgt verwenden:quelle
Hinweis: Dies verwendet nicht die Standardbibliothek, ist aber recht einfach.
$ pip install pif
quelle
netifaces ist über pip und easy_install verfügbar. (Ich weiß, es ist nicht in der Basis, aber es könnte die Installation wert sein.)
netifaces hat plattformübergreifende Besonderheiten:
Hier ist ein Netifaces-Code zum Spielen:
Der obige Code ordnet eine Adresse nicht ihrem Schnittstellennamen zu (nützlich zum schnellen Generieren von ebtables / iptables-Regeln). Hier ist eine Version, die die obigen Informationen mit dem Schnittstellennamen in einem Tupel enthält:
Und nein, ich bin nicht verliebt in Listenverständnisse. So funktioniert mein Gehirn heutzutage.
Das folgende Snippet druckt alles aus:
Genießen!
quelle
Eine Python 3.4-Version, die das neu eingeführte Asyncio-Paket verwendet.
Dies basiert auf der hervorragenden Antwort von UnkwnTech .
quelle
Um die IP-Adresse zu erhalten, können Sie einen Shell-Befehl direkt in Python verwenden :
quelle