最近用上了学校的校园网, 速度还行吧
不过校园网每次要 web登录认证
, 就有点无语, 像我这么懒的人怎么可能每次都要重新登录一次
围观地址: https://github.com/jsxxzy/inet
原理很简单, 无非就是登录一个 POST
请求, 然后亿点点细节就可以了
懒才是第一生产力啊..
原理分析 2020-11-29
最近真的闲的不行, 没什么事情做, 奇怪的是室友不知道发生什么事了, 全都在学JAVA
, 搞得我一脸懵逼(按理说不应该天天游戏吗/雾)
所以就写了一个java
版本的校园网客户端: https://github.com/jsxxzy/inetl
首先查看入口函数: /src/main/java/io/xxzy/App.java
System.out.println(" login: 登录");
System.out.println(" get: 获取保存的账号密码");
System.out.println(" save: 保存账号密码");
System.out.println(" fix: 初始化账号密码");
System.out.println(" check: 查询是否登录");
System.out.println(" info: 查询信息");
System.out.println("logout: 注销");
System.out.println("=============>");
登录
校园网有登录的网端
稍微看一下就知道这就是简单的 post
请求
密码是经过 md5
机密, 加几个偏移值, 这几个偏移值在 html
片段里都有
/**
* 生成密码
* https://github.com/jsxxzy/ipsd
* @return 密码
*/
public String CreatePassword(String p) {
String offset1 = constvar.Pid + p + constvar.Calg;
String md5 = utilsx.CreateMD5(offset1);
return md5 + constvar.Calg + constvar.Pid;
}
请求之后, 后台返回的html
片段, 比较恶心的是, 居然不是utf-8
, 所以还需要将其转为utf-8
格式
/**
* 转为 `utf-8`
*/
static String toUTF8(String input) {
return new String(input.getBytes(), StandardCharsets.UTF_8);
}
返回的html
里有你需要的一些信息, 用来判断是否登录成功, 我们需要运行这段js
然后通过判断变量msga
来判断
但是第一步是去除其 <!--
/**
* 运营商的js写的不标准, 此函数试图去除一些不标准
*
* 一开口就老外包了...
*
* @param raw 源数据
* @return 正确的`js-code`
*/
public static String jsCodeRemoveCommit(String raw) {
String cp = raw.trim();
String left = "<!--";
String right = "// -->";
if (cp.startsWith(left)) {
cp = cp.substring(left.length());
};
if (cp.endsWith(right)) {
int endIndex = cp.length() - right.length();
cp = cp.substring(0, endIndex);
}
return cp;
}
判断条件为, 若为空表示登录成功, 若为 5
多台设备在线, 若为 1
表示账号或密码错误
查询是否登录
查询是否登录
只是查询信息
的alias
// 未登录将会自动跳转到 `/0.htm` 登录界面, 但判断条件为 `title` 字符串为空
String title = $.title();
查询信息
查询信息相对有点复杂, 访问校园路由, 然后和登录差不多, 先转utf-8
然后拿到js
, 运行, 就可以拿到了
// 运行`js`
void InitData(Document $) {
js jsRuntime = new js();
Elements jsData = $.select(constvar.QueryInfoSelectText);
String jsDataText = jsData.get(0).html();
String jsInputData = utilsx.jsCodeRemoveCommit(jsDataText);
jsRuntime.RunScript(jsInputData);
String cacheTimeString = jsRuntime.GetString(constvar.InfoTime);
try {
this.Time = Integer.parseInt(cacheTimeString);
} catch (NumberFormatException e) {
e.printStackTrace();
}
this.Ipv6 = jsRuntime.GetString(constvar.InfoIpv6);
this.Ipv4 = jsRuntime.GetString(constvar.InfoIpv4);
this.UID = jsRuntime.GetString(constvar.InfoUID);
this.Xip = jsRuntime.GetString(constvar.InfoXip);
this.Portalname = jsRuntime.GetString(constvar.InfoPortalname);
String cacheFlowData = jsRuntime.GetString(constvar.InfoFlow);
try {
this.Flow = Integer.parseInt(cacheFlowData);
} catch (NumberFormatException e) {
}
注销
注销比较简单, 只是GET
请求一下注销的路由即可
get
| save
| fix
存储账号到本地, 比较简单, 读写一个文件, 不过我自己实现了一个解析格式
/**
* 解析格式
*/
private String[] parseLocalAuth(String rawString) {
String[] em = new String[0];
if (rawString.length() == 0) {
return em;
}
String[] arr = rawString.split(this.offset);
if (arr.length <= 1) {
return em;
}
String[] r = new String[2];
r[0] = arr[0];
r[1] = arr[1];
return r;
}
作者有话说
额, 迫于无聊编写的, 以前一直对于java
有偏见, 但是写了以后发现好像还挺好的哈