Firefox 跟 Chrome支持WebRTC可以向STUN服务器请求,返回内外网IP,不同于XMLHttpRequest请求,STUN请求开发者工具当中看不到网络请求的。
! p. @0 q; z# f
3 j1 U6 s( [% I& s//get the IP addresses associated with an account
V" Q2 _& n# d2 S5 i% ]; B2 u- mfunction getIPs(callback){
$ O( y: |$ C# E: q& f0 g) C- _' ? var ip_dups = {};6 j7 `6 K* N: Q* G
9 p+ f" Y" b J" J
//compatibility for firefox and chrome& u6 ?/ l' V/ c. G6 n
var RTCPeerConnection = window.RTCPeerConnection+ g# x, H# _" q* l1 _# d' l
|| window.mozRTCPeerConnection
; b' h8 _1 t9 N* f3 x. l2 |: w || window.webkitRTCPeerConnection;) V2 a! r$ g Z9 u8 A
var mediaConstraints = {
3 m* T. L& x# w' @4 ?2 P optional: [{RtpDataChannels: true}]
0 Y+ S9 E1 U6 }% y1 s1 `' Y };
; e4 A2 I$ V2 I1 o3 ]. R$ {) M- q
% s( d% s! }2 m- C9 Y+ q& a7 S //firefox already has a default stun server in about:config
% Z3 O6 B! q7 q7 R1 W% l+ f$ o // media.peerconnection.default_iceservers =
* M* Y B9 c; I. [- A // [{"url": "stun:stun.services.mozilla.com"}]4 c* [% ^% q% T0 S
var servers = undefined;6 X; F* p& Z5 R+ w4 U: ]4 F
% s+ h3 D) l2 l* t1 A2 B( K6 m //add same stun server for chrome
+ z2 b6 D( }# l if(window.webkitRTCPeerConnection)
! n$ n6 m! g0 n4 q9 p- x" i& x) Q servers = {iceServers: [{urls: "stun:stun.services.mozilla.com"}]};; [- x+ Q( F9 P- o7 g* D
' K1 @; d0 _' U3 O/ d+ K //construct a new RTCPeerConnection
% P. B% q% `; P# b7 C var pc = new RTCPeerConnection(servers, mediaConstraints);
1 `! Y2 u& c* D o* r! ^. j/ G
: B& G. X4 e5 a( b" K //listen for candidate events
' m3 y) @* q. f& j* T: Z pc.onicecandidate = function(ice){
% G- T; o; s7 C2 L & \* n; I7 H& B4 }
//skip non-candidate events
* f+ Y7 H; I, E* k) q( u5 D: j* m if(ice.candidate){+ W# G# c4 f$ Y* t; k
, P9 e, ?" w7 O" ]# H, V
//match just the IP address
. O5 X; D* @* ~" _. y5 G var ip_regex = /([0-9]{1,3}(\.[0-9]{1,3}){3})/
& E( P) k5 @- f7 [. g var ip_addr = ip_regex.exec(ice.candidate.candidate)[1];
$ u l; m6 [4 A& E5 d T6 S9 G) ?! J6 J& i7 |
//remove duplicates
+ g6 s& }# A o& H if(ip_dups[ip_addr] === undefined)4 |0 @( w2 ]" p3 H8 r* S8 Z3 ^3 Q
callback(ip_addr);
* \& W& O/ B% k) [/ d- I# H
+ G$ s! v: o5 b% i# D* \" ^! n ip_dups[ip_addr] = true;
# _0 y+ }$ a$ m" q$ [& r }' M0 W8 n3 E( T b
};
5 ]1 _( s6 j$ F% v% w* x j' z - l4 Z" O; i3 G# |" U
//create a bogus data channel1 x% }' U/ L/ J# l, L2 M( z# a9 |
pc.createDataChannel("");
e" h& B% J+ W: a4 q* a- R; r
3 T( w4 H$ A! u# S- Y6 y1 q! b! P //create an offer sdp
$ g) ]7 n) X2 i' T7 m) t( R pc.createOffer(function(result){/ N. _' e( G* i
+ A8 _, i! G1 z' y! ` ?
//trigger the stun server request
( h5 k1 y% O* g& t pc.setLocalDescription(result, function(){});. W+ w: F5 R, V( [) m
# ^( d) ~" B0 o' M- [/ r3 O
}, function(){});# k/ b% @, N4 D% s3 N$ N
}
1 ^8 h- {$ v6 k) G
& d' y; ~" R0 \4 a; B//Test: Print the IP addresses into the console8 `$ H( t; j1 l( C# Q
getIPs(function(ip){console.log(ip);}); |
|