WebRTC:匹配最近的同行

给定一个公共IP地址(对等体A)和许多其他公有IP地址(IPv4和IPv6地址混合)的列表,最简单的方法是将对等体A与最近对等体的IP地址进行匹配,对等方手动ping对方进行延迟基准testing?

我认为这可以使用BGP与一堆复杂的查询(也许涉及OSPF),但我希望可能有一个解决scheme或库,使它像下面的理论function调用一样简单。

 // `peer` is a single IP address. `peer_list` is a list of IP addresses // get the 5 nearest peers (ordered) to `peer` from `peer_list` nearest_peers = get_nearest_ips(peer, peer_list, 5); 

我应该只使用MaxMind的GeoIP数据库+ Haversine / Vincenty的本地实例,还是通过一个库(在需要的时候使用适当的caching)来使用BGP来实现这一目标是否可行?

似乎这种代码可能存在于一个开放源代码的选播路由实现中,尽pipe我还没有find任何符合这个用例的东西。

解决scheme或build议的库不必在node.js上工作 – 任何语言都可以。

当我阅读它时,你的问题比你的Javascript / WebRTC用例更普遍。

谁是这样的:“给定一个P2Pnetworking,并知道所有连接对等点的中央服务器,这是最好的度量标准,可以用来配对?

=>将两个任意节点配对的好度量是它们之间的跳距。 问题是这个值是不可能计算的(你只能猜测ISP路由器在节点之间select哪条path)。

如何近似呢?

1.使用地理距离作为跳距离的近似值

在这种情况下,你已经完成了很多工作。 使用任何“ip到latlng”服务,你就完成了。

2.尝试通过映射互联网来猜测真正的跳距

我find了关于这个主题的论文,这可能对你有用。 你可能会在他们的参考文献中find一些有关同一主题的文献:

估计任意主机对之间的跳跃距离 http://nowak.ece.wisc.edu/infocom09.pdf

摘要 – build立一个清晰和及时的互联网拓扑图很复杂,包括基础设施的庞大规模和dynamic性。 在本文中,我们描述了一种估计互联网拓扑的重要特征的方法 – 任意端主机之间的跳距。 我们的目标是开发一种准确,可扩展,及时且不需要重要的测量基础设施的双向跳距估计方法。 我们的方法基于部署一组使用类似traceroute探针的界标节点来build立一组精确的成对跳跃距离。 标志性节点还被configuration为从被动监控的networking分组业务中收集源IP地址和TTL值。 我们开发了一种新颖的多维缩放algorithm,可应用于被动和主动测量,以生成所有观测源主机地址的成对跳跃距离估计。 然后通过BGP路由信息增强基本algorithm来考虑源主机的自治系统成员资格。 我们使用一组合成networking拓扑来研究我们的估计algorithm的能力。 结果表明,我们的方法可以在一系列networking规模和configuration以及具有里程碑意义的基础架构大小上生成高度准确的双向跳数距离估计。

安装https://github.com/runk/node-maxmind

http://dev.maxmind.com/geoip/geoip2/geolite2/下载“GeoLite2-City.mmdb”

 var maxmind = require('maxmind'); var lookup = maxmind.open('./GeoLite2-City.mmdb'); /**/ var peers = [ '31.193.128.0', // UK '23.112.0.0', // USA '5.24.0.0', // Turkey '196.203.0.0', // Tunisia '77.243.64.0' // Malta ]; var peerLocations = {}; peers.forEach(function(peer) { var tmp = lookup.get(peer); if (!tmp || !tmp.location) { throw new Error('Unable to get initial peer location: ' + peer); } peerLocations[peer] = tmp.location; }); /**/ var testIp = '84.17.64.0'; // Turkey // 84.17.64.0 // Turkey // 37.219.0.0 // Finland // 5.39.0.0 // France // 37.75.32.0 // Malta // 5.2.96.0 // UK // 15.0.0.0 // USA // 41.224.0.0 // Tunisia console.log( findClosestPeer(testIp, 3) ); function findClosestPeer(ip, len) { var ipData = lookup.get(ip); var distances = []; if (ipData && ipData.location) { Object.keys(peerLocations).forEach(function(key) { var peer = peerLocations[key]; var distance = getDistanceFromLatLonInKM(ipData.location.latitude, ipData.location.longitude, peer.latitude, peer.longitude); distances.push({ip: key, distance: distance}); }); } // 0 ... 9 distances.sort(function(a, b) { return a.distance - b.distance; }); return len > 1 ? distances.slice(0, len) : distances.shift(); } /* http://stackoverflow.com/a/21279990/605399 */ function getDistanceFromLatLonInKM(lat1, lon1, lat2, lon2) { var R = 6371; // Radius of the earth in km var dLat = deg2rad(lat2 - lat1); // deg2rad below var dLon = deg2rad(lon2 - lon1); var a = Math.sin(dLat/2) * Math.sin(dLat/2) + Math.cos(deg2rad(lat1)) * Math.cos(deg2rad(lat2)) * Math.sin(dLon/2) * Math.sin(dLon/2) ; var c = 2 * Math.atan2( Math.sqrt(a), Math.sqrt(1 - a) ); var d = R * c; // Distance in km return d; } function deg2rad(deg) { return deg * ( Math.PI / 180 ); } 

寻找最近对等点的最简单的方法是发送每个对等点的回应请求,并测量得到响应所需的时间,就像ping一样。