Java模拟登陆微博并上传图片到相册

发现微博相册的图片可以外链而且访问速度超快不用担心流量限制,所以在网上搜索了一下发现很多用微博做图床的代码,但是都是陈年老代码现在也不适用了,因为主要搞Java,所以我用Java写了一段:Java模拟登陆微博并上传图片到相册的代码。
主要用到两个包:FastJson、Okhttp
//本人代码水平较差,为了你的电子设备的安全不建议一边吃东西一边时浏览

1、登陆

1.1 上传图片显然需要先登陆,Chrome F12显示微博登录Post很多参数

1
2
URL:https://login.sina.com.cn/sso/login.php?client=ssologin.js(v1.4.19)&_=1552118477253
//上面的URL最后的显然是时间戳

POST的参数为:
![登陆所有参数][1]

这些参数很多是固定的,用户名和密码是加密的,从pwencode可以看出来密码使用了rsa2的加密方式,有了解加密的人应该知道Rsa加密是需要一个公钥的,但是我们并不知道公钥是啥,所以再次打开Chrome查看登陆页面打开的所有链接。

1.2预登陆(获取数据)

发现一个链接,请求方式为GET

1
2
URL:https://login.sina.com.cn/sso/prelogin.php?entry=weibo&callback=sinaSSOController.preloginCallBack&su=&rsakt=mod&client=ssologin.js(v1.4.19)&_=1552119228733
//上面的URL最后的显然是时间戳

![预登陆请求][2]
返回数据:
![预登陆返回数据][3]
里面已经包含了我们需要的pubkey,还有几个数据是登陆的POST参数

代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
private JSONObject proLogin(){
Request request=new Request.Builder()
.url("https://login.sina.com.cn/sso/prelogin.php?entry=weibo&callback=sinaSSOController.preloginCallBack&su=&rsakt=mod&client=ssologin.js(v1.4.19)")
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
String body=response.body().string();
body=body.replace("sinaSSOController.preloginCallBack(","");
body=body.replace(")","");
if(JsonUtil.isJson(body)){
return JSONObject.parseObject(body);
}
}
} catch (IOException e) {
e.printStackTrace();
}
return null;
}

1.3模拟登陆吧

1.1中的POST参数中su为加密后的用户名,sp代表加密后的密码
su的加密方式为简单的Base64加密
sp的加密方式为rsa2,公钥由预登陆中获取到的pubkey和字符串”10001”生成

登陆的Java代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
public boolean userLogin(){
JSONObject preObj=proLogin();
if(preObj==null){
System.out.println("预登陆数据获取失败");
return false;
}
String pwd=preObj.getString("servertime")+"\t"+preObj.getString("nonce")+"\n"+PASSWD;
FormBody.Builder builder = new FormBody.Builder();
builder.add("entry","weibo")
.add("gateway","1")
.add("from","")
.add("savestate","7")
.add("useticket","1")
.add("pagerefer","https://passport.weibo.com")
.add("vsnf","1")
.add("su",Base64.getEncoder().encodeToString(Phone.getBytes()))
.add("service","miniblog")
.add("servertime",preObj.getString("servertime"))
.add("nonce",preObj.getString("nonce"))
.add("pwencode","rsa2")
.add("rsakv",preObj.getString("rsakv"))
.add("sp", RSAEncoder.RSAEncrypt(pwd,preObj.getString("pubkey"),"10001"))
.add("sr","1366*768")
.add("encoding","UTF-8")
.add("prelt","115")
.add("cdult","38")
.add("url","http://weibo.com/ajaxlogin.php?framelogin=1&callback=parent.sinaSSOController.feedBackUrlCallBack")
.add("returntype","TEXT");
RequestBody formBody = builder.build();
Request request=new Request
.Builder()
.url("https://login.sina.com.cn/sso/login.php?client=ssologin.js(v1.4.19)")
.post(formBody)
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
String body=response.body().string();
if(!JsonUtil.isJson(body)){
System.out.println("登陆失败");
return false;
}
getWeibo(JSONObject.parseObject(body));
return true;
}
} catch (IOException e) {
e.printStackTrace();
}
return false;
}

如上我们已经有了登陆成功的Cookie了

1.3获取上传图片

在Chrome里F12捕获的接口

1
URL:http://picupload.service.weibo.com/interface/pic_upload.php?s=rdxt&app=miniblog&cb=//photo.weibo.com/upload/simple_upload/pic/1

Java代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
public JSONObject uploadImg(File file){
RequestBody requestBody = new MultipartBody.Builder()
.setType(MultipartBody.FORM)
.addFormDataPart("pic1", file.getName(), RequestBody.create(MediaType.parse("image/png"), file))
.build();

Request request=new Request
.Builder()
.addHeader("User-Agent","Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/52.0.2743.116 Safari/537.36")
.url("http://picupload.service.weibo.com/interface/pic_upload.php?s=rdxt&app=miniblog&cb=//photo.weibo.com/upload/simple_upload/pic/1")
.post(requestBody)
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
String body=response.body().string();
return getImgPid(body);//获取图片的Pid
}
} catch (IOException e) {
e.printStackTrace();
}
return null;
}

private JSONObject getImgPid(String body){
if(!body.contains("ete(")){
System.out.println(body);
return null;
}
String jsonstr=body.substring(body.indexOf("ete(")+4,body.indexOf(",1);"));
if(JsonUtil.isJson(jsonstr)){
JSONObject pic1= JSON.parseObject(jsonstr);
if(pic1.getString("pid") !=null && pic1.getString("pid").length()>5){
System.out.println(pic1);
return pic1;
}
}
return null;
}

