在Debian jessie下使用Python的stdlib查找本地IP地址

我正在编写一个分布式系统程序在Python中,在这个程序中,我需要知道本地IP地址…例如。 168.192 …. 10.13 ….. etc,不是127.0.0.1或主机名。

我已经find了以下解决scheme在计算器上

https://stackoverflow.com/questions/166506/finding-local-ip-addresses-using-pythons-stdlib

import socket socket.gethostbyname(socket.gethostname()) 

当我在Debian的jessie笔记本电脑上运行这个程序时,我得到了127.0.0.1, 然而 ,当他运行相同的脚本(例如168.192 ..)时,我的朋友在他的机器上使用Fedora获得了所需的IP地址。

如果可能的话,我更喜欢使用上面的解决scheme来获得本地IP地址,因为大多数其他build议的解决scheme要么是黑客或令人难以置信的长期…

有什么我可以安装在我的Debian的jessie笔记本电脑,使Python将返回正确的本地IP地址?

  • 使用debian jessie
  • python3
  • 连接到networking(..和电脑打开)…;)
  • / etc / hosts目前包含:

127.0.0.1 localhost 127.0.0.1 debianASUS ::1 localhost ip6-localhost ip6-loopback ff02::1 ip6-allnodes ff02::2 ip6-allrouters

你有没有考虑通过configuration参数推迟在最终用户在运行时的决定? 这是这个问题的标准做法。

原因是没有系统的万无一失的方式来确定本地IP地址(一个主机可能是多宿主的,可能是运行一个v4 / v6双栈,一个VPN等)。 运行时configuration将使系统pipe理员的工作更轻松!

查找主机用于通信的IP地址的最可靠的方法是在连接的UDP套接字上使用getsockname 。 在UDP情况下, connect系统调用不涉及任何networking通信。

以下是我为了类似目的而写的过去的Python函数。 如果您事先不知道您将与哪个远程IP地址通信,则应该查找将使用默认路由的一个IP地址。 如果您已经知道您将与哪个远程IP地址进行通信,则最好在连接呼叫中使用该IP地址。

 def my_ip(): s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) try: s.connect(('192.0.0.8', 1027)) except socket.error: return None return s.getsockname()[0] 

只需稍作更改,就可以使用此function来返回IPv6地址而不是IPv4:

 def my_ipv6(): s = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM) try: s.connect(('2001:db8::', 1027)) except socket.error: return None return s.getsockname()[0]