不知道是公网IP不够用了,还是什么鬼原因,近期我这的联通ADSL拨号很大程度上获取的是一个10.开头的内网IP。虽说通常情况下无需关心,但跑PT,VPN等速度上大打折扣。投诉无果后只能自己写个脚本来自动更换IP。
其原理很简单,模拟登录到路由器上检查WANIP是否是10.或0.开头,如是则断开重连,以此循环。代码是Java编写,无任何依赖,运行在树莓派上,24小时监视,在运营商完全分配内网IP之前还可以挣扎一阵子。有需要的朋友可以参考下。
我这用的是TP-LINK WR720N路由器,设置了局域网IP为192.168.30.1 端口88,通过Chrome登录到路由器,可以在开发者工具中查看到Basic加密的Key,替换相应的位置即可。
查询IP的链接
http://192.168.30.1:88/userRpm/StatusRpm.htm
断开拨号的链接
http://192.168.30.1:88/userRpm/StatusRpm.htm?Disconnect=%B6%CF%20%CF%DF&wan=1
重新拨号的链接
http://192.168.30.1:88/userRpm/StatusRpm.htm?Connect=%C1%AC%20%BD%D3&wan=1
代码如下:
import java.io.BufferedReader; import java.io.InputStream; import java.io.InputStreamReader; import java.net.URL; import java.net.URLConnection; import java.text.SimpleDateFormat; import java.util.Date; import java.util.regex.Matcher; import java.util.regex.Pattern; public class CheckIP { private static SimpleDateFormat simpleDateFormat = new SimpleDateFormat( "yyyy-MM-dd HH:mm:ss"); public static void main(String[] args) throws Exception { do { String currentIP = getIP(); if (currentIP.startsWith("10.") || currentIP.startsWith("0.")) { System.out.println(simpleDateFormat.format(new Date()) + " 检测到异常:" + currentIP); getHtml("http://192.168.30.1:88/userRpm/StatusRpm.htm?Disconnect=%B6%CF%20%CF%DF&wan=1"); Thread.sleep(1000 * 1); getHtml("http://192.168.30.1:88/userRpm/StatusRpm.htm?Connect=%C1%AC%20%BD%D3&wan=1"); Thread.sleep(1000 * 3); } Thread.sleep(1000 * 3); } while (true); } private static String getIP() throws Exception { String wanPara = getHtml("http://192.168.30.1:88/userRpm/StatusRpm.htm"); if (null != wanPara) { wanPara = wanPara.substring(wanPara.indexOf("var wanPara"), wanPara.length()); wanPara = wanPara.substring(0, wanPara.indexOf(");") + 2); } return getFirstIp(wanPara); } private static String getHtml(String address) throws Exception { URL url = new URL(address); URLConnection connection = url.openConnection(); connection.setRequestProperty("Authorization", "Basic YWRtaW46d3Npa3Nr"); connection.connect(); InputStream inputStream = null; StringBuffer stringBuffer = new StringBuffer(); inputStream = connection.getInputStream(); BufferedReader bufferedReader = new BufferedReader( new InputStreamReader(inputStream)); String line; while ((line = bufferedReader.readLine()) != null) { stringBuffer.append(line); } bufferedReader.close(); inputStream.close(); return stringBuffer.toString(); } private static String getFirstIp(String packet) { Pattern p = Pattern.compile("\\d+\\.\\d+\\.\\d+\\.\\d+"); Matcher m = p.matcher(packet); if (m.find()) { return m.group(); } else { return null; } } }
编译
pi@raspberrypi ~ $ javac CheckIP.java
后台运行
pi@raspberrypi ~ $ nohup java CheckIP &
日志
pi@raspberrypi ~ $ tail -f nohup.out