得到上传图片的Pid之后可以通过
http://ww1.sinaimg.cn/large/+Pid+.jpg
比如:http://ww1.sinaimg.cn/large/007FnlFugy1g0wlfct1u4j30go0godhs.jpg
访问到这个图片了

完整代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
package crawler.sina;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import crawler.utils.FileUtil;
import crawler.utils.JsonUtil;
import crawler.utils.MyCookieJar;
import crawler.utils.RSAEncoder;
import okhttp3.*;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Base64;

public class WeiBoUtil {
OkHttpClient client;
MyCookieJar cookies;
String PASSWD="";//密码
String Phone="";//用户名

public WeiBoUtil(){
cookies=new MyCookieJar();
client = new OkHttpClient.Builder().cookieJar(cookies).build();
}

private JSONObject proLogin(){
Request request=new Request.Builder()
.url("https://login.sina.com.cn/sso/prelogin.php?entry=weibo&callback=sinaSSOController.preloginCallBack&su=&rsakt=mod&client=ssologin.js(v1.4.19)")
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
String body=response.body().string();
body=body.replace("sinaSSOController.preloginCallBack(","");
body=body.replace(")","");
if(JsonUtil.isJson(body)){
return JSONObject.parseObject(body);
}
}
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
public boolean userLogin(){
JSONObject preObj=proLogin();
if(preObj==null){
System.out.println("预登陆数据获取失败");
return false;
}
String pwd=preObj.getString("servertime")+"\t"+preObj.getString("nonce")+"\n"+PASSWD;
FormBody.Builder builder = new FormBody.Builder();
builder.add("entry","weibo")
.add("gateway","1")
.add("from","")
.add("savestate","7")
.add("useticket","1")
.add("pagerefer","https://passport.weibo.com")
.add("vsnf","1")
.add("su",Base64.getEncoder().encodeToString(Phone.getBytes()))
.add("service","miniblog")
.add("servertime",preObj.getString("servertime"))
.add("nonce",preObj.getString("nonce"))
.add("pwencode","rsa2")
.add("rsakv",preObj.getString("rsakv"))
.add("sp", RSAEncoder.RSAEncrypt(pwd,preObj.getString("pubkey"),"10001"))
.add("sr","1366*768")
.add("encoding","UTF-8")
.add("prelt","115")
.add("cdult","38")
.add("url","http://weibo.com/ajaxlogin.php?framelogin=1&callback=parent.sinaSSOController.feedBackUrlCallBack")
.add("returntype","TEXT");
RequestBody formBody = builder.build();
Request request=new Request
.Builder()
.url("https://login.sina.com.cn/sso/login.php?client=ssologin.js(v1.4.19)")
.post(formBody)
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
String body=response.body().string();
if(!JsonUtil.isJson(body)){
System.out.println("登陆失败");
return false;
}
getWeibo(JSONObject.parseObject(body));
return true;
}
} catch (IOException e) {
e.printStackTrace();
}
return false;
}
private void getWeibo(JSONObject json){
Request request=new Request
.Builder()
.url("https://passport.weibo.com/wbsso/login?ticket=" +json.getString("ticket")+
"&ssosavestate=1583576124&callback=sinaSSOController.doCrossDomainCallBack&scriptId=ssoscript0&client=ssologin.js(v1.4.19)&_=1552040124932")
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
//复制几个cookie
cookies.copyCookies("passport.weibo.com","picupload.service.weibo.com");
cookies.copyCookies("passport.weibo.com","weibo.com");
cookies.copyCookies("passport.weibo.com","photo.weibo.com");
}

} catch (IOException e) {
e.printStackTrace();
}
}

public JSONObject uploadImg(File file){
RequestBody requestBody = new MultipartBody.Builder()
.setType(MultipartBody.FORM)
.addFormDataPart("pic1", file.getName(), RequestBody.create(MediaType.parse("image/png"), file))
.build();

Request request=new Request
.Builder()
.addHeader("User-Agent","Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/52.0.2743.116 Safari/537.36")
.url("http://picupload.service.weibo.com/interface/pic_upload.php?s=rdxt&app=miniblog&cb=//photo.weibo.com/upload/simple_upload/pic/1")
.post(requestBody)
.build();
try {
Response response=client.newCall(request).execute();
if(response.isSuccessful()){
String body=response.body().string();
return getImgPid(body);
}
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
private JSONObject getImgPid(String body){
if(!body.contains("ete(")){
System.out.println(body);
return null;
}
String jsonstr=body.substring(body.indexOf("ete(")+4,body.indexOf(",1);"));
if(JsonUtil.isJson(jsonstr)){
JSONObject pic1= JSON.parseObject(jsonstr);
if(pic1.getString("pid") !=null && pic1.getString("pid").length()>5){
System.out.println(pic1);
return pic1;
}
}
return null;
}
}

[1]: http://ww1.sinaimg.cn/large/007FnlFugy1g1681ls47mj30lg0i5gme.jpg
[2]: http://ww1.sinaimg.cn/large/007FnlFugy1g1681tnr89j30mh05ejrl.jpg
[3]: http://ww1.sinaimg.cn/large/007FnlFugy1g168215h1uj30sf047mxf.jpg