Javascript 我可以在不使用外部服务的情况下在chrome应用程序中获取我的IP地址吗?

Javascript 我可以在不使用外部服务的情况下在chrome应用程序中获取我的IP地址吗?,javascript,sockets,google-chrome,google-chrome-app,Javascript,Sockets,Google Chrome,Google Chrome App,我正在构建并通过创建一个UDP套接字 有没有一种方法可以在不使用外部服务的情况下检索您自己的IP地址? 我所说的“自己的IP地址”:客户端和服务器都在同一个网络上。chrome应用程序需要使用自己的本地IP地址回答UDP广播 实际上,对于这个用例有一个精确的定义。但不幸的是,我只收到以下回调对象:object{paused:false,persistent:false,socketId:17},它缺少localAddress属性。它是SocketInfo对象中的(可选)属性,根据。这就是我正在运

我正在构建并通过创建一个UDP套接字

有没有一种方法可以在不使用外部服务的情况下检索您自己的IP地址? 我所说的“自己的IP地址”:客户端和服务器都在同一个网络上。chrome应用程序需要使用自己的本地IP地址回答UDP广播

实际上,对于这个用例有一个精确的定义。但不幸的是,我只收到以下回调对象:
object{paused:false,persistent:false,socketId:17}
,它缺少
localAddress
属性。它是
SocketInfo
对象中的(可选)属性,根据。这就是我正在运行的代码的本质:

chrome.sockets.udp.create({}, function(socketInfo){
    chrome.sockets.udp.getInfo(socketInfo.socketId, function (detailedInfo){
        ipAddress = detailedInfo.localAddress;
        console.debug(detailedInfo); // containts no `localAddress`
    });
});
我也不认为我遗漏了任何内容,因为本手册中没有描述任何特殊权限。这就是我使用的:

"sockets": {
  "udp": {
    "send": "*",
    "bind": "*"
  }
}
当我使用Python时,我可以实现以下目标:

import socket
ip_address = socket.gethostbyname(socket.gethostname())

任何帮助都会很好

未连接的套接字还没有本地地址,除非它专门绑定到一个地址。只有在连接套接字(TCP)或通过套接字(UDP)发送数据后,它才会获取本地和远程地址。它只获取本地机器的IP地址,而如果您在某个NAT路由器(即大多数家庭用户)后面,则外部服务会看到面向internet的路由器外部地址。

结果表明我使用了错误的API。对于我的用例,我需要使用

这将返回IP地址为的所有接口的数组

这是我的示例代码:

chrome.system.network.getNetworkInterfaces(function(interfaces){
    console.log(interfaces);
});
清单权限:

"permissions": [
  "system.network"
],
考虑到这些评论,要提供一个完美的解决方案并不容易,因为必须找到UDP端口的正确接口


在这一点上,完美匹配接口的唯一方法是绑定
getNetworkInterfaces
提供的所有接口的所有地址。然后您就可以确切地知道使用哪个接口来接收调用,并且您可以使用正确的IP地址来响应

您提供给
udp.create()
的回调在最初创建套接字时调用,而不是在套接字接收数据包时调用。在创建时,套接字尚未与任何
localAddress
localPort
关联。您必须调用
udp.bind()
,以建立套接字将侦听其上数据包的特定
localPort
(以及可选的特定
localAddress
)。如果将
bind()
绑定到
“0.0.0.0”
,则套接字将侦听所有本地IP

当新数据包到达时,将触发
udp.onReceive
事件。数据包是由特定的
localAddress
接收的,但是Chrome API没有提供直接查询哪个
localAddress
接收到数据包的方法(底层的
recvfrom()
socket函数不提供该信息)。要发现接收的本地IP,您必须:

  • 将套接字绑定到特定的
    localAddress
    ,因为这将是唯一可以触发该套接字的
    onReceive
    事件的本地IP

  • 检查chrome.system.network.getNetworkInterfaces()报告的接口列表。。如果报告1个接口,则该接口将接收所有数据包,因此您可以使用其
    地址
    。但是,如果报告了2+个接口,则必须从数据包的
    remoteAddress
    解析网络前缀,并将该值与每个报告接口的前缀进行比较,直到找到匹配项(假设发送方正在从本地计算机连接到的同一网络子网进行广播,而不是跨子网边界进行广播)


  • 这就是说,所有这些只有在您需要将本地IP放入广播应答的数据有效负载时才相关。假设有3个本地接口,并且广播数据包在接口2上接收。使用接口1或3的
    localAddress
    应答显然是错误的,因为它们位于不同于broadcas的网络上然而,如果你不需要把你的
    localAddress
    放在回复的有效载荷中,那么广播公司只需查看回复的
    remoteAddress
    ,就可以知道你的IP地址是什么。然后你根本不需要计算出你的本地IP,当你将回复发送到
    remo时,操作系统将为你处理一切teAddress
    /
    远程端口
    ,您从中接收广播。

    我想您的回答可能已经告诉了我我想知道的内容。我正在本地网络中运行此应用程序(客户端和服务器将在同一网络上)。我正在接收一条UDP广播消息,我将用自己的IP地址对其进行响应。因此,这对我来说已经足够充分了-一旦知道它是否有效,我将回信。如此接近…我确实等待了
    getInfo
    调用,直到我收到第一个包。是的,它现在终于具有属性
    localAddress
    。不幸的是,它的
    0.0.0
    ——即使我在
    send
    后返回时也是如此……现在完整的对象是
    Object{localAddress:“0.0.0”,localPort:22222,paused:false,persistent:false,socketId:21}
    这是因为您的UDP套接字在创建时未绑定到任何特定的本地IP,因此它侦听并接收所有本地IP上的数据包。这就是
    “0.0.0.0”
    表示。这不会告诉您哪个接口实际接收UDP广播数据包。答复时,您应该指定接收数据包的接口的IP,因为该接口连接到发生广播的LAN。这是正确的-必须有人提出一个完美的解决方案谨慎。