我正在构建chrome app并通过chrome socket api创建 UDP套接字。
有没有办法在不使用外部服务的情况下检索自己的 IP地址? 我所说的“自己的IP地址”:客户端和服务器都在同一个网络上。 Chrome应用需要使用自己的本地IP地址来回复 UDP广播。
实际上只有chrome socket API用于该用例。但遗憾的是,我只收到以下回调对象:Object {paused: false, persistent: false, socketId: 17}
,它错过了localAddress
属性。根据{{3}},它是SocketInfo
对象中的(可选)属性。这本质上就是我正在运行的代码:
chrome.sockets.udp.create({}, function(socketInfo){
chrome.sockets.udp.getInfo(socketInfo.socketId, function (detailedInfo){
ipAddress = detailedInfo.localAddress;
console.debug(detailedInfo); // containts no `localAddress`
});
});
由于documentation中没有特殊权限,我也不认为我遗漏了任何manifest-permissions。这就是我使用的:
"sockets": {
"udp": {
"send": "*",
"bind": "*"
}
}
当我使用 Python 时,我可以实现以下目标:
import socket
ip_address = socket.gethostbyname(socket.gethostname())
任何帮助都会很棒!
答案 0 :(得分:4)
原来我一直在使用错误的API。对于我的用例,我需要使用chrome.system.network.getNetworkInterfaces。
这将返回所有接口的数组及其 IP地址。
这是我的示例代码:
chrome.system.network.getNetworkInterfaces(function(interfaces){
console.log(interfaces);
});
清单的权限:
"permissions": [
"system.network"
],
考虑到这些评论,不容易提供完美的解决方案,因为必须找到UDP端口的正确接口。
此时,完全匹配接口的唯一方法是bind
给出的所有接口的getNetworkInterfaces
所有地址。然后您确切地知道接收呼叫的确切接口,您可以使用正确的IP地址进行回复。
答案 1 :(得分:0)
未连接的套接字尚未拥有本地地址,除非它专门绑定到某个地址。一旦连接套接字(TCP)或通过套接字(UDP)发送数据,它只获取本地和远程地址。它只获取本地计算机的IP地址,而如果您在某些NAT路由器(即大多数家庭用户)后面,外部服务会看到路由器面向Internet的外部地址。
答案 2 :(得分:-1)
在最初创建套接字时调用您提供给udp.create()
的回调,而不是在套接字接收数据包时调用。在创建时,套接字尚未与任何localAddress
或localPort
相关联。您必须调用udp.bind()
来建立套接字将侦听数据包的特定localPort
(以及可选的特定localAddress
)。如果您bind()
到"0.0.0.0"
,则套接字将侦听所有本地IP。
当新数据包到达时,会触发udp.onReceive
事件。该数据包是由特定localAddress
收到的,但Chrome API未提供直接查询哪个localAddress
收到数据包的方法(基础recvfrom()
套接字函数未提供该信息) 。要发现接收本地IP,您必须:
将套接字绑定到特定的localAddress
,因为这将是唯一可以触发该套接字的onReceive
事件的本地IP。
检查chrome.system.network.getNetworkInterfaces()
报告的接口列表。如果报告1个接口,那将是接收所有数据包的接口,因此您可以使用其address
。但是,如果报告了2个以上的接口,则必须从数据包的remoteAddress
解析网络前缀,并将该值与每个报告的接口的前缀进行比较,直到找到匹配项(假设发送方正在从同一个网络广播)本地计算机连接到的网络子网,而不是跨子网边界进行广播。)
话虽如此,如果您需要将本地IP放入广播回复的数据有效负载中,所有这些都是相关的。假设有3个本地接口,并且在接口2上接收广播数据包。回复接口1或3的localAddress
显然是错误的,因为它们位于与广播公司不同的网络上。但是,如果您不需要将localAddress
放入回复的有效负载中,那么广播公司只需查看回复的remoteAddress
即可知道您的IP地址是什么。然后您根本不需要弄清楚您的本地IP,当您将回复发送到您收到广播的remoteAddress
/ remotePort
时,操作系统将为您处理所有内容。