├── README.md
├── assert
├── code0.png
├── console1.png
├── demo1.png
└── wechat4j.jar
└── wechat4j-common
├── .classpath
├── .project
├── .settings
├── org.eclipse.core.resources.prefs
├── org.eclipse.jdt.core.prefs
└── org.eclipse.m2e.core.prefs
├── dependency-reduced-pom.xml
├── pom.xml
├── src
└── main
│ ├── java
│ └── com
│ │ └── iyuexian
│ │ └── wechat4j
│ │ ├── WechatStartup.java
│ │ ├── bean
│ │ ├── BaseRequest.java
│ │ ├── ChatRoom.java
│ │ ├── ChatRoomMember.java
│ │ ├── ContactUser.java
│ │ ├── GroupMember.java
│ │ └── Msg.java
│ │ ├── config
│ │ ├── Constant.java
│ │ ├── Enums.java
│ │ └── MsgType.java
│ │ ├── core
│ │ ├── WechatApiUtil.java
│ │ └── WechatMeta.java
│ │ ├── demo
│ │ └── Demo1.java
│ │ ├── exception
│ │ └── WechatException.java
│ │ ├── plugin
│ │ ├── ContactManager.java
│ │ ├── ContactUserUtil.java
│ │ ├── FileHandler.java
│ │ ├── FriendAddTask.java
│ │ ├── MessageListener.java
│ │ ├── QRCodeWindow.java
│ │ ├── QrUtil.java
│ │ ├── Storage.java
│ │ ├── Task.java
│ │ ├── TulingRobot.java
│ │ ├── TxtMessageRobot.java
│ │ ├── WxLocalCache.java
│ │ ├── message
│ │ │ ├── AbstractMessageHandler.java
│ │ │ ├── IMessageHandler.java
│ │ │ ├── MessageManager.java
│ │ │ ├── MpMessageHandler.java
│ │ │ ├── PictureMessageHandler.java
│ │ │ ├── TxtMessageHandler.java
│ │ │ ├── VideoMessageHandler.java
│ │ │ └── VoiceMessageHandler.java
│ │ └── storage
│ │ │ ├── FilePipeLine.java
│ │ │ ├── MessagePipeLine.java
│ │ │ └── PipeLineManager.java
│ │ └── util
│ │ ├── Converter.java
│ │ ├── CookieUtil.java
│ │ ├── DigestUtils.java
│ │ ├── Emptys.java
│ │ ├── FileUploadHelper.java
│ │ ├── FileUtil.java
│ │ ├── HttpClient.java
│ │ ├── IOKit.java
│ │ ├── Matchers.java
│ │ ├── PropertyReader.java
│ │ └── TulingUtil.java
│ └── resources
│ ├── config.properties
│ ├── log4j.properties
│ └── logging.properties
└── target
├── classes
├── .gitignore
├── META-INF
│ ├── MANIFEST.MF
│ └── maven
│ │ └── com.iyuexian.wechat4j
│ │ └── wechat4j-common
│ │ ├── pom.properties
│ │ └── pom.xml
├── com
│ └── iyuexian
│ │ └── wechat4j
│ │ ├── WechatStartup$1.class
│ │ ├── WechatStartup.class
│ │ ├── bean
│ │ ├── BaseRequest.class
│ │ ├── ChatRoom.class
│ │ ├── ChatRoomMember.class
│ │ ├── ContactUser.class
│ │ ├── GroupMember.class
│ │ └── Msg.class
│ │ ├── config
│ │ ├── Constant.class
│ │ ├── Enums$FileType.class
│ │ ├── Enums$MsgType.class
│ │ ├── Enums$OS.class
│ │ └── Enums.class
│ │ ├── core
│ │ ├── WechatApiUtil.class
│ │ └── WechatMeta.class
│ │ ├── demo
│ │ └── Demo1.class
│ │ ├── exception
│ │ └── WechatException.class
│ │ ├── plugin
│ │ ├── ContactManager.class
│ │ ├── ContactUserUtil.class
│ │ ├── FileHandler.class
│ │ ├── FriendAddTask.class
│ │ ├── MessageListener.class
│ │ ├── QRCodeWindow$1.class
│ │ ├── QRCodeWindow.class
│ │ ├── QrUtil.class
│ │ ├── Storage.class
│ │ ├── Task$1.class
│ │ ├── Task.class
│ │ ├── TulingRobot$InputText.class
│ │ ├── TulingRobot$Location.class
│ │ ├── TulingRobot$UserInfo.class
│ │ ├── TulingRobot.class
│ │ ├── TxtMessageRobot.class
│ │ ├── WxLocalCache$CacheItem.class
│ │ ├── WxLocalCache$Holder.class
│ │ ├── WxLocalCache.class
│ │ ├── message
│ │ │ ├── AbstractMessageHandler.class
│ │ │ ├── IMessageHandler.class
│ │ │ ├── MessageManager.class
│ │ │ ├── MpMessageHandler.class
│ │ │ ├── PictureMessageHandler.class
│ │ │ ├── TxtMessageHandler.class
│ │ │ ├── VideoMessageHandler.class
│ │ │ └── VoiceMessageHandler.class
│ │ └── storage
│ │ │ ├── FilePipeLine.class
│ │ │ ├── MessagePipeLine.class
│ │ │ ├── PipeLineManager$Holder.class
│ │ │ └── PipeLineManager.class
│ │ └── util
│ │ ├── Converter.class
│ │ ├── CookieUtil.class
│ │ ├── DigestUtils.class
│ │ ├── Emptys$NullPlaceholder.class
│ │ ├── Emptys.class
│ │ ├── FileUploadHelper.class
│ │ ├── FileUtil.class
│ │ ├── HttpClient.class
│ │ ├── IOKit.class
│ │ ├── Matchers.class
│ │ ├── PropertyReader.class
│ │ └── TulingUtil.class
├── config.properties
├── log4j.properties
└── logging.properties
├── maven-archiver
└── pom.properties
├── maven-status
└── maven-compiler-plugin
│ ├── compile
│ └── default-compile
│ │ ├── createdFiles.lst
│ │ └── inputFiles.lst
│ └── testCompile
│ └── default-testCompile
│ └── inputFiles.lst
├── original-wechat4j.jar
├── wechat4j-common-0.0.1-SNAPSHOT-shaded.jar
└── wechat4j.jar
/README.md:
--------------------------------------------------------------------------------
1 | # wechat4j
2 | 用java实现的微信客户端,支持自动聊天, 消息监听,自动回复,添加好友,获取群成员列表,自动记录聊天记录,自动下载图片,语音,视频消息
3 |
4 | QQ交流群:580889921
5 |
6 |
7 | # 启动方式
8 | ### 1:控制台启动
9 | 自定任意类,在main方法下用WecahtStartup.login()实现扫码登陆
10 | ```
11 | WechatMeta meta = WechatStartup.login();
12 | ```
13 | 登陆成功后,会返回WechatMeta实例,里面包含了当前扫码用户的登陆信息,后面所有的功能都需要该实例
14 | WechatApiUtil类封装微信的相关接口,具体功能实现在plugin及其实子包里,您也可以在这基础上扩展
15 |
16 |
17 |
18 | ### 下载jar包体验
19 | [wechat4j.jar](https://github.com/hexiangtao/wechat4j/blob/master/assert/wechat4j.jar)
20 |
21 | #### 运行方式
22 | ````
23 | java -jar wechat4j.jar
24 | ````
25 |
26 |
27 | 启动后控制台如下:
28 | 
29 |
30 |
31 | #### 代码示例
32 | 
33 |
34 |
35 |
36 | #### 运行示例图
37 | 
38 |
39 |
40 |
41 |
42 |
43 |
--------------------------------------------------------------------------------
/assert/code0.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/assert/code0.png
--------------------------------------------------------------------------------
/assert/console1.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/assert/console1.png
--------------------------------------------------------------------------------
/assert/demo1.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/assert/demo1.png
--------------------------------------------------------------------------------
/assert/wechat4j.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/assert/wechat4j.jar
--------------------------------------------------------------------------------
/wechat4j-common/.classpath:
--------------------------------------------------------------------------------
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 |
--------------------------------------------------------------------------------
/wechat4j-common/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | wechat4j-common
4 |
5 |
6 |
7 |
8 |
9 | org.eclipse.jdt.core.javabuilder
10 |
11 |
12 |
13 |
14 | org.eclipse.m2e.core.maven2Builder
15 |
16 |
17 |
18 |
19 |
20 | org.eclipse.jdt.core.javanature
21 | org.eclipse.m2e.core.maven2Nature
22 |
23 |
24 |
--------------------------------------------------------------------------------
/wechat4j-common/.settings/org.eclipse.core.resources.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | encoding/=UTF-8
3 |
--------------------------------------------------------------------------------
/wechat4j-common/.settings/org.eclipse.jdt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
3 | org.eclipse.jdt.core.compiler.codegen.methodParameters=generate
4 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8
5 | org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
6 | org.eclipse.jdt.core.compiler.compliance=1.8
7 | org.eclipse.jdt.core.compiler.debug.lineNumber=generate
8 | org.eclipse.jdt.core.compiler.debug.localVariable=generate
9 | org.eclipse.jdt.core.compiler.debug.sourceFile=generate
10 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
11 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
12 | org.eclipse.jdt.core.compiler.problem.forbiddenReference=warning
13 | org.eclipse.jdt.core.compiler.source=1.8
14 |
--------------------------------------------------------------------------------
/wechat4j-common/.settings/org.eclipse.m2e.core.prefs:
--------------------------------------------------------------------------------
1 | activeProfiles=
2 | eclipse.preferences.version=1
3 | resolveWorkspaceProjects=true
4 | version=1
5 |
--------------------------------------------------------------------------------
/wechat4j-common/dependency-reduced-pom.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 4.0.0
4 | com.iyuexian.wechat4j
5 | wechat4j-common
6 | wechat4j Maven Webapp
7 | 0.0.1-SNAPSHOT
8 | http://maven.apache.org
9 |
10 | compile
11 | wechat4j
12 |
13 |
14 | maven-shade-plugin
15 |
16 |
17 | package
18 |
19 | shade
20 |
21 |
22 |
23 |
24 | com.iyuexian.wechat4j.demo.Demo1
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 | maven-compiler-plugin
33 |
34 | 1.8
35 | 1.8
36 |
37 | -parameters
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 | junit
46 | junit
47 | 3.8.1
48 | test
49 |
50 |
51 |
52 |
53 |
--------------------------------------------------------------------------------
/wechat4j-common/pom.xml:
--------------------------------------------------------------------------------
1 |
3 | 4.0.0
4 | com.iyuexian.wechat4j
5 | wechat4j-common
6 | jar
7 | 0.0.1-SNAPSHOT
8 | wechat4j Maven Webapp
9 | http://maven.apache.org
10 |
11 |
12 | junit
13 | junit
14 | 3.8.1
15 | test
16 |
17 |
18 | com.bladejava
19 | blade-kit
20 | 1.3.4
21 |
22 |
23 | org.slf4j
24 | slf4j-log4j12
25 | 1.7.21
26 |
27 |
28 | com.alibaba
29 | fastjson
30 | 1.2.44
31 |
32 |
33 | commons-io
34 | commons-io
35 | 2.7
36 |
37 |
38 | mysql
39 | mysql-connector-java
40 | 8.0.16
41 |
42 |
43 | org.sql2o
44 | sql2o
45 | 1.6.0-RC3
46 |
47 |
48 |
49 | com.qiniu
50 | qiniu-java-sdk
51 | 7.0.2
52 |
53 |
54 |
55 |
56 | wechat4j
57 |
58 |
59 | org.apache.maven.plugins
60 | maven-shade-plugin
61 |
62 |
63 | package
64 |
65 | shade
66 |
67 |
68 |
69 |
70 | com.iyuexian.wechat4j.demo.Demo1
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 | org.apache.maven.plugins
79 | maven-compiler-plugin
80 |
81 | 1.8
82 | 1.8
83 |
84 | -parameters
85 |
86 |
87 |
88 |
89 | compile
90 |
91 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/WechatStartup.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j;
2 |
3 | import java.awt.EventQueue;
4 |
5 | import javax.swing.UIManager;
6 |
7 | import org.slf4j.Logger;
8 | import org.slf4j.LoggerFactory;
9 |
10 | import com.blade.kit.json.JSONArray;
11 | import com.blade.kit.json.JSONObject;
12 | import com.iyuexian.wechat4j.config.Constant;
13 | import com.iyuexian.wechat4j.core.WechatApiUtil;
14 | import com.iyuexian.wechat4j.core.WechatMeta;
15 | import com.iyuexian.wechat4j.exception.WechatException;
16 | import com.iyuexian.wechat4j.plugin.QRCodeWindow;
17 | import com.iyuexian.wechat4j.plugin.WxLocalCache;
18 | import com.iyuexian.wechat4j.util.Matchers;
19 |
20 | public class WechatStartup {
21 |
22 | protected Logger logger = LoggerFactory.getLogger(WechatStartup.class);
23 | private QRCodeWindow qrCodeFrame;
24 | private WechatMeta meta;
25 |
26 | private WechatStartup() {
27 | System.setProperty("https.protocols", "TLSv1");
28 | System.setProperty("jsse.enableSNIExtension", "false");
29 | }
30 |
31 | public static WechatMeta login() {
32 | try {
33 | WechatStartup instance = new WechatStartup();
34 | instance.doLogin();
35 | return instance.meta;
36 | } catch (Exception ex) {
37 | ex.printStackTrace();
38 | }
39 | return null;
40 |
41 | }
42 |
43 | private void doLogin() throws Exception {
44 | String uuid = WechatApiUtil.getUUID();
45 | showQrCode(uuid);
46 |
47 | while (true) {
48 |
49 | String res = WechatApiUtil.waitLogin(0, uuid);
50 | String code = Matchers.match("window.code=(\\d+);", res);
51 |
52 | if (!Constant.HTTP_OK.equals(code)) {
53 | Thread.sleep(2000);
54 | continue;
55 | }
56 | closeQrWindow();
57 | WechatMeta meta = WechatApiUtil.newWechatMeta(res);
58 | WechatApiUtil.login(meta);
59 | JSONObject wxInitObj = WechatApiUtil.wxInit(meta);
60 | WechatApiUtil.openStatusNotify(meta);
61 | this.meta = meta;
62 | JSONArray contactList = wxInitObj.get("ContactList").asArray();
63 | WxLocalCache.init(this.meta).setLatestContactList(contactList);
64 | break;
65 | }
66 | }
67 |
68 | private void showQrCode(String uuid) throws WechatException {
69 |
70 | final String path = WechatApiUtil.getQrCode(uuid);
71 | EventQueue.invokeLater(new Runnable() {
72 | public void run() {
73 | try {
74 | UIManager.setLookAndFeel("com.sun.java.swing.plaf.nimbus.NimbusLookAndFeel");
75 | qrCodeFrame = new QRCodeWindow(path);
76 | } catch (Exception e) {
77 | e.printStackTrace();
78 | }
79 | }
80 | });
81 |
82 | }
83 |
84 | private void closeQrWindow() {
85 | qrCodeFrame.dispose();
86 | }
87 |
88 | public WechatMeta getMeta() {
89 | return meta;
90 | }
91 |
92 | }
93 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/bean/BaseRequest.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.bean;
2 |
3 | public class BaseRequest {
4 |
5 | private String Uin;
6 | private String Sid = "";
7 | private String Skey = "";
8 | private String DeviceID = "";
9 |
10 | public String getUin() {
11 | return Uin;
12 | }
13 |
14 | public String getSid() {
15 | return Sid;
16 | }
17 |
18 | public String getSkey() {
19 | return Skey;
20 | }
21 |
22 | public String getDeviceID() {
23 | return DeviceID;
24 | }
25 |
26 | public void setUin(String uin) {
27 | Uin = uin;
28 | }
29 |
30 | public void setSid(String sid) {
31 | Sid = sid;
32 | }
33 |
34 | public void setSkey(String skey) {
35 | Skey = skey;
36 | }
37 |
38 | public void setDeviceID(String deviceID) {
39 | DeviceID = deviceID;
40 | }
41 |
42 | }
43 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/bean/ChatRoom.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.bean;
2 |
3 | import java.util.List;
4 |
5 | import com.blade.kit.json.JSONObject;
6 |
7 | public class ChatRoom {
8 |
9 | private int Uin;
10 | private String UserName;
11 | private String NickName;
12 | private String HeadImgUrl;
13 | private int ContactFlag;
14 | private int MemberCount;
15 | private List MemberList;
16 |
17 | public ChatRoom() {
18 | }
19 |
20 | public static ChatRoom parseFromJSON(JSONObject data) {
21 | ChatRoom chatroom = new ChatRoom();
22 | chatroom.Uin = data.getInt("Uin");
23 | chatroom.UserName = data.getString("UserName");
24 | chatroom.NickName = data.getString("NickName");
25 | chatroom.HeadImgUrl = data.getString("HeadImgUrl");
26 | chatroom.ContactFlag = data.getInt("ContactFlag");
27 | chatroom.MemberCount = data.getInt("MemberCount");
28 | return chatroom;
29 | }
30 |
31 | public ChatRoom(int uin, String userName, String nickName, String headImgUrl, int contactFlag, int memberCount) {
32 | super();
33 | Uin = uin;
34 | UserName = userName;
35 | NickName = nickName;
36 | HeadImgUrl = headImgUrl;
37 | ContactFlag = contactFlag;
38 | MemberCount = memberCount;
39 | }
40 |
41 | public int getUin() {
42 | return Uin;
43 | }
44 |
45 | public String getUserName() {
46 | return UserName;
47 | }
48 |
49 | public String getNickName() {
50 | return NickName;
51 | }
52 |
53 | public String getHeadImgUrl() {
54 | return HeadImgUrl;
55 | }
56 |
57 | public int getContactFlag() {
58 | return ContactFlag;
59 | }
60 |
61 | public int getMemberCount() {
62 | return MemberCount;
63 | }
64 |
65 | public List getMemberList() {
66 | return MemberList;
67 | }
68 |
69 | public void setUin(int uin) {
70 | Uin = uin;
71 | }
72 |
73 | public void setUserName(String userName) {
74 | UserName = userName;
75 | }
76 |
77 | public void setNickName(String nickName) {
78 | NickName = nickName;
79 | }
80 |
81 | public void setHeadImgUrl(String headImgUrl) {
82 | HeadImgUrl = headImgUrl;
83 | }
84 |
85 | public void setContactFlag(int contactFlag) {
86 | ContactFlag = contactFlag;
87 | }
88 |
89 | public void setMemberCount(int memberCount) {
90 | MemberCount = memberCount;
91 | }
92 |
93 | public void setMemberList(List memberList) {
94 | MemberList = memberList;
95 | }
96 |
97 | }
98 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/bean/ChatRoomMember.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.bean;
2 |
3 | import com.blade.kit.json.JSONObject;
4 |
5 | public class ChatRoomMember {
6 |
7 | private Integer Uin;
8 | private String UserName;
9 | private String NickName;
10 | private String AttrStatus;
11 | private String PYInitial;
12 | private String PYQuanPin;
13 | private String RemarkPYInitial;
14 | private String RemarkPYQuanPin;
15 | private Integer MemberStatus; // 0
16 | private String DisplayName;
17 | private String KeyWord;
18 |
19 | public ChatRoomMember() {
20 | }
21 |
22 | public ChatRoomMember(Integer uin, String userName, String nickName, String attrStatus, String pYInitial, String pYQuanPin, String remarkPYInitial,
23 | String remarkPYQuanPin, Integer memberStatus, String displayName, String keyWord) {
24 | this.Uin = uin;
25 | this.UserName = userName;
26 | this.NickName = nickName;
27 | this.AttrStatus = attrStatus;
28 | this.PYInitial = pYInitial;
29 | this.PYQuanPin = pYQuanPin;
30 | this.RemarkPYInitial = remarkPYInitial;
31 | this.RemarkPYQuanPin = remarkPYQuanPin;
32 | this.MemberStatus = memberStatus;
33 | this.DisplayName = displayName;
34 | this.KeyWord = keyWord;
35 | }
36 |
37 | public ChatRoomMember(JSONObject item) {
38 | this.Uin = item.getInt("Uin");
39 | this.UserName = item.getString("UserName");
40 | this.NickName = item.getString("NickName");
41 | this.AttrStatus = item.get("AttrStatus").toString();
42 | this.PYInitial = item.getString("PYInitial");
43 | this.PYQuanPin = item.getString("PYQuanPin");
44 | this.RemarkPYInitial = item.getString("RemarkPYInitial");
45 | this.RemarkPYQuanPin = item.getString("RemarkPYQuanPin");
46 | this.MemberStatus = item.getInt("MemberStatus");
47 | this.DisplayName = item.getString("DisplayName");
48 | this.KeyWord = item.getString("KeyWord");
49 | }
50 |
51 | public Integer getUin() {
52 | return Uin;
53 | }
54 |
55 | public String getUserName() {
56 | return UserName;
57 | }
58 |
59 | public String getNickName() {
60 | return NickName;
61 | }
62 |
63 | public String getAttrStatus() {
64 | return AttrStatus;
65 | }
66 |
67 | public String getPYInitial() {
68 | return PYInitial;
69 | }
70 |
71 | public String getPYQuanPin() {
72 | return PYQuanPin;
73 | }
74 |
75 | public String getRemarkPYInitial() {
76 | return RemarkPYInitial;
77 | }
78 |
79 | public String getRemarkPYQuanPin() {
80 | return RemarkPYQuanPin;
81 | }
82 |
83 | public Integer getMemberStatus() {
84 | return MemberStatus;
85 | }
86 |
87 | public String getDisplayName() {
88 | return DisplayName;
89 | }
90 |
91 | public String getKeyWord() {
92 | return KeyWord;
93 | }
94 |
95 | public void setUin(Integer uin) {
96 | Uin = uin;
97 | }
98 |
99 | public void setUserName(String userName) {
100 | UserName = userName;
101 | }
102 |
103 | public void setNickName(String nickName) {
104 | NickName = nickName;
105 | }
106 |
107 | public void setAttrStatus(String attrStatus) {
108 | AttrStatus = attrStatus;
109 | }
110 |
111 | public void setPYInitial(String pYInitial) {
112 | PYInitial = pYInitial;
113 | }
114 |
115 | public void setPYQuanPin(String pYQuanPin) {
116 | PYQuanPin = pYQuanPin;
117 | }
118 |
119 | public void setRemarkPYInitial(String remarkPYInitial) {
120 | RemarkPYInitial = remarkPYInitial;
121 | }
122 |
123 | public void setRemarkPYQuanPin(String remarkPYQuanPin) {
124 | RemarkPYQuanPin = remarkPYQuanPin;
125 | }
126 |
127 | public void setMemberStatus(Integer memberStatus) {
128 | MemberStatus = memberStatus;
129 | }
130 |
131 | public void setDisplayName(String displayName) {
132 | DisplayName = displayName;
133 | }
134 |
135 | public void setKeyWord(String keyWord) {
136 | KeyWord = keyWord;
137 | }
138 |
139 | @Override
140 | public String toString() {
141 | return "GroupMember [Uin=" + Uin + ", UserName=" + UserName + ", NickName=" + NickName + ", AttrStatus=" + AttrStatus + ", PYInitial="
142 | + PYInitial + ", PYQuanPin=" + PYQuanPin + ", RemarkPYInitial=" + RemarkPYInitial + ", RemarkPYQuanPin=" + RemarkPYQuanPin
143 | + ", MemberStatus=" + MemberStatus + ", DisplayName=" + DisplayName + ", KeyWord=" + KeyWord + "]";
144 | }
145 |
146 | }
147 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/bean/ContactUser.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.bean;
2 |
3 | import java.util.List;
4 |
5 | /**
6 | * 会话用户,包括 普通用户,群,公众号,服务号
7 | *
8 | * @author hexia
9 | *
10 | */
11 | public class ContactUser {
12 |
13 | public static final int CONTACT_FLAG_OF_FILE_HELPER = 1;
14 | public static final int CONTACT_FLAG_OF_GROUP = 3;// 群
15 | public static final int CONTACT_FLAG_OF_USER = 3;// 普通用户
16 |
17 | /****** 如果该值为0 ****/
18 | private int Uin;
19 | /****** 用户惟一标识,例如:@84a60bd0094062b1ff98bbbd195035d2 ****/
20 | private String UserName;
21 | /***** 用户昵称:例如eno ******/
22 | private String NickName;
23 | /***** 头像 **/
24 | private String HeadImgUrl;
25 | /****** 未知,一般为1 ****/
26 | private int ContactFlag; //1-好友, 2-群组, 3-公众号
27 | /*** 成员数,如果是群,该值应该大于0,如果是用户,该值为0 ***/
28 | private int MemberCount;
29 | /**** 群成员列表 ***/
30 | private List MemberList;
31 | /*** 未知 **/
32 | private String RemarkName;
33 | /****** 一般为0 **/
34 | private int HideInputBarFlag;
35 | /***** 性别 *****/
36 | private int Sex;
37 | /*** 签名? **/
38 | private String Signature;
39 | /***********/
40 | private int VerifyFlag;
41 | /************/
42 | private int OwnerUin;
43 | private String PYInitial;
44 |
45 | private String PYQuanPin;
46 |
47 | private String RemarkPYInitial;
48 | private String RemarkPYQuanPin;
49 | private int StarFriend;
50 | private int AppAccountFlag;
51 | private int Statues;
52 | private int AttrStatus;
53 | private String Province;
54 | private String City;
55 | private String Alias;
56 | private int SnsFlag;
57 | private int UniFriend;
58 | private String DisplayName;
59 | private Integer ChatRoomId;
60 | private String KeyWord;
61 | private String EncryChatRoomId;
62 | /***** 是否本人:0:否,1:是 *****/
63 | private Integer IsOwner;
64 |
65 | public ContactUser() {
66 | }
67 |
68 | public ContactUser(String userName, String nickName, int memberCount, List memberList) {
69 | UserName = userName;
70 | NickName = nickName;
71 | MemberCount = memberCount;
72 | MemberList = memberList;
73 | }
74 |
75 | public int getUin() {
76 | return Uin;
77 | }
78 |
79 | public String getUserName() {
80 | return UserName;
81 | }
82 |
83 | public String getNickName() {
84 | return NickName;
85 | }
86 |
87 | public String getHeadImgUrl() {
88 | return HeadImgUrl;
89 | }
90 |
91 | public int getContactFlag() {
92 | return ContactFlag;
93 | }
94 |
95 | public int getMemberCount() {
96 | return MemberCount;
97 | }
98 |
99 | public String getRemarkName() {
100 | return RemarkName;
101 | }
102 |
103 | public int getHideInputBarFlag() {
104 | return HideInputBarFlag;
105 | }
106 |
107 | public int getSex() {
108 | return Sex;
109 | }
110 |
111 | public String getSignature() {
112 | return Signature;
113 | }
114 |
115 | public int getVerifyFlag() {
116 | return VerifyFlag;
117 | }
118 |
119 | public int getOwnerUin() {
120 | return OwnerUin;
121 | }
122 |
123 | public String getPYInitial() {
124 | return PYInitial;
125 | }
126 |
127 | public String getPYQuanPin() {
128 | return PYQuanPin;
129 | }
130 |
131 | public String getRemarkPYInitial() {
132 | return RemarkPYInitial;
133 | }
134 |
135 | public String getRemarkPYQuanPin() {
136 | return RemarkPYQuanPin;
137 | }
138 |
139 | public int getStarFriend() {
140 | return StarFriend;
141 | }
142 |
143 | public int getAppAccountFlag() {
144 | return AppAccountFlag;
145 | }
146 |
147 | public int getStatues() {
148 | return Statues;
149 | }
150 |
151 | public int getAttrStatus() {
152 | return AttrStatus;
153 | }
154 |
155 | public String getProvince() {
156 | return Province;
157 | }
158 |
159 | public String getCity() {
160 | return City;
161 | }
162 |
163 | public String getAlias() {
164 | return Alias;
165 | }
166 |
167 | public int getSnsFlag() {
168 | return SnsFlag;
169 | }
170 |
171 | public int getUniFriend() {
172 | return UniFriend;
173 | }
174 |
175 | public String getDisplayName() {
176 | return DisplayName;
177 | }
178 |
179 | public Integer getChatRoomId() {
180 | return ChatRoomId;
181 | }
182 |
183 | public String getKeyWord() {
184 | return KeyWord;
185 | }
186 |
187 | public String getEncryChatRoomId() {
188 | return EncryChatRoomId;
189 | }
190 |
191 | public Integer getIsOwner() {
192 | return IsOwner;
193 | }
194 |
195 | public void setUin(int uin) {
196 | Uin = uin;
197 | }
198 |
199 | public void setUserName(String userName) {
200 | UserName = userName;
201 | }
202 |
203 | public void setNickName(String nickName) {
204 | NickName = nickName;
205 | }
206 |
207 | public void setHeadImgUrl(String headImgUrl) {
208 | HeadImgUrl = headImgUrl;
209 | }
210 |
211 | public void setContactFlag(int contactFlag) {
212 | ContactFlag = contactFlag;
213 | }
214 |
215 | public void setMemberCount(int memberCount) {
216 | MemberCount = memberCount;
217 | }
218 |
219 | public void setRemarkName(String remarkName) {
220 | RemarkName = remarkName;
221 | }
222 |
223 | public void setHideInputBarFlag(int hideInputBarFlag) {
224 | HideInputBarFlag = hideInputBarFlag;
225 | }
226 |
227 | public void setSex(int sex) {
228 | Sex = sex;
229 | }
230 |
231 | public void setSignature(String signature) {
232 | Signature = signature;
233 | }
234 |
235 | public void setVerifyFlag(int verifyFlag) {
236 | VerifyFlag = verifyFlag;
237 | }
238 |
239 | public void setOwnerUin(int ownerUin) {
240 | OwnerUin = ownerUin;
241 | }
242 |
243 | public void setPYInitial(String pYInitial) {
244 | PYInitial = pYInitial;
245 | }
246 |
247 | public void setPYQuanPin(String pYQuanPin) {
248 | PYQuanPin = pYQuanPin;
249 | }
250 |
251 | public void setRemarkPYInitial(String remarkPYInitial) {
252 | RemarkPYInitial = remarkPYInitial;
253 | }
254 |
255 | public void setRemarkPYQuanPin(String remarkPYQuanPin) {
256 | RemarkPYQuanPin = remarkPYQuanPin;
257 | }
258 |
259 | public void setStarFriend(int starFriend) {
260 | StarFriend = starFriend;
261 | }
262 |
263 | public void setAppAccountFlag(int appAccountFlag) {
264 | AppAccountFlag = appAccountFlag;
265 | }
266 |
267 | public void setStatues(int statues) {
268 | Statues = statues;
269 | }
270 |
271 | public void setAttrStatus(int attrStatus) {
272 | AttrStatus = attrStatus;
273 | }
274 |
275 | public void setProvince(String province) {
276 | Province = province;
277 | }
278 |
279 | public void setCity(String city) {
280 | City = city;
281 | }
282 |
283 | public void setAlias(String alias) {
284 | Alias = alias;
285 | }
286 |
287 | public void setSnsFlag(int snsFlag) {
288 | SnsFlag = snsFlag;
289 | }
290 |
291 | public void setUniFriend(int uniFriend) {
292 | UniFriend = uniFriend;
293 | }
294 |
295 | public void setDisplayName(String displayName) {
296 | DisplayName = displayName;
297 | }
298 |
299 | public void setChatRoomId(Integer chatRoomId) {
300 | ChatRoomId = chatRoomId;
301 | }
302 |
303 | public void setKeyWord(String keyWord) {
304 | KeyWord = keyWord;
305 | }
306 |
307 | public void setEncryChatRoomId(String encryChatRoomId) {
308 | EncryChatRoomId = encryChatRoomId;
309 | }
310 |
311 | public void setIsOwner(Integer isOwner) {
312 | IsOwner = isOwner;
313 | }
314 |
315 | public List getMemberList() {
316 | return MemberList;
317 | }
318 |
319 | public void setMemberList(List memberList) {
320 | MemberList = memberList;
321 | }
322 |
323 | }
324 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/bean/GroupMember.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.bean;
2 |
3 | import com.blade.kit.json.JSONObject;
4 |
5 | public class GroupMember {
6 |
7 | private Integer Uin;
8 | private String UserName;
9 | private String NickName;
10 | private Integer AttrStatus;
11 | private String PYInitial;
12 | private String PYQuanPin;
13 | private String RemarkPYInitial;
14 | private String RemarkPYQuanPin;
15 | private Integer MemberStatus; // 0
16 | private String DisplayName;
17 | private String KeyWord;
18 |
19 | public GroupMember() {
20 | }
21 |
22 | public GroupMember(Integer uin, String userName, String nickName, Integer attrStatus, String pYInitial, String pYQuanPin, String remarkPYInitial,
23 | String remarkPYQuanPin, Integer memberStatus, String displayName, String keyWord) {
24 | this.Uin = uin;
25 | this.UserName = userName;
26 | this.NickName = nickName;
27 | this.AttrStatus = attrStatus;
28 | this.PYInitial = pYInitial;
29 | this.PYQuanPin = pYQuanPin;
30 | this.RemarkPYInitial = remarkPYInitial;
31 | this.RemarkPYQuanPin = remarkPYQuanPin;
32 | this.MemberStatus = memberStatus;
33 | this.DisplayName = displayName;
34 | this.KeyWord = keyWord;
35 | }
36 |
37 | public GroupMember(JSONObject item) {
38 | this.Uin = item.getInt("Uin");
39 | this.UserName = item.getString("UserName");
40 | this.NickName = item.getString("NickName");
41 | this.AttrStatus = item.getInt("AttrStatus");
42 | this.PYInitial = item.getString("PYInitial");
43 | this.PYQuanPin = item.getString("PYQuanPin");
44 | this.RemarkPYInitial = item.getString("RemarkPYInitial");
45 | this.RemarkPYQuanPin = item.getString("RemarkPYQuanPin");
46 | this.MemberStatus = item.getInt("MemberStatus");
47 | this.DisplayName = item.getString("DisplayName");
48 | this.KeyWord = item.getString("KeyWord");
49 | }
50 |
51 | public Integer getUin() {
52 | return Uin;
53 | }
54 |
55 | public String getUserName() {
56 | return UserName;
57 | }
58 |
59 | public String getNickName() {
60 | return NickName;
61 | }
62 |
63 | public Integer getAttrStatus() {
64 | return AttrStatus;
65 | }
66 |
67 | public String getPYInitial() {
68 | return PYInitial;
69 | }
70 |
71 | public String getPYQuanPin() {
72 | return PYQuanPin;
73 | }
74 |
75 | public String getRemarkPYInitial() {
76 | return RemarkPYInitial;
77 | }
78 |
79 | public String getRemarkPYQuanPin() {
80 | return RemarkPYQuanPin;
81 | }
82 |
83 | public Integer getMemberStatus() {
84 | return MemberStatus;
85 | }
86 |
87 | public String getDisplayName() {
88 | return DisplayName;
89 | }
90 |
91 | public String getKeyWord() {
92 | return KeyWord;
93 | }
94 |
95 | public void setUin(Integer uin) {
96 | Uin = uin;
97 | }
98 |
99 | public void setUserName(String userName) {
100 | UserName = userName;
101 | }
102 |
103 | public void setNickName(String nickName) {
104 | NickName = nickName;
105 | }
106 |
107 | public void setAttrStatus(Integer attrStatus) {
108 | AttrStatus = attrStatus;
109 | }
110 |
111 | public void setPYInitial(String pYInitial) {
112 | PYInitial = pYInitial;
113 | }
114 |
115 | public void setPYQuanPin(String pYQuanPin) {
116 | PYQuanPin = pYQuanPin;
117 | }
118 |
119 | public void setRemarkPYInitial(String remarkPYInitial) {
120 | RemarkPYInitial = remarkPYInitial;
121 | }
122 |
123 | public void setRemarkPYQuanPin(String remarkPYQuanPin) {
124 | RemarkPYQuanPin = remarkPYQuanPin;
125 | }
126 |
127 | public void setMemberStatus(Integer memberStatus) {
128 | MemberStatus = memberStatus;
129 | }
130 |
131 | public void setDisplayName(String displayName) {
132 | DisplayName = displayName;
133 | }
134 |
135 | public void setKeyWord(String keyWord) {
136 | KeyWord = keyWord;
137 | }
138 |
139 | @Override
140 | public String toString() {
141 | return "GroupMember [Uin=" + Uin + ", UserName=" + UserName + ", NickName=" + NickName + ", AttrStatus=" + AttrStatus + ", PYInitial="
142 | + PYInitial + ", PYQuanPin=" + PYQuanPin + ", RemarkPYInitial=" + RemarkPYInitial + ", RemarkPYQuanPin=" + RemarkPYQuanPin
143 | + ", MemberStatus=" + MemberStatus + ", DisplayName=" + DisplayName + ", KeyWord=" + KeyWord + "]";
144 | }
145 |
146 | }
147 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/bean/Msg.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.bean;
2 |
3 | public class Msg {
4 |
5 | private String msgId;
6 | private String fromUserName;
7 | private String toUserName;
8 | private Integer msgType;
9 | private String content;
10 | private Integer status;
11 | private Integer imgStatus;
12 | private Integer createTime;
13 | private Integer voiceLength;
14 | private Integer playLength;
15 | private String fileName;
16 | private String fileSize;
17 | private String mediaId;
18 | private String url;
19 | private Integer appMsgType;
20 | private Integer statusNotifyCode;
21 | private String statusNotifyUserName;
22 | private String recommendInfo;
23 |
24 | public String getMsgId() {
25 | return msgId;
26 | }
27 |
28 | public String getFromUserName() {
29 | return fromUserName;
30 | }
31 |
32 | public String getToUserName() {
33 | return toUserName;
34 | }
35 |
36 | public Integer getMsgType() {
37 | return msgType;
38 | }
39 |
40 | public String getContent() {
41 | return content;
42 | }
43 |
44 | public Integer getStatus() {
45 | return status;
46 | }
47 |
48 | public Integer getImgStatus() {
49 | return imgStatus;
50 | }
51 |
52 | public Integer getCreateTime() {
53 | return createTime;
54 | }
55 |
56 | public Integer getVoiceLength() {
57 | return voiceLength;
58 | }
59 |
60 | public Integer getPlayLength() {
61 | return playLength;
62 | }
63 |
64 | public String getFileName() {
65 | return fileName;
66 | }
67 |
68 | public String getFileSize() {
69 | return fileSize;
70 | }
71 |
72 | public String getMediaId() {
73 | return mediaId;
74 | }
75 |
76 | public String getUrl() {
77 | return url;
78 | }
79 |
80 | public Integer getAppMsgType() {
81 | return appMsgType;
82 | }
83 |
84 | public Integer getStatusNotifyCode() {
85 | return statusNotifyCode;
86 | }
87 |
88 | public String getStatusNotifyUserName() {
89 | return statusNotifyUserName;
90 | }
91 |
92 | public String getRecommendInfo() {
93 | return recommendInfo;
94 | }
95 |
96 | public void setMsgId(String msgId) {
97 | this.msgId = msgId;
98 | }
99 |
100 | public void setFromUserName(String fromUserName) {
101 | this.fromUserName = fromUserName;
102 | }
103 |
104 | public void setToUserName(String toUserName) {
105 | this.toUserName = toUserName;
106 | }
107 |
108 | public void setMsgType(Integer msgType) {
109 | this.msgType = msgType;
110 | }
111 |
112 | public void setContent(String content) {
113 | this.content = content;
114 | }
115 |
116 | public void setStatus(Integer status) {
117 | this.status = status;
118 | }
119 |
120 | public void setImgStatus(Integer imgStatus) {
121 | this.imgStatus = imgStatus;
122 | }
123 |
124 | public void setCreateTime(Integer createTime) {
125 | this.createTime = createTime;
126 | }
127 |
128 | public void setVoiceLength(Integer voiceLength) {
129 | this.voiceLength = voiceLength;
130 | }
131 |
132 | public void setPlayLength(Integer playLength) {
133 | this.playLength = playLength;
134 | }
135 |
136 | public void setFileName(String fileName) {
137 | this.fileName = fileName;
138 | }
139 |
140 | public void setFileSize(String fileSize) {
141 | this.fileSize = fileSize;
142 | }
143 |
144 | public void setMediaId(String mediaId) {
145 | this.mediaId = mediaId;
146 | }
147 |
148 | public void setUrl(String url) {
149 | this.url = url;
150 | }
151 |
152 | public void setAppMsgType(Integer appMsgType) {
153 | this.appMsgType = appMsgType;
154 | }
155 |
156 | public void setStatusNotifyCode(Integer statusNotifyCode) {
157 | this.statusNotifyCode = statusNotifyCode;
158 | }
159 |
160 | public void setStatusNotifyUserName(String statusNotifyUserName) {
161 | this.statusNotifyUserName = statusNotifyUserName;
162 | }
163 |
164 | public void setRecommendInfo(String recommendInfo) {
165 | this.recommendInfo = recommendInfo;
166 | }
167 |
168 | // {"UserName":"","NickName":"","QQNum":0,"Province":"","City":"","Content":"","Signature":"","Alias":"","Scene":0,"VerifyFlag":0,"AttrStatus":0,"Sex":0,"Ticket":"","OpCode":0},
169 | // "ForwardFlag":0,"AppInfo":{"AppID":"","Type":0},"HasProductId":0,"Ticket":"","ImgHeight":0,"ImgWidth":0,"SubMsgType":0,"NewMsgId":2692073074812973378,"OriContent":""}
170 |
171 | }
172 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/config/Constant.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.config;
2 |
3 | import java.util.Arrays;
4 | import java.util.List;
5 |
6 | import com.iyuexian.wechat4j.util.PropertyReader;
7 |
8 | public class Constant {
9 |
10 | // 特殊用户 须过滤
11 | public static final List FILTER_USERS = Arrays.asList("newsapp", "fmessage", "filehelper", "weibo", "qqmail", "fmessage", "tmessage",
12 | "qmessage", "qqsync", "floatbottle", "lbsapp", "shakeapp", "medianote", "qqfriend", "readerapp", "blogapp", "facebookapp", "masssendapp",
13 | "meishiapp", "feedsapp", "voip", "blogappweixin", "weixin", "brandsessionholder", "weixinreminder", "wxid_novlwrv3lqwv11",
14 | "gh_22b87fa7cb3c", "officialaccounts", "notification_messages", "wxid_novlwrv3lqwv11", "gh_22b87fa7cb3c", "wxitil",
15 | "userexperience_alarm", "notification_messages");
16 |
17 | public static final String[] SYNC_HOST = { "webpush.weixin.qq.com", "webpush2.weixin.qq.com", "webpush.wechat.com", "webpush1.wechat.com",
18 | "webpush2.wechat.com" };
19 |
20 | public static final String QINIU_AK = "qiniu_ak";
21 | /**** 七牛access secret ***/
22 | public static final String QINIU_SK = "qiniu_sk";
23 | /**** 图片域名地址 ***/
24 | public static final String QIUNIU_IMG_URL = "qiuniu_img_url";
25 | /****** 视频域名地址 *****/
26 | public static final String QIUNIU_VDEO_URL = "qiuniu_video_url";
27 | /**** 七牛图片bucket名称 ****/
28 | public static final String QINIU_BUCKET_IMAGE0 = "qiniu_bucket_image0";
29 | /**** 七牛视频bucket名称 ****/
30 | public static final String QINIU_BUCKET_VIDEO = "qiniu_bucket_video";
31 |
32 |
33 | /***** 是否开启自动回复 ******/
34 | public static final boolean AUTO_REPLY = false;
35 | /***** 是否打印成员信息 ****/
36 | public static final boolean PRINT_MEMBER_INFO = false;
37 | /****** 是否开启自动添加好友 ******/
38 | public static final boolean ADD_FRIEND = false;
39 |
40 | public static final String HTTP_OK = "200";
41 | public static final String BASE_URL = "https://webpush2.weixin.qq.com/cgi-bin/mmwebwx-bin";
42 | public static final String JS_LOGIN_URL = "https://login.weixin.qq.com/jslogin";
43 | public static final String QRCODE_URL = "https://login.weixin.qq.com/qrcode/";
44 | public static final String USER_AGENT = "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/57.0.2987.133 Safari/537.36";
45 | public static PropertyReader configReader = PropertyReader.load("config.properties");
46 |
47 | }
48 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/config/Enums.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.config;
2 |
3 | public class Enums {
4 | public static enum OS {
5 | WINDOWS, LINUX, DARWIN, MAC, OTHER
6 | }
7 |
8 | public enum FileType {
9 | Picture, Video, File
10 | }
11 |
12 | public static enum MsgType {
13 | MEDIA(-1, "媒体消息", "ebwxgetvideo"),
14 |
15 | TXT(1, "文本消息", ""),
16 |
17 | PICTURE(3, "图片消息", "webwxgetmsgimg"),
18 |
19 | VOICE(34, "语音消息", "webwxgetvoice"),
20 |
21 | FRIEND_VERIFY(37, "好友确认消息", ""),
22 |
23 | POSSIBLEFRIEND_MSG(40, "POSSIBLEFRIEND_MSG", ""),
24 |
25 | SHARE_MP(42, "共享名片", ""),
26 |
27 | VIDEO(43, "视频消息", "webwxgetvideo"),
28 |
29 | ANIMATION(47, "动画消息", ""),
30 |
31 | LOCATION(48, "位置消息", ""),
32 |
33 | SHARE_LINK(49, "分享链接", ""),
34 |
35 | VOIPMSG(50, "VOIPMSG", ""),
36 |
37 | WX_INIT(51, "微信初始化消息", ""),
38 |
39 | VOIPNOTIFY(52, "VOIPNOTIFY", ""),
40 |
41 | VOIPINVITE(53, "VOIPINVITE", ""),
42 |
43 | SMALL_VIDEO(62, "小视频", "webwxgetvideo"),
44 |
45 | SYSNOTICE(9999, "SYSNOTICE", ""),
46 |
47 | SYSTEM(10000, "", "系统消息E"),
48 |
49 | MSG_ROLLBACK(10002, "撤回消息", "");
50 |
51 | private int type;
52 | private String name;
53 | private String downloadPath;
54 |
55 | private MsgType(int type, String name, String downloadPath) {
56 | this.type = type;
57 | this.downloadPath = downloadPath;
58 | }
59 |
60 | public int getType() {
61 | return type;
62 | }
63 |
64 | public String getName() {
65 | return name;
66 | }
67 |
68 | public String getDownloadPath() {
69 | return downloadPath;
70 | }
71 |
72 | public static MsgType getType(int type) {
73 | MsgType[] types = MsgType.values();
74 | for (MsgType msgType : types) {
75 | if (msgType.getType() == type) {
76 | return msgType;
77 | }
78 | }
79 | return null;
80 | }
81 |
82 | }
83 | }
84 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/config/MsgType.java:
--------------------------------------------------------------------------------
1 | //package com.iyuexian.wechat4j.config;
2 | //
3 | //public class MsgType {
4 | //
5 | // public static final int MSGTYPE_TEXT = 1; // 文本消息类型
6 | // public static final int MSGTYPE_IMAGE = 3; // 图片消息
7 | // public static final int MSGTYPE_VOICE = 34; // 语音消息
8 | // public static final int MSGTYPE_VIDEO = 43; // 小视频消息
9 | // public static final int MSGTYPE_MICROVIDEO = 62;
10 | // public static final int MSGTYPE_EMOTICON = 47;
11 | // public static final int MSGTYPE_APP = 49;
12 | // public static final int MSGTYPE_VOIPMSG = 50;
13 | // public static final int MSGTYPE_VOIPNOTIFY = 52;
14 | // public static final int MSGTYPE_VOIPINVITE = 53;
15 | // public static final int MSGTYPE_LOCATION = 48;
16 | // public static final int MSGTYPE_STATUSNOTIFY = 51;
17 | // public static final int MSGTYPE_SYSNOTICE = 9999;
18 | // public static final int MSGTYPE_POSSIBLEFRIEND_MSG = 40;
19 | // public static final int MSGTYPE_VERIFYMSG = 37;
20 | // public static final int MSGTYPE_SHARECARD = 42;
21 | // public static final int MSGTYPE_SYS = 10000;
22 | // public static final int MSGTYPE_RECALLED = 10002;
23 | //
24 | // // 文本信息
25 | // public static String TEXT = "Text";
26 | // // 图片信息
27 | // public static String PIC = "Pic";
28 | // // 语音信息
29 | // public static String VOICE = "Voice";
30 | // // 小视频消息
31 | // public static String VIEDO = "Video";
32 | // // name card 明片消息
33 | // public static String NAMECARD = "NameCard";
34 | //}
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/core/WechatApiUtil.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.core;
2 |
3 | import java.io.File;
4 | import java.text.MessageFormat;
5 | import java.util.Date;
6 | import java.util.List;
7 |
8 | import org.slf4j.Logger;
9 | import org.slf4j.LoggerFactory;
10 |
11 | import com.blade.kit.DateKit;
12 | import com.blade.kit.StringKit;
13 | import com.blade.kit.http.HttpRequest;
14 | import com.blade.kit.json.JSONArray;
15 | import com.blade.kit.json.JSONKit;
16 | import com.blade.kit.json.JSONObject;
17 | import com.iyuexian.wechat4j.config.Constant;
18 | import com.iyuexian.wechat4j.exception.WechatException;
19 | import com.iyuexian.wechat4j.plugin.Storage;
20 | import com.iyuexian.wechat4j.util.CookieUtil;
21 | import com.iyuexian.wechat4j.util.HttpClient;
22 | import com.iyuexian.wechat4j.util.Matchers;
23 |
24 | public class WechatApiUtil {
25 | static final Logger LOGGER = LoggerFactory.getLogger(WechatApiUtil.class);
26 |
27 | public static String getUUID() throws WechatException {
28 | HttpRequest request = HttpRequest.get(Constant.JS_LOGIN_URL, true, "appid", "wx782c26e4c19acffb", "fun", "new", "lang", "zh_CN", "_",
29 | DateKit.getCurrentUnixTime());
30 | String res = request.body();
31 | request.disconnect();
32 | if (StringKit.isBlank(res)) {
33 | throw new WechatException("获取UUID失败");
34 | }
35 | String code = Matchers.match("window.QRLogin.code = (\\d+);", res);
36 | if (null == code || !code.equals("200")) {
37 | throw new WechatException("获取UUID失败," + code);
38 | }
39 | String uuid = Matchers.match("window.QRLogin.uuid = \"(.*)\";", res);
40 | return uuid;
41 | }
42 |
43 | public static String getQrCode(String uuid) throws WechatException {
44 |
45 | if (StringKit.isBlank(uuid)) {
46 | throw new WechatException("请先获取UUID");
47 | }
48 | String url = Constant.QRCODE_URL + uuid;
49 | String folder=System.getProperty("java.io.tmpdir");
50 | final File output = new File(folder+File.separator+"wechat4j_qrcode.jpg");
51 | HttpRequest.post(url, true, "t", "webwx", "_", DateKit.getCurrentUnixTime()).receive(output);
52 |
53 | if (null == output || !output.exists() || !output.isFile()) {
54 | throw new WechatException("获取登陆二维码失败");
55 | }
56 | return output.getPath();
57 |
58 | }
59 |
60 | public static String waitLogin(int tip, String uuid) {
61 | String url = "https://login.weixin.qq.com/cgi-bin/mmwebwx-bin/login";
62 | HttpRequest request = HttpRequest.get(url, true, "tip", tip, "uuid", uuid, "_", DateKit.getCurrentUnixTime());
63 | LOGGER.warn("等待登陆");
64 | String res = request.body();
65 | request.disconnect();
66 | return res;
67 |
68 | }
69 |
70 | public static WechatMeta newWechatMeta(String waitloginRes) {
71 | String pm = Matchers.match("window.redirect_uri=\"(\\S+?)\";", waitloginRes);
72 | String redirectUrl = pm + "&fun=new";
73 | String baseUrl = redirectUrl.substring(0, redirectUrl.lastIndexOf("/"));
74 | WechatMeta meta = new WechatMeta();
75 | meta.setRedirect_uri(redirectUrl);
76 | meta.setBase_uri(baseUrl);
77 | meta.setLoginDate(new Date());
78 | return meta;
79 | }
80 |
81 | public static void login(WechatMeta meta) throws WechatException {
82 |
83 | if (StringKit.isBlank(meta.getRedirect_uri())) {
84 | throw new WechatException("redirect_url不能为空");
85 | }
86 |
87 | HttpRequest request = HttpRequest.get(meta.getRedirect_uri());
88 | String res = request.body();
89 | meta.setCookie(CookieUtil.getCookie(request));
90 | request.disconnect();
91 | if (StringKit.isBlank(res)) {
92 | throw new WechatException("登录失败");
93 | }
94 | meta.setSkey(Matchers.match("(\\S+)", res));
95 | meta.setWxsid(Matchers.match("(\\S+)", res));
96 | meta.setWxuin(Matchers.match("(\\S+)", res));
97 | meta.setPass_ticket(Matchers.match("(\\S+)", res));
98 |
99 | JSONObject baseRequest = new JSONObject();
100 | baseRequest.put("Uin", meta.getWxuin());
101 | baseRequest.put("Sid", meta.getWxsid());
102 | baseRequest.put("Skey", meta.getSkey());
103 | baseRequest.put("DeviceID", meta.getDeviceId());
104 | meta.setBaseRequest(baseRequest);
105 | }
106 |
107 | public static JSONObject wxInit(WechatMeta meta) throws WechatException {
108 | String url = meta.getBase_uri() + "/webwxinit?r=" + DateKit.getCurrentUnixTime() + "&lang=zh_CN";
109 | JSONObject body = new JSONObject();
110 | body.put("BaseRequest", meta.getBaseRequest());
111 | HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie())
112 | .send(body.toString());
113 | String res = request.body();
114 | request.disconnect();
115 |
116 | JSONObject jsonObject = null;
117 | if (StringKit.isBlank(res) || (jsonObject = JSONKit.parseObject(res)) == null) {
118 | throw new WechatException("微信初始化失败");
119 | }
120 |
121 | JSONObject BaseResponse = jsonObject.get("BaseResponse").asJSONObject();
122 | if (null == BaseResponse || BaseResponse.getInt("Ret", -1) != 0) {
123 | throw new WechatException("微信初始化失败," + BaseResponse);
124 | }
125 |
126 | meta.setSyncKey(jsonObject.get("SyncKey").asJSONObject());
127 | meta.setUser(jsonObject.get("User").asJSONObject());
128 |
129 | StringBuffer synckey = new StringBuffer();
130 | JSONArray list = meta.getSyncKey().get("List").asArray();
131 | for (int i = 0, len = list.size(); i < len; i++) {
132 | JSONObject item = list.get(i).asJSONObject();
133 | synckey.append("|" + item.getInt("Key", 0) + "_" + item.getInt("Val", 0));
134 | }
135 | meta.setSynckey(synckey.substring(1));
136 | return jsonObject;
137 | }
138 |
139 | public static void openStatusNotify(WechatMeta meta) throws WechatException {
140 | String url = meta.getBase_uri() + "/webwxstatusnotify?lang=zh_CN&pass_ticket=" + meta.getPass_ticket();
141 |
142 | JSONObject body = new JSONObject();
143 | body.put("BaseRequest", meta.getBaseRequest());
144 | body.put("Code", 3);
145 | body.put("FromUserName", meta.getUser().getString("UserName"));
146 | body.put("ToUserName", meta.getUser().getString("UserName"));
147 | body.put("ClientMsgId", DateKit.getCurrentUnixTime());
148 |
149 | HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie())
150 | .send(body.toString());
151 | String res = request.body();
152 | request.disconnect();
153 |
154 | if (StringKit.isBlank(res)) {
155 | throw new WechatException("状态通知开启失败");
156 | }
157 |
158 | JSONObject jsonObject = JSONKit.parseObject(res);
159 | JSONObject BaseResponse = jsonObject.get("BaseResponse").asJSONObject();
160 | if (null == BaseResponse || BaseResponse.getInt("Ret", -1) != 0) {
161 | throw new WechatException("状态通知开启失败");
162 | }
163 | LOGGER.debug("状态通知已开启");
164 | }
165 |
166 | public static int[] syncCheck(WechatMeta meta, String url) {
167 | int[] arr = new int[] { -1, -1 };
168 | try {
169 | url = url == null ? meta.getWebpush_url() + "/synccheck" : "https://" + url + "/cgi-bin/mmwebwx-bin/synccheck";
170 | JSONObject body = new JSONObject();
171 | body.put("BaseRequest", meta.getBaseRequest());
172 | HttpRequest request = HttpRequest
173 | .get(url, true, "r", DateKit.getCurrentUnixTime() + StringKit.getRandomNumber(5), "skey", meta.getSkey(), "uin", meta.getWxuin(),
174 | "sid", meta.getWxsid(), "deviceid", meta.getDeviceId(), "synckey", meta.getSynckey(), "_", System.currentTimeMillis())
175 | .header("Cookie", meta.getCookie());
176 | String res = request.body();
177 | request.disconnect();
178 | if (StringKit.isBlank(res)) {
179 | return arr;
180 | }
181 |
182 | String retcode = Matchers.match("retcode:\"(\\d+)\",", res);
183 | String selector = Matchers.match("selector:\"(\\d+)\"}", res);
184 | if (null != retcode && null != selector) {
185 | arr[0] = Integer.parseInt(retcode);
186 | arr[1] = Integer.parseInt(selector);
187 | return arr;
188 | }
189 | return arr;
190 | } catch (Exception ex) {
191 | return arr;
192 | }
193 | }
194 |
195 | public static int[] syncCheck(WechatMeta meta) throws WechatException {
196 | return syncCheck(meta, null);
197 | }
198 |
199 | public static void choiceSyncLine(WechatMeta meta) throws WechatException {
200 | boolean enabled = false;
201 | for (String syncUrl : Constant.SYNC_HOST) {
202 | int[] res = syncCheck(meta, syncUrl);
203 | if (res[0] == 0) {
204 | String url = "https://" + syncUrl + "/cgi-bin/mmwebwx-bin";
205 | meta.setWebpush_url(url);
206 | LOGGER.info("选择线路:[{}]", syncUrl);
207 | enabled = true;
208 | break;
209 | }
210 | }
211 | if (!enabled) {
212 | throw new WechatException("同步线路不通畅");
213 | }
214 | }
215 |
216 | public static JSONObject webwxsync(WechatMeta meta) throws WechatException {
217 | String url = meta.getBase_uri() + "/webwxsync?skey=" + meta.getSkey() + "&sid=" + meta.getWxsid();
218 |
219 | JSONObject body = new JSONObject();
220 | body.put("BaseRequest", meta.getBaseRequest());
221 | body.put("SyncKey", meta.getSyncKey());
222 | body.put("rr", DateKit.getCurrentUnixTime());
223 |
224 | HttpClient httpRequsetUtil = new HttpClient(meta);
225 | JSONObject jsonObject = httpRequsetUtil.postJSON(url, body);
226 | JSONObject BaseResponse = jsonObject.get("BaseResponse").asJSONObject();
227 | if (null != BaseResponse) {
228 | int ret = BaseResponse.getInt("Ret", -1);
229 | if (ret == 0) {
230 | meta.setSyncKey(jsonObject.get("SyncKey").asJSONObject());
231 | StringBuffer synckey = new StringBuffer();
232 | JSONArray list = meta.getSyncKey().get("List").asArray();
233 | for (int i = 0, len = list.size(); i < len; i++) {
234 | JSONObject item = list.get(i).asJSONObject();
235 | synckey.append("|" + item.getInt("Key", 0) + "_" + item.getInt("Val", 0));
236 | }
237 | meta.setSynckey(synckey.substring(1));
238 | return jsonObject;
239 | }
240 | }
241 | return null;
242 | }
243 |
244 | public static String webwxsendmsg(WechatMeta meta, String content, JSONObject to) {
245 | String url = meta.getBase_uri() + "/webwxsendmsg?lang=zh_CN&pass_ticket=" + meta.getPass_ticket();
246 | final JSONObject body = new JSONObject();
247 | String clientMsgId = DateKit.getCurrentUnixTime() + StringKit.getRandomNumber(5);
248 | JSONObject Msg = new JSONObject();
249 |
250 | Msg.put("Type", 1);
251 | Msg.put("Content", content);
252 | Msg.put("FromUserName", meta.getUser().getString("UserName"));
253 | Msg.put("ToUserName", to.get("UserName"));
254 | Msg.put("LocalID", clientMsgId);
255 | Msg.put("ClientMsgId", clientMsgId);
256 |
257 | body.put("BaseRequest", meta.getBaseRequest());
258 | body.put("Msg", Msg);
259 | final HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie());
260 | request.send(body.toString());
261 | String msgResult = request.body();
262 | request.disconnect();
263 | return msgResult;
264 |
265 | }
266 |
267 | /**
268 | * 添加好友
269 | *
270 | * @param userName
271 | * @param status
272 | * 2,default=2
273 | * @param verifyContent
274 | * @param autoUpdate
275 | */
276 | public static JSONObject addFriend(WechatMeta meta, String userName, String verifyContent) {
277 | String url = "{0}/webwxverifyuser?r={1}&pass_ticket={2}";
278 | url = MessageFormat.format(url, meta.getBase_uri(), DateKit.getCurrentUnixTime(), meta.getPass_ticket());
279 |
280 | JSONObject body = new JSONObject();
281 | body.put("BaseRequest", meta.getBaseRequest());
282 | body.put("Opcode", 2);
283 | body.put("VerifyUserListSize", 1);
284 | JSONArray VerifyUserList = new JSONArray();
285 | JSONObject verifyItem = new JSONObject();
286 | verifyItem.put("Value", userName);
287 | verifyItem.put("VerifyUserTicket", "");
288 | VerifyUserList.add(verifyItem);
289 | body.put("VerifyUserList", VerifyUserList);
290 | body.put("VerifyContent", verifyContent);
291 | body.put("SceneListCount", 1);
292 | JSONArray sceneList = new JSONArray();
293 | sceneList.add(33);
294 | body.put("SceneList", sceneList);
295 | body.put("skey", meta.getSkey());
296 |
297 | HttpClient httpRequsetUtil = new HttpClient(meta);
298 | JSONObject resp = httpRequsetUtil.postJSON(url, body);
299 | return resp;
300 |
301 | }
302 |
303 | /**
304 | * 获取通讯录列表
305 | */
306 | public static JSONArray getContactList(WechatMeta meta) {
307 | String url = meta.getBase_uri() + "/webwxgetcontact?&seq=0&pass_ticket=" + meta.getPass_ticket() + "&skey=" + meta.getSkey() + "&r="
308 | + DateKit.getCurrentUnixTime();
309 | JSONObject body = new JSONObject();
310 | body.put("BaseRequest", meta.getBaseRequest());
311 | HttpClient httpRequsetUtil = new HttpClient(meta);
312 | JSONObject response = httpRequsetUtil.postJSON(url, body);
313 | JSONArray memberList = response.get("MemberList").asArray();
314 | return memberList;
315 |
316 | }
317 |
318 | /***
319 | * 初始化群(群名称需要从最新联系人或通过录里筛选)
320 | *
321 | * @param meta
322 | * @param chatRommNames
323 | */
324 | public static void initLatestChatroom(WechatMeta meta, List chatRommNames) {
325 | JSONArray groupArray = new JSONArray();
326 | // for (String groupUserName :
327 | // Storage.instance().getLatestChatRoomUserNameList()) {
328 | for (String groupUserName : chatRommNames) {
329 | JSONObject groupItem = new JSONObject();
330 | groupItem.put("UserName", groupUserName);
331 | groupItem.put("ChatRoomId", "");
332 | groupArray.add(groupItem);
333 | }
334 | JSONArray latestChatRoomList = getMemberListByChatroom(meta, groupArray);
335 | Storage.instance().setLatestChatRoomList(latestChatRoomList);
336 |
337 | }
338 |
339 | /**
340 | * 获取取成员列表
341 | * @param meta
342 | * @param chatRoomList
343 | * @return
344 | */
345 | public static JSONArray getMemberListByChatroom(WechatMeta meta, JSONArray chatRoomList) {
346 | String url = meta.getBase_uri() + "/webwxbatchgetcontact?type=ex&r=" + DateKit.getCurrentUnixTime() + "&lang=zh_CN";
347 | JSONObject body = new JSONObject();
348 | body.put("BaseRequest", meta.getBaseRequest());
349 | body.put("Count", chatRoomList.size());
350 | body.put("List", chatRoomList);
351 | HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie())
352 | .send(body.toString());
353 | String res = request.body();
354 | request.disconnect();
355 | if (StringKit.isBlank(res)) {
356 | throw new WechatException("获取群成员列表失败");
357 | }
358 | JSONObject jsonObject = JSONKit.parseObject(res);
359 | JSONObject baseResponse = jsonObject.get("BaseResponse").asJSONObject();
360 | if (null == baseResponse || baseResponse.getInt("Ret", -1) != 0) {
361 | LOGGER.warn("获取群列表失败,{}", baseResponse);
362 | return null;
363 | }
364 | JSONArray memberList = jsonObject.get("ContactList").asArray();
365 | // LOGGER.info("获取群成员:{}", memberList);
366 | return memberList;
367 |
368 | }
369 | }
370 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/core/WechatMeta.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.core;
2 |
3 | import java.util.Date;
4 |
5 | import com.blade.kit.DateKit;
6 | import com.blade.kit.json.JSONObject;
7 | import com.iyuexian.wechat4j.config.Constant;
8 |
9 | public class WechatMeta {
10 |
11 | private String mobile;
12 | protected String base_uri, redirect_uri, webpush_url = Constant.BASE_URL;
13 | protected String uuid;
14 | protected String skey;
15 | protected String synckey;
16 | protected String wxsid;
17 | protected String wxuin;
18 | protected String pass_ticket;
19 | protected boolean alive;
20 | protected String deviceId = "e" + DateKit.getCurrentUnixTime();
21 |
22 | protected String cookie;
23 |
24 | protected JSONObject baseRequest;
25 | protected JSONObject SyncKey;
26 | protected JSONObject User;
27 |
28 | protected Date loginDate;
29 |
30 |
31 | public boolean isAlive() {
32 | return alive;
33 | }
34 |
35 | public void setAlive(boolean alive) {
36 | this.alive = alive;
37 | }
38 |
39 | public String getUuid() {
40 | return uuid;
41 | }
42 |
43 | public void setUuid(String uuid) {
44 | this.uuid = uuid;
45 | }
46 |
47 | public String getSkey() {
48 | return skey;
49 | }
50 |
51 | public void setSkey(String skey) {
52 | this.skey = skey;
53 | }
54 |
55 | public String getSynckey() {
56 | return synckey;
57 | }
58 |
59 | public void setSynckey(String synckey) {
60 | this.synckey = synckey;
61 | }
62 |
63 | public String getWxsid() {
64 | return wxsid;
65 | }
66 |
67 | public void setWxsid(String wxsid) {
68 | this.wxsid = wxsid;
69 | }
70 |
71 | public String getWxuin() {
72 | return wxuin;
73 | }
74 |
75 | public void setWxuin(String wxuin) {
76 | this.wxuin = wxuin;
77 | }
78 |
79 | public String getPass_ticket() {
80 | return pass_ticket;
81 | }
82 |
83 | public void setPass_ticket(String pass_ticket) {
84 | this.pass_ticket = pass_ticket;
85 | }
86 |
87 | public String getDeviceId() {
88 | return deviceId;
89 | }
90 |
91 | public void setDeviceId(String deviceId) {
92 | this.deviceId = deviceId;
93 | }
94 |
95 | public String getCookie() {
96 | return cookie;
97 | }
98 |
99 | public void setCookie(String cookie) {
100 | this.cookie = cookie;
101 | }
102 |
103 | public JSONObject getBaseRequest() {
104 | return baseRequest;
105 | }
106 |
107 | public void setBaseRequest(JSONObject baseRequest) {
108 | this.baseRequest = baseRequest;
109 | }
110 |
111 | public JSONObject getSyncKey() {
112 | return SyncKey;
113 | }
114 |
115 | public void setSyncKey(JSONObject syncKey) {
116 | SyncKey = syncKey;
117 | }
118 |
119 | public JSONObject getUser() {
120 | return User;
121 | }
122 |
123 | public void setUser(JSONObject user) {
124 | User = user;
125 | }
126 |
127 | public String getBase_uri() {
128 | return base_uri;
129 | }
130 |
131 | public void setBase_uri(String base_uri) {
132 | this.base_uri = base_uri;
133 | }
134 |
135 | public String getRedirect_uri() {
136 | return redirect_uri;
137 | }
138 |
139 | public void setRedirect_uri(String redirect_uri) {
140 | this.redirect_uri = redirect_uri;
141 | }
142 |
143 | public String getWebpush_url() {
144 | return webpush_url;
145 | }
146 |
147 | public void setWebpush_url(String webpush_url) {
148 | this.webpush_url = webpush_url;
149 | }
150 |
151 | public String getMobile() {
152 | return mobile;
153 | }
154 |
155 | public void setMobile(String mobile) {
156 | this.mobile = mobile;
157 | }
158 |
159 | public Date getLoginDate() {
160 | return loginDate;
161 | }
162 |
163 | public void setLoginDate(Date loginDate) {
164 | this.loginDate = loginDate;
165 | }
166 |
167 | }
168 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/demo/Demo1.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.demo;
2 |
3 | import com.blade.kit.json.JSONArray;
4 | import com.blade.kit.json.JSONObject;
5 | import com.iyuexian.wechat4j.WechatStartup;
6 | import com.iyuexian.wechat4j.core.WechatApiUtil;
7 | import com.iyuexian.wechat4j.core.WechatMeta;
8 | import com.iyuexian.wechat4j.plugin.FriendAddTask;
9 | import com.iyuexian.wechat4j.plugin.MessageListener;
10 | import com.iyuexian.wechat4j.plugin.WxLocalCache;
11 |
12 | public class Demo1 {
13 |
14 | public static void main(String[] args) {
15 | test3();
16 | }
17 |
18 | // 给指定人发消息
19 | public static void test1() throws InterruptedException {
20 | WechatMeta meta = WechatStartup.login();
21 | JSONObject contact = WxLocalCache.instance().getContactByRemarkName("Test");
22 | if (contact == null) {
23 | return;
24 | }
25 | WechatApiUtil.webwxsendmsg(meta, "哈哈", contact);
26 | }
27 |
28 | // 给所有联系人发消息
29 | public static void test2() {
30 | WechatMeta meta = WechatStartup.login();
31 | JSONArray contactList = WxLocalCache.instance().getContactList();
32 | for (int i = 0; i < contactList.size(); i++) {
33 | WechatApiUtil.webwxsendmsg(meta, "^^", contactList.get(i).asJSONObject());
34 | }
35 | }
36 |
37 | // 监听消息
38 | public static void test3() {
39 | WechatMeta meta = WechatStartup.login();
40 | MessageListener listener = new MessageListener(meta);
41 | listener.listen();
42 | }
43 |
44 | // 批量添加群里的人(该方法不稳定,没控制好间隔时间很容易被微信服务器察觉,返回失败)
45 | public static void batchAddChatRoomFriend() {
46 | WechatMeta meta = WechatStartup.login();
47 | FriendAddTask task = new FriendAddTask(meta, "添加添加好友的群名称", 15);
48 | task.start();
49 | }
50 |
51 | }
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/exception/WechatException.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.exception;
2 |
3 | public class WechatException extends RuntimeException {
4 |
5 | private static final long serialVersionUID = 209248116271894410L;
6 |
7 | public WechatException() {
8 | super();
9 | }
10 |
11 | public WechatException(String message) {
12 | super(message);
13 | }
14 |
15 | public WechatException(Throwable cause) {
16 | super(cause);
17 | }
18 |
19 | }
20 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/ContactManager.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.util.List;
4 |
5 | import org.slf4j.Logger;
6 | import org.slf4j.LoggerFactory;
7 |
8 | import com.blade.kit.DateKit;
9 | import com.blade.kit.StringKit;
10 | import com.blade.kit.http.HttpRequest;
11 | import com.blade.kit.json.JSONArray;
12 | import com.blade.kit.json.JSONKit;
13 | import com.blade.kit.json.JSONObject;
14 | import com.iyuexian.wechat4j.core.WechatMeta;
15 | import com.iyuexian.wechat4j.exception.WechatException;
16 | import com.iyuexian.wechat4j.util.HttpClient;
17 |
18 | public class ContactManager {
19 |
20 | public static Logger LOGGER = LoggerFactory.getLogger(ContactManager.class);
21 | private WechatMeta meta;
22 |
23 | private HttpClient httpRequsetUtil;
24 |
25 | public ContactManager(WechatMeta meta) {
26 | super();
27 | this.meta = meta;
28 | this.httpRequsetUtil = new HttpClient(meta);
29 | }
30 |
31 | /**
32 | * 获取通讯录列表
33 | */
34 | public JSONArray getContactList() {
35 | String url = meta.getBase_uri() + "/webwxgetcontact?&seq=0&pass_ticket=" + meta.getPass_ticket() + "&skey=" + meta.getSkey() + "&r="
36 | + DateKit.getCurrentUnixTime();
37 | JSONObject body = new JSONObject();
38 | body.put("BaseRequest", meta.getBaseRequest());
39 | JSONObject response = httpRequsetUtil.postJSON(url, body);
40 | JSONArray memberList = response.get("MemberList").asArray();
41 | return memberList;
42 |
43 | }
44 |
45 | public void initLatestChatroom(List chatRommNames) {
46 | JSONArray groupArray = new JSONArray();
47 | // for (String groupUserName :
48 | // Storage.instance().getLatestChatRoomUserNameList()) {
49 | for (String groupUserName : chatRommNames) {
50 | JSONObject groupItem = new JSONObject();
51 | groupItem.put("UserName", groupUserName);
52 | groupItem.put("ChatRoomId", "");
53 | groupArray.add(groupItem);
54 | }
55 | JSONArray latestChatRoomList = getMemberListByChatroom(groupArray);
56 | Storage.instance().setLatestChatRoomList(latestChatRoomList);
57 |
58 | }
59 |
60 | public JSONArray getMemberListByChatroom(JSONArray chatRoomList) {
61 | String url = meta.getBase_uri() + "/webwxbatchgetcontact?type=ex&r=" + DateKit.getCurrentUnixTime() + "&lang=zh_CN";
62 | JSONObject body = new JSONObject();
63 | body.put("BaseRequest", meta.getBaseRequest());
64 | body.put("Count", chatRoomList.size());
65 | body.put("List", chatRoomList);
66 | HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie())
67 | .send(body.toString());
68 | String res = request.body();
69 | request.disconnect();
70 | if (StringKit.isBlank(res)) {
71 | throw new WechatException("获取群成员列表失败");
72 | }
73 | JSONObject jsonObject = JSONKit.parseObject(res);
74 | JSONObject baseResponse = jsonObject.get("BaseResponse").asJSONObject();
75 | if (null == baseResponse || baseResponse.getInt("Ret", -1) != 0) {
76 | LOGGER.warn("获取群列表失败,{}", baseResponse);
77 | return null;
78 | }
79 | JSONArray memberList = jsonObject.get("ContactList").asArray();
80 | // LOGGER.info("获取群成员:{}", memberList);
81 | return memberList;
82 |
83 | }
84 |
85 | }
86 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/ContactUserUtil.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | import org.slf4j.Logger;
7 | import org.slf4j.LoggerFactory;
8 |
9 | import com.blade.kit.json.JSONArray;
10 | import com.blade.kit.json.JSONObject;
11 | import com.iyuexian.wechat4j.bean.ChatRoom;
12 | import com.iyuexian.wechat4j.bean.ChatRoomMember;
13 | import com.iyuexian.wechat4j.bean.GroupMember;
14 | import com.iyuexian.wechat4j.config.Constant;
15 |
16 | public class ContactUserUtil {
17 |
18 | public static final Logger LOGGER = LoggerFactory.getLogger(ContactUserUtil.class);
19 |
20 | @Deprecated
21 | public static List processMemberJSON(JSONArray memberList) {
22 | List members = new ArrayList();
23 | for (int i = 0; i < memberList.size(); i++) {
24 | JSONObject member = memberList.get(i).asJSONObject();
25 | GroupMember item = new GroupMember(member);
26 | members.add(item);
27 | }
28 | return members;
29 | }
30 |
31 | public static List processChatRoomMember(JSONArray memberList) {
32 | List members = new ArrayList();
33 | for (int i = 0; i < memberList.size(); i++) {
34 | JSONObject member = memberList.get(i).asJSONObject();
35 | ChatRoomMember item = new ChatRoomMember(member);
36 | if (Constant.PRINT_MEMBER_INFO) {
37 | LOGGER.warn("当前群成员:{}", item.getNickName());
38 | }
39 | members.add(item);
40 | }
41 | return members;
42 | }
43 |
44 | public static List processChatRoom(JSONArray chatrooms) {
45 |
46 | List roomList = new ArrayList();
47 | for (int i = 0; i < chatrooms.size(); i++) {
48 | JSONObject item = chatrooms.get(i).asJSONObject();
49 | ChatRoom chatRoom = ChatRoom.parseFromJSON(item);
50 | LOGGER.warn("当前群:{},人数:{}", chatRoom.getNickName(), chatRoom.getMemberCount());
51 | JSONArray memberArray = item.get("MemberList").asArray();
52 | List memberList = processChatRoomMember(memberArray);
53 | chatRoom.setMemberList(memberList);
54 | roomList.add(chatRoom);
55 | }
56 | return roomList;
57 |
58 | }
59 |
60 | }
61 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/FileHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.io.File;
4 | import java.nio.file.Path;
5 | import java.nio.file.Paths;
6 | import java.util.Date;
7 | import java.util.HashMap;
8 | import java.util.Map;
9 | import java.util.Random;
10 |
11 | import org.slf4j.Logger;
12 | import org.slf4j.LoggerFactory;
13 |
14 | import com.blade.kit.StringKit;
15 | import com.blade.kit.http.HttpRequest;
16 | import com.blade.kit.json.JSONObject;
17 | import com.iyuexian.wechat4j.core.WechatMeta;
18 | import com.iyuexian.wechat4j.exception.WechatException;
19 | import com.iyuexian.wechat4j.util.CookieUtil;
20 | import com.iyuexian.wechat4j.util.FileUtil;
21 |
22 | public class FileHandler {
23 | public static Logger LOGGER = LoggerFactory.getLogger(FileHandler.class);
24 | private WechatMeta meta;
25 |
26 | public FileHandler(WechatMeta meta) {
27 | super();
28 | this.meta = meta;
29 | }
30 |
31 | public String uploadFile(String filePath, String toUserName) {
32 |
33 | Map params = new HashMap();
34 |
35 | Path path = Paths.get(filePath);
36 | String contentType = FileUtil.getContentType(path, "text/plain");
37 | File file = path.toFile();
38 | params.put("id", "WU_FILE_0");
39 | params.put("name", file.getName());
40 | params.put("type", contentType);
41 | params.put("size", file.length());
42 | params.put("mediatype", FileUtil.isDoc(contentType) ? "doc" : FileUtil.isPicture(contentType) ? "pic" : "video"); // doc,video,pic
43 | String fileMD5 = FileUtil.getMD5(file);
44 | params.put("uploadmediarequest", getUploadmediaRequest(fileMD5, file.length(), 0, file.length(), toUserName));
45 | params.put("webwx_data_ticket", CookieUtil.getValueFromCookieStr(meta.getCookie(), "webwx_data_ticket"));
46 | params.put("pass_ticket", meta.getPass_ticket());
47 | HttpRequest request = HttpRequest.post("https://file.wx2.qq.com/cgi-bin/mmwebwx-bin/webwxuploadmedia?f=json")
48 | .contentType("multipart/form-data").part("filename", file.getName(), contentType, file).send(params.toString().getBytes());
49 |
50 | String res = request.body();
51 | LOGGER.debug("response from wechat:{}", res);
52 | request.disconnect();
53 | if (StringKit.isBlank(res)) {
54 | throw new WechatException(res.toString());
55 | }
56 | return res;
57 |
58 | }
59 |
60 | private JSONObject getUploadmediaRequest(String fileMD5, long totalLen, long startPos, long dataLen, String toUserName) {
61 | String clientMediaId = String.valueOf(new Date().getTime()) + String.valueOf(new Random().nextLong()).substring(0, 4);
62 | JSONObject mediaRequest = new JSONObject();
63 | // TODO unkonw the meaning of uploadType
64 | mediaRequest.put("UploadType", 2);
65 | mediaRequest.put("BaseRequest", this.meta.getBaseRequest());
66 | mediaRequest.put("ClientMediaId", clientMediaId);
67 | mediaRequest.put("TotalLen", totalLen);
68 | mediaRequest.put("StartPos", startPos);
69 | mediaRequest.put("DataLen", dataLen);
70 | // TODO unkonw the meaning of MediaType
71 | mediaRequest.put("MediaType", 4);
72 | mediaRequest.put("FromUserName", meta.getUser().getString("UserName"));
73 |
74 | mediaRequest.put("ToUserName", toUserName == null ? "filehelper" : toUserName);
75 | mediaRequest.put("FileMd5", fileMD5);
76 | return mediaRequest;
77 |
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/FriendAddTask.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.util.Random;
4 |
5 | import org.slf4j.Logger;
6 | import org.slf4j.LoggerFactory;
7 |
8 | import com.blade.kit.json.JSONArray;
9 | import com.blade.kit.json.JSONObject;
10 | import com.iyuexian.wechat4j.core.WechatApiUtil;
11 | import com.iyuexian.wechat4j.core.WechatMeta;
12 |
13 | public class FriendAddTask implements Runnable {
14 | private long sleepSecond = 5;
15 | private String chatRoomName = "";
16 | protected Logger logger = LoggerFactory.getLogger(FriendAddTask.class);
17 | private WechatMeta meta;
18 |
19 | public void start() {
20 | new Thread(this).start();
21 | }
22 |
23 | public FriendAddTask(WechatMeta meta) {
24 | }
25 |
26 | public FriendAddTask(WechatMeta meta, String chatRoom, long sleepSecond) {
27 | this.meta = meta;
28 | this.sleepSecond = sleepSecond;
29 | this.chatRoomName = chatRoom;
30 | }
31 |
32 | @Override
33 | public void run() {
34 | JSONArray rooms = Storage.instance().getLatestChatRoomList();
35 | for (int i = 0; i < rooms.size(); i++) {
36 | JSONObject room = rooms.get(i).asJSONObject();
37 | logger.info("发现群:【{}】,人数:{}", room.getString("NickName"), room.getInt("MemberCount"));
38 | if (chatRoomName == null || chatRoomName.trim().length() == 0) {
39 | continue;
40 | }
41 | if (!room.getString("NickName").contains(chatRoomName)) {
42 | continue;
43 | }
44 | addFriend(room);
45 | }
46 | }
47 |
48 | private void addFriend(JSONObject room) {
49 | JSONArray members = room.get("MemberList").asArray();
50 | for (int j = 0; j < members.size(); j++) {
51 | JSONObject member = members.get(j).asJSONObject();
52 | String userName = member.getString("UserName");
53 | String nickName = member.getString("NickName");
54 | if (Storage.instance().isFriend(userName)) {
55 | logger.info("发现您的好友 【{}】,在【{}】群中,忽略", nickName, room.getString("NickName"));
56 | continue;
57 | }
58 |
59 | logger.info("开始添加好友 【{}】", nickName);
60 | WechatApiUtil.addFriend(meta, userName, "nihao");
61 | long sleep = this.sleepSecond + new Random().nextInt(100);
62 | logger.info("休眠:{}秒", sleep);
63 | try {
64 | Thread.sleep(sleep * 1000);
65 | } catch (InterruptedException e) {
66 | e.printStackTrace();
67 | }
68 | }
69 | }
70 |
71 | public long getSleepSecond() {
72 | return sleepSecond;
73 | }
74 |
75 | public String getChatRoomName() {
76 | return chatRoomName;
77 | }
78 |
79 | public void setSleepSecond(long sleepSecond) {
80 | this.sleepSecond = sleepSecond;
81 | }
82 |
83 | public void setChatRoomName(String chatRoomName) {
84 | this.chatRoomName = chatRoomName;
85 | }
86 |
87 | }
88 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/MessageListener.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.util.concurrent.TimeUnit;
4 |
5 | import org.slf4j.Logger;
6 | import org.slf4j.LoggerFactory;
7 |
8 | import com.blade.kit.json.JSONObject;
9 | import com.iyuexian.wechat4j.core.WechatApiUtil;
10 | import com.iyuexian.wechat4j.core.WechatMeta;
11 | import com.iyuexian.wechat4j.plugin.message.MessageManager;
12 |
13 | public class MessageListener implements Runnable {
14 |
15 | private Logger logger = LoggerFactory.getLogger(MessageListener.class);
16 | private WechatMeta meta;
17 | private MessageManager messageManager;
18 |
19 | public MessageListener(WechatMeta meta) {
20 | this.meta = meta;
21 | messageManager = new MessageManager(meta);
22 | }
23 |
24 | public void listen() {
25 | new Thread(this).start();
26 | }
27 |
28 | @Override
29 | public void run() {
30 | WechatApiUtil.choiceSyncLine(meta);
31 | while (true) {
32 | int[] arr = WechatApiUtil.syncCheck(meta); // 消息检查
33 | logger.debug("正在监听消息,retcode={}, selector={}", arr[0], arr[1]);
34 |
35 | // retcode: 0 正常 1100 失败/登出微信 selector: 0 正常 2 新的消息 7 进入/离开聊天界面 ```
36 | int retcode = arr[0], selector = arr[1];
37 |
38 | if (retcode == 1100 || retcode == 1101) {
39 | logger.warn("用户微信退出");
40 | break;
41 | }
42 | if (retcode != 0) {
43 | sleep(2);
44 | continue;
45 | }
46 | if (selector == 7) {
47 | logger.debug("进入(离开)聊天界面");
48 | } else if (selector == 0 || selector == 3) {
49 | continue;
50 | } else if (selector == 2 || selector == 6) {
51 | handleMsg();
52 | }
53 | sleep(4);
54 |
55 | }
56 |
57 | }
58 |
59 | private void handleMsg() {
60 | try {
61 | JSONObject data = WechatApiUtil.webwxsync(meta);
62 | messageManager.process(data);
63 | } catch (Exception ex) {
64 | logger.error("处理消息异常,ex:{}", ex);
65 | }
66 |
67 | }
68 |
69 | private void sleep(int seconds) {
70 | try {
71 | TimeUnit.SECONDS.sleep(seconds);
72 | } catch (InterruptedException e) {
73 | e.printStackTrace();
74 | }
75 | }
76 |
77 | }
78 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/QRCodeWindow.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.awt.Color;
4 | import java.awt.Font;
5 | import java.awt.Graphics;
6 |
7 | import javax.swing.ImageIcon;
8 | import javax.swing.JFrame;
9 | import javax.swing.JLabel;
10 | import javax.swing.JPanel;
11 | import javax.swing.SwingConstants;
12 | import javax.swing.border.EmptyBorder;
13 |
14 | public class QRCodeWindow extends JFrame {
15 |
16 | private static final long serialVersionUID = 8550014433017811556L;
17 | private JPanel contentPane;
18 |
19 | /**
20 | * Create the frame.
21 | */
22 | @SuppressWarnings("serial")
23 | public QRCodeWindow(final String filePath) {
24 | setBackground(Color.WHITE);
25 | this.setResizable(false);
26 | this.setTitle("\u8BF7\u7528\u624B\u673A\u626B\u63CF\u5FAE\u4FE1\u4E8C\u7EF4\u7801");
27 | this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
28 | this.setBounds(100, 100, 297, 362);
29 | this.contentPane = new JPanel();
30 | contentPane.setBackground(new Color(102, 153, 255));
31 | this.contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
32 | this.setContentPane(contentPane);
33 | contentPane.setLayout(null);
34 |
35 | JPanel qrcodePanel = new JPanel() {
36 | public void paintComponent(Graphics g) {
37 | ImageIcon icon = new ImageIcon(filePath);
38 | // 图片随窗体大小而变化
39 | g.drawImage(icon.getImage(), 0, 0, 301, 301, this);
40 | }
41 | };
42 | qrcodePanel.setBounds(0, 0, 295, 295);
43 |
44 | JLabel tipLable = new JLabel("扫描二维码登录微信");
45 | tipLable.setFont(new Font("微软雅黑", Font.PLAIN, 18));
46 | tipLable.setHorizontalAlignment(SwingConstants.CENTER);
47 | tipLable.setBounds(0, 297, 291, 37);
48 |
49 | contentPane.add(qrcodePanel);
50 | contentPane.add(tipLable);
51 |
52 | this.setLocationRelativeTo(null);
53 | this.setVisible(true);
54 | }
55 | }
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/QrUtil.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import com.iyuexian.wechat4j.config.Enums.OS;
4 |
5 | public class QrUtil {
6 |
7 | public static OS getOsName() {
8 | String os = System.getProperty("os.name").toUpperCase();
9 | if (os.indexOf(OS.DARWIN.toString()) >= 0) {
10 | return OS.DARWIN;
11 | } else if (os.indexOf(OS.WINDOWS.toString()) >= 0) {
12 | return OS.WINDOWS;
13 | } else if (os.indexOf(OS.LINUX.toString()) >= 0) {
14 | return OS.LINUX;
15 | } else if (os.indexOf(OS.MAC.toString()) >= 0) {
16 | return OS.MAC;
17 | }
18 | return OS.OTHER;
19 | }
20 |
21 | public static void printQr(String qrPath) throws Exception {
22 | String cmd = "";
23 | switch (getOsName()) {
24 | case WINDOWS: {
25 | cmd = " cmd /c start ";
26 | break;
27 | }
28 | case MAC:
29 | cmd = " open ";
30 | break;
31 | default:
32 | throw new RuntimeException("operation not supported");
33 | }
34 | Runtime runtime = Runtime.getRuntime();
35 | runtime.exec(cmd + qrPath);
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/Storage.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | import org.slf4j.Logger;
7 | import org.slf4j.LoggerFactory;
8 |
9 | import com.blade.kit.json.JSONArray;
10 | import com.blade.kit.json.JSONObject;
11 | import com.iyuexian.wechat4j.config.Constant;
12 |
13 | public class Storage {
14 |
15 | public static final Logger LOGGER = LoggerFactory.getLogger(Storage.class);
16 |
17 | private List LATEST_GROUP_USERNAME_LIST = new ArrayList();
18 | private JSONArray latestChatRoomList;
19 |
20 | private JSONArray allContact = new JSONArray();
21 | private JSONArray chatRoomList = new JSONArray();
22 | private JSONArray mpList = new JSONArray();
23 | private JSONArray specailList = new JSONArray();
24 | private JSONArray friendList = new JSONArray();
25 |
26 | private static Storage instance = null;
27 |
28 | private Storage() {
29 | };
30 |
31 | public synchronized static Storage instance() {
32 | if (instance != null)
33 | return instance;
34 | instance = new Storage();
35 | return instance;
36 |
37 | }
38 |
39 | public void addLasetChatroomUserName(String userName) {
40 | this.LATEST_GROUP_USERNAME_LIST.add(userName);
41 | }
42 |
43 | public void loadMemberList(JSONArray all) {
44 |
45 | this.allContact = all;
46 | if (all != null) {
47 | parseMemberList(allContact);
48 | }
49 |
50 | }
51 |
52 | private void clear() {
53 | this.mpList = new JSONArray();
54 | this.specailList = new JSONArray();
55 | this.chatRoomList = new JSONArray();
56 |
57 | }
58 |
59 | private void parseMemberList(JSONArray contactList) {
60 | clear();
61 | for (int i = 0; i < contactList.size(); i++) {
62 | JSONObject item = contactList.get(i).asJSONObject();
63 | if (item.getInt("VerifyFlag", 0) == 8) {
64 | mpList.add(item);
65 | } else if (Constant.FILTER_USERS.contains(item.getString("UserName"))) {
66 | specailList.add(item);
67 |
68 | } else if (item.getString("UserName").indexOf("@@") != -1) {
69 | chatRoomList.add(item);
70 |
71 | } else {
72 | friendList.add(item);
73 |
74 | }
75 | }
76 | LOGGER.info("初始化联系人完成,当前共加载{}个联系人,公众号:{}个,好友:{}个,群:{}个", allContact.size(), mpList.size(), friendList.size(), chatRoomList.size());
77 | }
78 |
79 | public boolean isFriend(String userName) {
80 | for (int i = 0; i < friendList.size(); i++) {
81 | JSONObject member = friendList.get(i).asJSONObject();
82 | if (member.getString("UserName").equals(userName)) {
83 | return true;
84 | }
85 | }
86 | return false;
87 | }
88 |
89 | public List getLatestChatRoomUserNameList() {
90 | return this.LATEST_GROUP_USERNAME_LIST;
91 | }
92 |
93 | public JSONArray getAllContact() {
94 | return allContact;
95 | }
96 |
97 | public JSONArray getChatRoomList() {
98 | return chatRoomList;
99 | }
100 |
101 | public JSONArray getMpList() {
102 | return mpList;
103 | }
104 |
105 | public JSONArray getSpecailList() {
106 | return specailList;
107 | }
108 |
109 | public JSONArray getFriendList() {
110 | return friendList;
111 | }
112 |
113 | public JSONArray getLatestChatRoomList() {
114 | return latestChatRoomList;
115 | }
116 |
117 | public void setLatestChatRoomList(JSONArray latestChatRoomList) {
118 | this.latestChatRoomList = latestChatRoomList;
119 | }
120 |
121 | }
122 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/Task.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | public abstract class Task {
4 | public void start() {
5 | try {
6 | new Thread(wrapWithRunnable(), "user-tasks-" + System.currentTimeMillis()).start();
7 | } catch (Exception ex) {
8 | ex.printStackTrace();
9 | }
10 | }
11 |
12 | public Runnable wrapWithRunnable() {
13 | return new Runnable() {
14 | @Override
15 | public void run() {
16 | initTask();
17 | }
18 | };
19 | }
20 | public abstract void initTask();
21 |
22 | }
23 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/TulingRobot.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.http.HttpRequest;
7 | import com.blade.kit.json.JSON;
8 | import com.blade.kit.json.JSONObject;
9 | import com.iyuexian.wechat4j.util.TulingUtil;
10 |
11 | public class TulingRobot {
12 | public static final Logger LOGGER = LoggerFactory.getLogger(TulingRobot.class);
13 | private String key = "7507257e2872417d9e4fb0e2764cf0ac";
14 | private String secret = "36c3be794b4950dc";
15 | private String url = "http://www.tuling123.com/openapi/api";
16 | private static TulingRobot instance = null;
17 |
18 | private static final int V1 = 1;
19 | private static final int V2 = 2;
20 |
21 | private TulingRobot() {
22 | }
23 |
24 | public static TulingRobot instance() {
25 | if (instance != null) {
26 | return instance;
27 | }
28 | instance = new TulingRobot();
29 | return instance;
30 | }
31 |
32 | public String chat(String userId, String content) {
33 | return chat(userId, content, null);
34 | }
35 |
36 | public String chat(String userId, String content, Location location) {
37 | if (content == null)
38 | throw new IllegalArgumentException("content不能为null");
39 | try {
40 | JSONObject params = populateV2Param(content, userId);
41 | String resp = send(params, V1);
42 | if (resp == null)
43 | return "";
44 | return JSON.parse(resp).asJSONObject().getString("text");
45 | } catch (Exception ex) {
46 | ex.printStackTrace();
47 | return "";
48 | }
49 |
50 | }
51 |
52 | public JSONObject populateV2Param(String content, String userId) {
53 |
54 | JSONObject params = new JSONObject();
55 | params.put("key", key);
56 | params.put("info", content);
57 | params.put("userid", userId);
58 | return params;
59 | }
60 |
61 | public JSONObject populateV2Param(String content, String userId, Location location) {
62 | JSONObject params = new JSONObject();
63 | JSONObject perception = new JSONObject();
64 | perception.put("inputText", new InputText(content));
65 |
66 | JSONObject userInfo = new JSONObject();
67 | userInfo.put("apiKey", key);
68 | new UserInfo(key, userId);
69 | params.put("userInfo", userInfo);
70 | params.put("perception", perception);
71 |
72 | if (location != null) {
73 | JSONObject selfInfo = new JSONObject();
74 | selfInfo.put("location", location);
75 | params.put("selfInfo", selfInfo);
76 |
77 | }
78 | return params;
79 |
80 | }
81 |
82 | public String encryptSend(JSONObject reqParams) throws Exception {
83 | long timestamp = System.currentTimeMillis();
84 | String keyParam = secret + timestamp + key;
85 | String aesKey = TulingUtil.MD5(keyParam);
86 | String data = TulingUtil.encrypt(aesKey, reqParams.toString());
87 |
88 | JSONObject req = new JSONObject();
89 | req.put("key", key);
90 | req.put("timestamp", String.valueOf(timestamp));
91 | req.put("data", data);
92 | return send(req, V2);
93 |
94 | }
95 |
96 | public String send(JSONObject params, int version) {
97 |
98 | if (version == V2) {
99 | url = url + "/v2";
100 | }
101 |
102 | HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8");
103 | request.send(params.toString());
104 | String resp = request.body();
105 | request.disconnect();
106 | return resp;
107 | }
108 |
109 | // private String encryptReq(Map reqParam) throws Exception
110 | // {
111 | // long timestamp = System.currentTimeMillis();
112 | // String keyParam = secret + timestamp + key;
113 | // String aesKey = TulingUtil.MD5(keyParam);
114 | // String data = TulingUtil.encrypt(aesKey, JSON.toJSONString(reqParam));
115 | // Map req = new HashMap();
116 | // req.put("key", key);
117 | // req.put("timestamp", String.valueOf(timestamp));
118 | // req.put("data", data);
119 | // String str =
120 | // TulingUtil.sendPost(com.alibaba.fastjson.JSON.toJSONString(req), url);
121 | // if (str == null || str.trim().length() == 0)
122 | // return "";
123 | //
124 | // JSONObject repJSON = JSON.parseObject(str);
125 | // // int code = repJSON.getIntValue("code");
126 | // String text = repJSON.getString("text");
127 | // return text;
128 | //
129 | // }
130 |
131 | public String getKey() {
132 | return key;
133 | }
134 |
135 | public void setKey(String key) {
136 | this.key = key;
137 | }
138 |
139 | public String getSecret() {
140 | return secret;
141 | }
142 |
143 | public void setSecret(String secret) {
144 | this.secret = secret;
145 | }
146 |
147 | public String getUrl() {
148 | return url;
149 | }
150 |
151 | public void setUrl(String url) {
152 | this.url = url;
153 | }
154 |
155 | public static class InputText {
156 |
157 | private String text;
158 |
159 | public InputText(String text) {
160 | super();
161 | this.text = text;
162 | }
163 |
164 | public String getText() {
165 | return text;
166 | }
167 |
168 | public void setText(String text) {
169 | this.text = text;
170 | }
171 |
172 | }
173 |
174 | public static class Location {
175 |
176 | private String city; // 例如:北京
177 | private String latitude;
178 | private String longitude;
179 | private String nearest_poi_name;// 例如:上地环岛南
180 | private String province;// 例如:北京
181 | private String street; // 例如:信息路
182 |
183 | public String getCity() {
184 | return city;
185 | }
186 |
187 | public String getLatitude() {
188 | return latitude;
189 | }
190 |
191 | public String getLongitude() {
192 | return longitude;
193 | }
194 |
195 | public String getNearest_poi_name() {
196 | return nearest_poi_name;
197 | }
198 |
199 | public String getProvince() {
200 | return province;
201 | }
202 |
203 | public String getStreet() {
204 | return street;
205 | }
206 |
207 | public void setCity(String city) {
208 | this.city = city;
209 | }
210 |
211 | public void setLatitude(String latitude) {
212 | this.latitude = latitude;
213 | }
214 |
215 | public void setLongitude(String longitude) {
216 | this.longitude = longitude;
217 | }
218 |
219 | public void setNearest_poi_name(String nearest_poi_name) {
220 | this.nearest_poi_name = nearest_poi_name;
221 | }
222 |
223 | public void setProvince(String province) {
224 | this.province = province;
225 | }
226 |
227 | public void setStreet(String street) {
228 | this.street = street;
229 | }
230 |
231 | }
232 |
233 | public static class UserInfo {
234 |
235 | private String apiKey;
236 | private String userId;
237 |
238 | public UserInfo(String apiKey, String userId) {
239 | this.apiKey = apiKey;
240 | this.userId = userId;
241 | }
242 |
243 | public String getApiKey() {
244 | return apiKey;
245 | }
246 |
247 | public String getUserId() {
248 | return userId;
249 | }
250 |
251 | public void setApiKey(String apiKey) {
252 | this.apiKey = apiKey;
253 | }
254 |
255 | public void setUserId(String userId) {
256 | this.userId = userId;
257 | }
258 |
259 | }
260 |
261 | }
262 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/TxtMessageRobot.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | public interface TxtMessageRobot {
4 |
5 | public String reply(String uid, String content);
6 |
7 | }
8 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/WxLocalCache.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin;
2 |
3 | import java.util.HashMap;
4 | import java.util.Map;
5 |
6 | import org.slf4j.Logger;
7 | import org.slf4j.LoggerFactory;
8 |
9 | import com.blade.kit.json.JSONArray;
10 | import com.blade.kit.json.JSONObject;
11 | import com.iyuexian.wechat4j.core.WechatMeta;
12 |
13 | public class WxLocalCache {
14 |
15 | private final String CONTACT = "webwxgetcontact";
16 | private final String LATEST_CONTACT = "latest_webwxgetcontact";
17 |
18 | private Map cacheInstance;
19 | private ContactManager contactManager;
20 |
21 | private Logger logger = LoggerFactory.getLogger(WxLocalCache.class);
22 |
23 | private WxLocalCache(WechatMeta meta) {
24 | super();
25 | this.cacheInstance = new HashMap();
26 | this.contactManager = new ContactManager(meta);
27 | }
28 |
29 | static class Holder {
30 | static WxLocalCache instance = null;
31 | }
32 |
33 | public static WxLocalCache instance() {
34 | if (Holder.instance == null) {
35 | throw new IllegalStateException("wxLocalCache not init");
36 | }
37 | return Holder.instance;
38 |
39 | }
40 |
41 | public static WxLocalCache init(WechatMeta meta) {
42 | if (Holder.instance != null) {
43 | return Holder.instance;
44 | }
45 | Holder.instance = new WxLocalCache(meta);
46 | return Holder.instance;
47 | }
48 |
49 | public JSONArray getContactList() {
50 | JSONArray arr = get(CONTACT);
51 | if (arr == null && (arr = contactManager.getContactList()) == null) {
52 | logger.error("获取联系人失败");
53 | return null;
54 | }
55 | return arr;
56 | }
57 |
58 | public JSONObject getContactByRemarkName(String remarkName) {
59 | return getContactByName("RemarkName", remarkName);
60 | }
61 |
62 | public JSONObject getContactByNickName(String nickName) {
63 | return getContactByName("NickName", nickName);
64 | }
65 |
66 | public JSONObject getContactByUserName(String ContactName) {
67 | return getContactByName("UserName", ContactName);
68 | }
69 |
70 | private JSONObject getContactByName(String fieldName, String fieldVal) {
71 | JSONArray arr = getContactList();
72 | if (arr == null) {
73 | return null;
74 | }
75 |
76 | for (int i = 0; i < arr.size(); i++) {
77 | JSONObject val = arr.get(i).asJSONObject();
78 | String userName = val.getString("UserName");
79 | String nickName = val.getString("NickName");
80 | String remarkName = val.getString("RemarkName");
81 | if (fieldName.equals("UserName") && userName.equals(fieldVal)) {
82 | return val;
83 | } else if (fieldName.equals("NickName") && nickName.equals(fieldVal)) {
84 | return val;
85 | } else if (fieldName.equals("RemarkName") && remarkName.equals(fieldVal)) {
86 | return val;
87 | }
88 | }
89 | logger.error("can't find the contact of " + fieldName + " named " + fieldName);
90 | return null;
91 |
92 | }
93 |
94 | public void put(String key, Object data) {
95 | CacheItem item = new CacheItem(key, data);
96 | cacheInstance.put(key, item);
97 | }
98 |
99 | @SuppressWarnings("unchecked")
100 | public T get(String key) {
101 | CacheItem item = cacheInstance.get(key);
102 | if (item == null) {
103 | return null;
104 | }
105 | return (T) item.getData();
106 |
107 | }
108 |
109 | public static class CacheItem {
110 |
111 | private String key;
112 | private Object data;
113 | private long timestamp;
114 |
115 | public CacheItem(String key, Object data) {
116 | this.key = key;
117 | this.data = data;
118 | this.timestamp = System.currentTimeMillis();
119 |
120 | }
121 |
122 | public String getKey() {
123 | return key;
124 | }
125 |
126 | public Object getData() {
127 | return data;
128 | }
129 |
130 | public long getTimestamp() {
131 | return timestamp;
132 | }
133 | }
134 |
135 | public JSONArray getLatestContactList() {
136 | return get(LATEST_CONTACT);
137 | }
138 |
139 |
140 |
141 | public void setLatestContactList(JSONArray contactList) {
142 | put(LATEST_CONTACT, contactList);
143 |
144 | for (int i = 0; i < contactList.size(); i++) {
145 | JSONObject item = contactList.get(i).asJSONObject();
146 | logger.info("初始化最新联系人 ,item:{}", item.getString("NickName"));
147 | String userName = item.getString("UserName");
148 | // 最近联系的群
149 | if (userName.startsWith("@@")) {
150 | Storage.instance().addLasetChatroomUserName(userName);
151 | continue;
152 | }
153 | // TODO 最近联系的用户
154 | }
155 |
156 | }
157 | }
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/AbstractMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import java.util.HashMap;
4 | import java.util.Map;
5 |
6 | import org.slf4j.Logger;
7 | import org.slf4j.LoggerFactory;
8 |
9 | import com.blade.kit.DateKit;
10 | import com.blade.kit.StringKit;
11 | import com.blade.kit.http.HttpRequest;
12 | import com.blade.kit.io.ByteArrayOutputStream;
13 | import com.blade.kit.json.JSONArray;
14 | import com.blade.kit.json.JSONObject;
15 | import com.iyuexian.wechat4j.config.Constant;
16 | import com.iyuexian.wechat4j.config.Enums.MsgType;
17 | import com.iyuexian.wechat4j.core.WechatMeta;
18 | import com.iyuexian.wechat4j.plugin.Storage;
19 | import com.iyuexian.wechat4j.plugin.TulingRobot;
20 | import com.iyuexian.wechat4j.plugin.TxtMessageRobot;
21 | import com.iyuexian.wechat4j.plugin.storage.PipeLineManager;
22 | import com.iyuexian.wechat4j.util.FileUploadHelper;
23 |
24 | public abstract class AbstractMessageHandler implements IMessageHandler, TxtMessageRobot {
25 |
26 | public static final Logger LOGGER = LoggerFactory.getLogger(AbstractMessageHandler.class);
27 | protected WechatMeta meta;
28 |
29 | private FileUploadHelper fileUploadHelper = new FileUploadHelper();
30 |
31 | public AbstractMessageHandler(WechatMeta meta) {
32 | super();
33 | this.meta = meta;
34 | }
35 |
36 | public String webwxsendmsg(String content, String to) {
37 | String url = meta.getBase_uri() + "/webwxsendmsg?lang=zh_CN&pass_ticket=" + meta.getPass_ticket();
38 | final JSONObject body = new JSONObject();
39 | String clientMsgId = DateKit.getCurrentUnixTime() + StringKit.getRandomNumber(5);
40 | JSONObject Msg = new JSONObject();
41 |
42 | Msg.put("Type", 1);
43 | Msg.put("Content", content);
44 | Msg.put("FromUserName", meta.getUser().getString("UserName"));
45 | Msg.put("ToUserName", to);
46 | Msg.put("LocalID", clientMsgId);
47 | Msg.put("ClientMsgId", clientMsgId);
48 |
49 | body.put("BaseRequest", meta.getBaseRequest());
50 | body.put("Msg", Msg);
51 | final HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie());
52 | request.send(body.toString());
53 | String msgResult = request.body();
54 | request.disconnect();
55 | return msgResult;
56 |
57 | }
58 |
59 | public boolean download(JSONObject msg, MsgType msgType) {
60 |
61 | Map headers = new HashMap();
62 | headers.put("Cookie", meta.getCookie());
63 | Map params = new HashMap();
64 |
65 | String ext = "";
66 | if (msgType == MsgType.PICTURE) {
67 | ext = "jpg";
68 | } else if (msgType == MsgType.VOICE) {
69 | ext = "mp3";
70 | } else if (msgType == MsgType.VIDEO || msgType == MsgType.SMALL_VIDEO) {
71 | LOGGER.warn("暂时不能处理video类消息,msg:{}", msg);
72 | ext = "mp4";
73 | } else if (msgType == MsgType.MEDIA) {
74 | headers.put("Range", "bytes=0-");
75 | params.put("sender", msg.getString("FromUserName"));
76 | params.put("mediaid", msg.getString("MediaId"));
77 | params.put("filename", msg.getString("FileName"));
78 | }
79 | params.put("msgid", msg.getString("MsgId"));
80 | params.put("skey", meta.getSkey());
81 | String host = meta.getBase_uri().endsWith("/") ? meta.getBase_uri() : meta.getBase_uri() + "/";
82 | String url = host + msgType.getDownloadPath() + "?MsgID=" + msg.getString("MsgId") + "&skey=" + meta.getSkey() + "&type=slave";
83 | LOGGER.info(" begin download resource for url:{}", url);
84 | ByteArrayOutputStream bios = new ByteArrayOutputStream();
85 | HttpRequest.get(url, params, true).headers(headers).receive(bios);
86 | String fileKey = fileUploadHelper.uploadToQiniu(bios.toInputStream(), "file." + ext);
87 | PipeLineManager.instance().process(meta, fileKey, msgType);
88 | return true;
89 | }
90 |
91 | public String getUserRemarkName(String id) {
92 | String name = "";
93 | for (int i = 0, len = Storage.instance().getAllContact().size(); i < len; i++) {
94 | JSONObject member = Storage.instance().getAllContact().get(i).asJSONObject();
95 | if (!member.getString("UserName").equals(id)) {
96 | continue;
97 | }
98 | if (StringKit.isNotBlank(member.getString("RemarkName"))) {
99 | name = member.getString("RemarkName");
100 | } else {
101 | name = member.getString("NickName");
102 | }
103 | return name;
104 | }
105 | return name;
106 | }
107 |
108 | public String getMemberRemarkName(String chatRoomUserName, String memberUserName) {
109 | JSONArray chatRoomList = Storage.instance().getLatestChatRoomList();
110 | for (int i = 0; i < chatRoomList.size(); i++) {
111 | JSONObject chatroom = chatRoomList.get(i).asJSONObject();
112 | if (!chatroom.getString("UserName").equals(chatRoomUserName)) {
113 | continue;
114 | }
115 | JSONArray memberList = chatroom.get("MemberList").asArray();
116 | for (int j = 0; j < memberList.size(); j++) {
117 | JSONObject member = memberList.get(j).asJSONObject();
118 | if (member.getString("UserName").equals(memberUserName)) {
119 | return member.getString("NickName");
120 | }
121 | }
122 | }
123 | return "未知昵称";
124 |
125 | }
126 |
127 | public boolean preHandle(JSONObject msg) {
128 |
129 | if (Constant.FILTER_USERS.contains(msg.getString("ToUserName"))) {
130 | LOGGER.info("你收到一条被过滤的消息");
131 | return false;
132 | }
133 | if (isSlefSend(msg)) {
134 | LOGGER.info("你发送了一条消息 ");
135 | return true;
136 | }
137 |
138 | if (msg.getString("FromUserName").startsWith("@@")) {
139 | LOGGER.info("您收到一条群聊消息");
140 | return true;
141 | }
142 | if (msg.getString("FromUserName").startsWith("@")) {
143 | LOGGER.info("您收到一条好友消息");
144 | return true;
145 | }
146 | LOGGER.warn("您收到一条 未知类型消息:{}", msg.toString());
147 | return true;
148 |
149 | }
150 |
151 | public boolean isSlefSend(JSONObject msg) {
152 | return msg.getString("FromUserName").equals(this.meta.getUser().getString("UserName"));
153 | }
154 |
155 | public String getSelfNickName() {
156 | return this.meta.getUser().getString("NickName");
157 | }
158 |
159 | public String getGroupMemberName(JSONObject msg) {
160 | String memberUserName = msg.getString("Content").split(":")[0];
161 | return getMemberRemarkName(msg.getString("FromUserName"), memberUserName);
162 | }
163 |
164 | public String getMemberNickName(JSONObject msg) {
165 | if (isSlefSend(msg)) {
166 | return getSelfNickName();
167 | } else if (isGroupMsg(msg)) {
168 | return getGroupMemberName(msg);
169 | } else {
170 | return getUserRemarkName(msg.getString("FromUserName"));
171 | }
172 | }
173 |
174 | public boolean isGroupMsg(JSONObject msg) {
175 | return msg.getString("FromUserName").startsWith("@@");
176 | }
177 |
178 | @Override
179 | public String reply(String uid, String content) {
180 | return TulingRobot.instance().chat(uid, content);
181 | }
182 |
183 | }
184 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/IMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import com.blade.kit.json.JSONObject;
4 |
5 | public interface IMessageHandler {
6 | public void process(JSONObject msg);
7 |
8 |
9 | }
10 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/MessageManager.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import java.util.HashMap;
4 | import java.util.Map;
5 |
6 | import org.slf4j.Logger;
7 | import org.slf4j.LoggerFactory;
8 |
9 | import com.blade.kit.json.JSONArray;
10 | import com.blade.kit.json.JSONObject;
11 | import com.iyuexian.wechat4j.config.Enums.MsgType;
12 | import com.iyuexian.wechat4j.core.WechatMeta;
13 |
14 | public class MessageManager implements IMessageHandler {
15 | protected Logger logger = LoggerFactory.getLogger(MessageManager.class);
16 |
17 | private WechatMeta meta;
18 | private Map handlers = new HashMap();
19 |
20 | public MessageManager(WechatMeta meta) {
21 | this.meta = meta;
22 | register();
23 | }
24 |
25 | private IMessageHandler getMessageHandler(int type) {
26 | MsgType msgType = MsgType.getType(type);
27 | if (msgType == null)
28 | return handlers.get(MsgType.TXT);
29 | return handlers.get(msgType);
30 |
31 | }
32 |
33 | private void register() {
34 | handlers.put(MsgType.TXT, new TxtMessageHandler(meta));
35 | handlers.put(MsgType.TXT, new TxtMessageHandler(meta));
36 | handlers.put(MsgType.VOICE, new VoiceMessageHandler(meta));
37 | handlers.put(MsgType.PICTURE, new PictureMessageHandler(meta));
38 | handlers.put(MsgType.SHARE_MP, new MpMessageHandler(meta));
39 | VideoMessageHandler videoMessageHandler = new VideoMessageHandler(meta);
40 | handlers.put(MsgType.SMALL_VIDEO, videoMessageHandler);
41 | handlers.put(MsgType.VIDEO, videoMessageHandler);
42 | }
43 |
44 | @Override
45 | public void process(JSONObject data) {
46 | if (null == data) {
47 | logger.warn("data不能为空");
48 | }
49 | JSONArray AddMsgList = data.get("AddMsgList").asArray();
50 | for (int i = 0, len = AddMsgList.size(); i < len; i++) {
51 | JSONObject msg = AddMsgList.get(i).asJSONObject();
52 | processSingleMsg(msg);
53 | }
54 |
55 | }
56 |
57 | private void processSingleMsg(JSONObject msg) {
58 | int msgType = msg.getInt("MsgType", 0);
59 | if (msgType == 51) {
60 | logger.info("msgType:{},do nothing", msgType);
61 | return;
62 | }
63 | IMessageHandler messageHandler = getMessageHandler(msgType);
64 | if (messageHandler == null) {
65 | logger.error("msgType:{},无法找到对应的消息处理器", msgType);
66 | return;
67 | }
68 | messageHandler.process(msg);
69 |
70 | }
71 |
72 | }
73 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/MpMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.json.JSONObject;
7 | import com.iyuexian.wechat4j.core.WechatMeta;
8 |
9 | public class MpMessageHandler extends AbstractMessageHandler {
10 |
11 | private static final Logger LOGGER = LoggerFactory.getLogger(VoiceMessageHandler.class);
12 |
13 | public MpMessageHandler(WechatMeta meta) {
14 | super(meta);
15 | this.meta = meta;
16 | }
17 |
18 | @Override
19 | public void process(JSONObject msg) {
20 | LOGGER.info("do nothing");
21 | webwxsendmsg("不知道你在说什么", msg.getString("FromUserName"));
22 | }
23 |
24 |
25 |
26 | }
27 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/PictureMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.json.JSONObject;
7 | import com.iyuexian.wechat4j.config.Enums.MsgType;
8 | import com.iyuexian.wechat4j.core.WechatMeta;
9 |
10 | public class PictureMessageHandler extends AbstractMessageHandler {
11 |
12 | private static final Logger LOGGER = LoggerFactory.getLogger(PictureMessageHandler.class);
13 |
14 | public PictureMessageHandler(WechatMeta meta) {
15 | super(meta);
16 | this.meta = meta;
17 | }
18 |
19 | @Override
20 | public void process(JSONObject msg) {
21 | LOGGER.info("开始处理图片消息");
22 | download(msg, MsgType.PICTURE);
23 |
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/TxtMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.json.JSONObject;
7 | import com.iyuexian.wechat4j.config.Enums.MsgType;
8 | import com.iyuexian.wechat4j.core.WechatMeta;
9 | import com.iyuexian.wechat4j.plugin.storage.PipeLineManager;
10 |
11 | public class TxtMessageHandler extends AbstractMessageHandler {
12 |
13 | private static final Logger LOGGER = LoggerFactory.getLogger(TxtMessageHandler.class);
14 |
15 | // private AccountConfigDao accountConfigDao = new AccountConfigDao();
16 |
17 | public TxtMessageHandler(WechatMeta meta) {
18 | super(meta);
19 | this.meta = meta;
20 | }
21 |
22 | @Override
23 | public void process(JSONObject msg) {
24 | String content = msg.getString("Content");
25 | LOGGER.info("content:{}", content);
26 | if (!preHandle(msg)) {
27 | return;
28 | }
29 |
30 | String fromUserName = msg.getString("FromUserName");
31 | String fromNickName = getUserRemarkName(fromUserName);
32 | String selftName = getSelfNickName();
33 | String[] contentArray = content.split(":");
34 | if (contentArray.length == 0 || contentArray.length == 1) {
35 | } else {
36 | content = contentArray[1].replace("
", "\n");
37 | }
38 | PipeLineManager.instance().process(meta, fromNickName + "-" + selftName + ":" + content, MsgType.TXT);
39 | // String autoReplay = accountConfigDao.selectOne(meta.getMobile(),
40 | // AccountConfig.NAME_AUTO_REPLAY);
41 | // if (!AccountConfig.ON.equals(autoReplay)) {
42 | // LOGGER.warn("auto reply setting was off,you can switch on it");
43 | // return;
44 | // }
45 | String ans = reply(fromUserName, content);
46 | webwxsendmsg(ans, msg.getString("FromUserName"));
47 | PipeLineManager.instance().process(meta, selftName + "-" + fromNickName + ":" + ans, MsgType.TXT);
48 | }
49 |
50 | }
51 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/VideoMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.json.JSONObject;
7 | import com.iyuexian.wechat4j.config.Enums.MsgType;
8 | import com.iyuexian.wechat4j.core.WechatMeta;
9 |
10 | public class VideoMessageHandler extends AbstractMessageHandler {
11 |
12 | private static final Logger LOGGER = LoggerFactory.getLogger(VideoMessageHandler.class);
13 |
14 | public VideoMessageHandler(WechatMeta meta) {
15 | super(meta);
16 | this.meta = meta;
17 | }
18 |
19 | @Override
20 | public void process(JSONObject msg) {
21 | LOGGER.info("开始处理视频消息");
22 | download(msg, MsgType.VIDEO);
23 | }
24 |
25 |
26 |
27 | }
28 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/message/VoiceMessageHandler.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.message;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.json.JSONObject;
7 | import com.iyuexian.wechat4j.config.Enums;
8 | import com.iyuexian.wechat4j.core.WechatMeta;
9 |
10 | public class VoiceMessageHandler extends AbstractMessageHandler {
11 |
12 | private static final Logger LOGGER = LoggerFactory.getLogger(VoiceMessageHandler.class);
13 |
14 | public VoiceMessageHandler(WechatMeta meta) {
15 | super(meta);
16 | this.meta = meta;
17 | }
18 |
19 | @Override
20 | public void process(JSONObject msg) {
21 | LOGGER.info("开始处理语音消息");
22 | download(msg, Enums.MsgType.VOICE);
23 |
24 | }
25 |
26 | }
27 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/storage/FilePipeLine.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.storage;
2 |
3 | import java.io.File;
4 | import java.io.IOException;
5 | import java.nio.file.Files;
6 | import java.nio.file.Paths;
7 | import java.nio.file.StandardOpenOption;
8 |
9 | import com.iyuexian.wechat4j.config.Constant;
10 | import com.iyuexian.wechat4j.config.Enums.MsgType;
11 | import com.iyuexian.wechat4j.core.WechatMeta;
12 |
13 | public class FilePipeLine implements MessagePipeLine {
14 |
15 | @Override
16 | public void processs(WechatMeta meta, String line, MsgType msgType) {
17 |
18 | File f = new File(Constant.configReader.get("app.msg_location"));
19 | if (!f.exists()) {
20 | f.mkdirs();
21 | }
22 | try {
23 | Files.write(Paths.get(Constant.configReader.get("app.msg_location")), line.toString().getBytes(), StandardOpenOption.CREATE,
24 | StandardOpenOption.WRITE, StandardOpenOption.APPEND);
25 | } catch (IOException e) {
26 | e.printStackTrace();
27 | }
28 | }
29 | }
30 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/storage/MessagePipeLine.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.storage;
2 |
3 | import com.iyuexian.wechat4j.config.Enums.MsgType;
4 | import com.iyuexian.wechat4j.core.WechatMeta;
5 |
6 | public interface MessagePipeLine {
7 | public void processs(WechatMeta meata, String line, MsgType msgType);
8 |
9 | }
10 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/plugin/storage/PipeLineManager.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.plugin.storage;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | import com.iyuexian.wechat4j.config.Enums.MsgType;
7 | import com.iyuexian.wechat4j.core.WechatMeta;
8 |
9 | public class PipeLineManager {
10 | private List pipelines;
11 |
12 | static class Holder {
13 | static PipeLineManager instance = new PipeLineManager();
14 | }
15 |
16 | public static PipeLineManager instance() {
17 | return Holder.instance;
18 | }
19 |
20 | private PipeLineManager() {
21 | pipelines = new ArrayList();
22 | }
23 |
24 | public void process(WechatMeta meta, String line, MsgType msgType) {
25 | for (MessagePipeLine pipeLine : pipelines) {
26 | if (pipeLine != null) {
27 | pipeLine.processs(meta, line, msgType);
28 | }
29 |
30 | }
31 | }
32 | }
33 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/Converter.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | public interface Converter {
4 | public T convert(S s);
5 |
6 | }
7 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/CookieUtil.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import java.net.HttpURLConnection;
4 | import java.util.List;
5 | import java.util.Map;
6 |
7 | import com.blade.kit.http.HttpRequest;
8 |
9 | public class CookieUtil {
10 |
11 | public static String getCookie(HttpRequest request) {
12 | HttpURLConnection conn = request.getConnection();
13 | Map> resHeaders = conn.getHeaderFields();
14 | StringBuffer sBuffer = new StringBuffer();
15 | for (Map.Entry> entry : resHeaders.entrySet()) {
16 | String name = entry.getKey();
17 | if (name == null)
18 | continue; // http/1.1 line
19 | List values = entry.getValue();
20 | if (name.equalsIgnoreCase("Set-Cookie")) {
21 | for (String value : values) {
22 | if (value == null) {
23 | continue;
24 | }
25 | String cookie = value.substring(0, value.indexOf(";") + 1);
26 | sBuffer.append(cookie);
27 | }
28 | }
29 | }
30 | if (sBuffer.length() > 0) {
31 | return sBuffer.toString();
32 | }
33 | return sBuffer.toString();
34 | }
35 |
36 | public static String getValueFromCookieStr(String cookieStr, String name) {
37 |
38 | if (cookieStr == null || cookieStr.trim().length() == 0) {
39 | return null;
40 | }
41 | String[] kvPairs = cookieStr.split(";");
42 |
43 | for (String item : kvPairs) {
44 | String[] kv = item.split("=");
45 | if (kv.length == 0) {
46 | continue;
47 | }
48 |
49 | String cookieName = kv[0];
50 | if (name.equals(cookieName)) {
51 | return kv.length > 1 ? kv[1] : "";
52 | }
53 |
54 | }
55 | return "";
56 | }
57 |
58 | }
59 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/DigestUtils.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import java.security.MessageDigest;
4 | import java.security.NoSuchAlgorithmException;
5 |
6 | public abstract class DigestUtils {
7 |
8 |
9 | private static final String MD5_ALGORITHM_NAME = "MD5";
10 |
11 | private static final char[] HEX_CHARS = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
12 |
13 | /**
14 | * Calculate the MD5 digest of the given bytes.
15 | *
16 | * @param bytes
17 | * the bytes to calculate the digest over
18 | * @return the digest
19 | */
20 | public static byte[] md5Digest(byte[] bytes) {
21 | return digest(MD5_ALGORITHM_NAME, bytes);
22 | }
23 |
24 | /**
25 | * Return a hexadecimal string representation of the MD5 digest of the given
26 | * bytes.
27 | *
28 | * @param bytes
29 | * the bytes to calculate the digest over
30 | * @return a hexadecimal digest string
31 | */
32 | public static String md5DigestAsHex(byte[] bytes) {
33 | return digestAsHexString(MD5_ALGORITHM_NAME, bytes);
34 | }
35 |
36 | /**
37 | * Append a hexadecimal string representation of the MD5 digest of the given
38 | * bytes to the given {@link StringBuilder}.
39 | *
40 | * @param bytes
41 | * the bytes to calculate the digest over
42 | * @param builder
43 | * the string builder to append the digest to
44 | * @return the given string builder
45 | */
46 | public static StringBuilder appendMd5DigestAsHex(byte[] bytes, StringBuilder builder) {
47 | return appendDigestAsHex(MD5_ALGORITHM_NAME, bytes, builder);
48 | }
49 |
50 | /**
51 | * Creates a new {@link MessageDigest} with the given algorithm. Necessary
52 | * because {@code MessageDigest} is not thread-safe.
53 | */
54 | private static MessageDigest getDigest(String algorithm) {
55 | try {
56 | return MessageDigest.getInstance(algorithm);
57 | } catch (NoSuchAlgorithmException ex) {
58 | throw new IllegalStateException("Could not find MessageDigest with algorithm \"" + algorithm + "\"", ex);
59 | }
60 | }
61 |
62 | private static byte[] digest(String algorithm, byte[] bytes) {
63 | return getDigest(algorithm).digest(bytes);
64 | }
65 |
66 | private static String digestAsHexString(String algorithm, byte[] bytes) {
67 | char[] hexDigest = digestAsHexChars(algorithm, bytes);
68 | return new String(hexDigest);
69 | }
70 |
71 | private static StringBuilder appendDigestAsHex(String algorithm, byte[] bytes, StringBuilder builder) {
72 | char[] hexDigest = digestAsHexChars(algorithm, bytes);
73 | return builder.append(hexDigest);
74 | }
75 |
76 | private static char[] digestAsHexChars(String algorithm, byte[] bytes) {
77 | byte[] digest = digest(algorithm, bytes);
78 | return encodeHex(digest);
79 | }
80 |
81 | private static char[] encodeHex(byte[] bytes) {
82 | char chars[] = new char[32];
83 | for (int i = 0; i < chars.length; i = i + 2) {
84 | byte b = bytes[i / 2];
85 | chars[i] = HEX_CHARS[(b >>> 0x4) & 0xf];
86 | chars[i + 1] = HEX_CHARS[b & 0xf];
87 | }
88 | return chars;
89 | }
90 |
91 | }
92 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/Emptys.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | /**
4 | * Copyright (c) 2015, biezhi 王爵 (biezhi.me@gmail.com)
5 | *
6 | * Licensed under the Apache License, Version 2.0 (the "License");
7 | * you may not use this file except in compliance with the License.
8 | * You may obtain a copy of the License at
9 | *
10 | * http://www.apache.org/licenses/LICENSE-2.0
11 | *
12 | * Unless required by applicable law or agreed to in writing, software
13 | * distributed under the License is distributed on an "AS IS" BASIS,
14 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 | * See the License for the specific language governing permissions and
16 | * limitations under the License.
17 | */
18 |
19 | import java.io.Serializable;
20 |
21 | /**
22 | * 定义各种代表“空”的常量
23 | *
24 | * @author biezhi
25 | * @since 1.0
26 | */
27 | public abstract class Emptys {
28 |
29 | // =============================================================
30 | // 数组常量
31 | // =============================================================
32 |
33 | // primitive arrays
34 |
35 | /** 空的byte数组。 */
36 | public static final byte[] EMPTY_BYTE_ARRAY = new byte[0];
37 | public static final Byte[] EMPTY_BYTE_OBJECT_ARRAY = new Byte[0];
38 |
39 | /** 空的short数组。 */
40 | public static final short[] EMPTY_SHORT_ARRAY = new short[0];
41 | public static final Short[] EMPTY_SHORT_OBJECT_ARRAY = new Short[0];
42 |
43 | /** 空的int数组。 */
44 | public static final int[] EMPTY_INT_ARRAY = new int[0];
45 | public static final Integer[] EMPTY_INTEGER_OBJECT_ARRAY = new Integer[0];
46 |
47 | /** 空的long数组。 */
48 | public static final long[] EMPTY_LONG_ARRAY = new long[0];
49 | public static final Long[] EMPTY_LONG_OBJECT_ARRAY = new Long[0];
50 |
51 | /** 空的float数组。 */
52 | public static final float[] EMPTY_FLOAT_ARRAY = new float[0];
53 | public static final Float[] EMPTY_FLOAT_OBJECT_ARRAY = new Float[0];
54 |
55 | /** 空的double数组。 */
56 | public static final double[] EMPTY_DOUBLE_ARRAY = new double[0];
57 | public static final Double[] EMPTY_DOUBLE_OBJECT_ARRAY = new Double[0];
58 |
59 | /** 空的char数组。 */
60 | public static final char[] EMPTY_CHAR_ARRAY = new char[0];
61 | public static final Character[] EMPTY_CHARACTER_OBJECT_ARRAY = new Character[0];
62 |
63 | /** 空的boolean数组。 */
64 | public static final boolean[] EMPTY_BOOLEAN_ARRAY = new boolean[0];
65 | public static final Boolean[] EMPTY_BOOLEAN_OBJECT_ARRAY = new Boolean[0];
66 |
67 | // object arrays
68 |
69 | /** 空的Object数组。 */
70 | public static final Object[] EMPTY_OBJECT_ARRAY = new Object[0];
71 |
72 | /** 空的Class数组。 */
73 | public static final Class>[] EMPTY_CLASS_ARRAY = new Class[0];
74 |
75 | /** 空的String数组。 */
76 | public static final String[] EMPTY_STRING_ARRAY = new String[0];
77 |
78 | // =============================================================
79 | // 对象常量
80 | // =============================================================
81 |
82 | // 0-valued primitive wrappers
83 | public static final Byte BYTE_ZERO = new Byte((byte) 0);
84 | public static final Short SHORT_ZERO = new Short((short) 0);
85 | public static final Integer INT_ZERO = new Integer(0);
86 | public static final Long LONG_ZERO = new Long(0L);
87 | public static final Float FLOAT_ZERO = new Float(0);
88 | public static final Double DOUBLE_ZERO = new Double(0);
89 | public static final Character CHAR_NULL = new Character('\0');
90 | public static final Boolean BOOL_FALSE = Boolean.FALSE;
91 |
92 | /** 代表null值的占位对象。 */
93 | public static final Object NULL_PLACEHOLDER = new NullPlaceholder();
94 |
95 | private final static class NullPlaceholder implements Serializable {
96 |
97 | /**
98 | *
99 | */
100 | private static final long serialVersionUID = 5893921848518437319L;
101 |
102 | @Override
103 | public String toString() {
104 | return "null";
105 | }
106 |
107 | private Object readResolve() {
108 | return NULL_PLACEHOLDER;
109 | }
110 | }
111 |
112 | /** 空字符串。 */
113 | public static final String EMPTY_STRING = "";
114 |
115 | }
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/FileUploadHelper.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import java.io.InputStream;
4 | import java.util.Calendar;
5 | import java.util.UUID;
6 |
7 | import org.apache.commons.io.IOUtils;
8 |
9 | import com.iyuexian.wechat4j.config.Constant;
10 | import com.qiniu.http.Response;
11 | import com.qiniu.storage.UploadManager;
12 | import com.qiniu.util.Auth;
13 |
14 | public class FileUploadHelper {
15 |
16 | private String ak = Constant.configReader.get(Constant.QINIU_AK);
17 | private String secret = Constant.configReader.get(Constant.QINIU_SK);
18 | private String bucket = Constant.configReader.get(Constant.QINIU_BUCKET_IMAGE0);
19 | private UploadManager uploadManager = new UploadManager();
20 |
21 | public FileUploadHelper(String ak, String secret, String bucket, UploadManager uploadManager) {
22 | if (ak != null && ak.trim().length() > 0)
23 | this.ak = ak;
24 |
25 | if (secret != null && secret.trim().length() > 0)
26 | this.secret = secret;
27 |
28 | if (bucket != null && bucket.trim().length() > 0)
29 | this.bucket = bucket;
30 |
31 | if (uploadManager != null) {
32 | this.uploadManager = uploadManager;
33 | }
34 |
35 | }
36 |
37 | public FileUploadHelper(String ak, String secret, String bucket) {
38 | this(ak, secret, bucket, null);
39 | }
40 |
41 | public FileUploadHelper(String ak, String secret) {
42 | this(ak, secret, null, null);
43 | }
44 |
45 | public FileUploadHelper() {
46 | this(null, null, null, null);
47 | }
48 |
49 | public static String generateFileKey(String fileName) {
50 | String ext = fileName.lastIndexOf(".") > 0 ? fileName.substring(fileName.lastIndexOf(".")) : "";
51 | return Calendar.getInstance().get(Calendar.YEAR) + "/" + UUID.randomUUID().toString().replace("-", "").toLowerCase() + ext;
52 | }
53 |
54 | public String uploadToQiniu(InputStream is, String fileName) {
55 | try {
56 | String host = Constant.configReader.get(Constant.QIUNIU_IMG_URL);
57 | String fileKey = generateFileKey(fileName);
58 | Auth auth = Auth.create(ak, secret);
59 | String uploadToken = auth.uploadToken(bucket);
60 | byte[] buffer = new byte[is.available()];
61 | IOUtils.readFully(is, buffer);
62 | Response response = uploadManager.put(buffer, fileKey, uploadToken);
63 | return response.isOK() ? host + fileKey : "";
64 | } catch (Exception ex) {
65 | return "";
66 | }
67 |
68 | }
69 |
70 | public String uploadToQiniu(byte[] bytes, String originalName) {
71 | try {
72 | Auth auth = Auth.create(ak, secret);
73 | String uploadToken = auth.uploadToken(bucket);
74 | String fileKey = generateFileKey(originalName);
75 | Response response = uploadManager.put(bytes, fileKey, uploadToken);
76 | if (!response.isOK()) {
77 | return "";
78 | }
79 | String host = Constant.configReader.get(Constant.QIUNIU_IMG_URL);
80 | return host + fileKey;
81 | } catch (Exception ex) {
82 | ex.printStackTrace();
83 | return "";
84 | }
85 | }
86 |
87 | }
88 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/FileUtil.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import java.io.File;
4 | import java.io.FileInputStream;
5 | import java.io.IOException;
6 | import java.nio.file.Files;
7 | import java.nio.file.Path;
8 | import java.security.MessageDigest;
9 | import java.security.NoSuchAlgorithmException;
10 |
11 | import org.slf4j.Logger;
12 | import org.slf4j.LoggerFactory;
13 |
14 | public class FileUtil {
15 |
16 | protected static final Logger logger = LoggerFactory.getLogger(FileUtil.class);
17 |
18 | private static final char[] HEX_CHARS = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
19 |
20 |
21 |
22 | public static final String getContentType(Path path, String defaultValue) {
23 | try {
24 | return Files.probeContentType(path);
25 | } catch (IOException e) {
26 | return defaultValue;
27 | }
28 | }
29 |
30 | public static boolean isVideo(String contentType) {
31 | // TODO
32 | return false;
33 | }
34 |
35 | public static boolean isPicture(String contentType) {
36 | if (contentType == null)
37 | return false;
38 | return contentType.contains("image");
39 | }
40 |
41 | public static boolean isDoc(String contentType) {
42 | if (contentType == null)
43 | return false;
44 | return contentType.contains("document") || contentType.contains("vnd.openxml");
45 | }
46 |
47 | /**
48 | * 计算文件的MD5码
49 | *
50 | * @param file
51 | * @return
52 | */
53 | public static String getMD5(File file) {
54 | FileInputStream fis = null;
55 | try {
56 | MessageDigest md = MessageDigest.getInstance("MD5");
57 | fis = new FileInputStream(file);
58 | byte[] buffer = new byte[8192];
59 | int length = -1;
60 | while ((length = fis.read(buffer)) != -1) {
61 | md.update(buffer, 0, length);
62 | }
63 | return new String(encodeHex(md.digest()));
64 | } catch (IOException ex) {
65 | logger.warn(ex.toString());
66 | return null;
67 | } catch (NoSuchAlgorithmException ex) {
68 | logger.warn(ex.toString());
69 | return null;
70 | } finally {
71 | try {
72 | fis.close();
73 | } catch (IOException ex) {
74 | logger.warn(ex.toString());
75 | }
76 | }
77 | }
78 |
79 | private static char[] encodeHex(byte[] bytes) {
80 | char chars[] = new char[32];
81 | for (int i = 0; i < chars.length; i = i + 2) {
82 | byte b = bytes[i / 2];
83 | chars[i] = HEX_CHARS[(b >>> 0x4) & 0xf];
84 | chars[i + 1] = HEX_CHARS[b & 0xf];
85 | }
86 | return chars;
87 | }
88 |
89 | /**
90 | * 得到文件的SHA码,用于校验
91 | *
92 | * @param file
93 | * @return
94 | */
95 | public static String getSHA(File file) {
96 | FileInputStream fis = null;
97 | try {
98 | MessageDigest md = MessageDigest.getInstance("SHA");
99 | fis = new FileInputStream(file);
100 | byte[] buffer = new byte[8192];
101 | int length = -1;
102 | while ((length = fis.read(buffer)) != -1) {
103 | md.update(buffer, 0, length);
104 | }
105 | return new String(encodeHex(md.digest()));
106 | } catch (IOException ex) {
107 | logger.warn(ex.toString());
108 | return null;
109 | } catch (NoSuchAlgorithmException ex) {
110 | logger.warn(ex.toString());
111 | return null;
112 | } finally {
113 | try {
114 | fis.close();
115 | } catch (IOException ex) {
116 | logger.warn(ex.toString());
117 | }
118 | }
119 | }
120 |
121 | }
122 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/HttpClient.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import org.slf4j.Logger;
4 | import org.slf4j.LoggerFactory;
5 |
6 | import com.blade.kit.StringKit;
7 | import com.blade.kit.http.HttpRequest;
8 | import com.blade.kit.json.JSONKit;
9 | import com.blade.kit.json.JSONObject;
10 | import com.iyuexian.wechat4j.core.WechatMeta;
11 | import com.iyuexian.wechat4j.exception.WechatException;
12 |
13 | public class HttpClient {
14 |
15 | public static Logger LOGGER = LoggerFactory.getLogger(HttpClient.class);
16 | private WechatMeta meta;
17 |
18 | public HttpClient(WechatMeta meta) {
19 | super();
20 | this.meta = meta;
21 | }
22 |
23 | public JSONObject postJSON(String url, JSONObject body) {
24 | HttpRequest request = HttpRequest.post(url).contentType("application/json;charset=utf-8").header("Cookie", meta.getCookie())
25 | .send(body.toString());
26 | String res = request.body();
27 | request.disconnect();
28 | if (StringKit.isBlank(res)) {
29 | throw new WechatException("请求微信接口异常");
30 | }
31 |
32 | JSONObject jsonObject = JSONKit.parseObject(res);
33 | JSONObject BaseResponse = jsonObject.get("BaseResponse").asJSONObject();
34 | if (null == BaseResponse || BaseResponse.getInt("Ret", -1) != 0) {
35 | LOGGER.warn("操作失败,{}", jsonObject);
36 | }
37 | return jsonObject;
38 | }
39 |
40 | }
41 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/IOKit.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 |
4 |
5 | import java.io.BufferedReader;
6 | import java.io.Closeable;
7 | import java.io.File;
8 | import java.io.FileOutputStream;
9 | import java.io.FileReader;
10 | import java.io.IOException;
11 | import java.io.InputStream;
12 | import java.io.InputStreamReader;
13 | import java.io.OutputStream;
14 | import java.io.PrintWriter;
15 | import java.io.Reader;
16 | import java.io.StringWriter;
17 | import java.io.Writer;
18 | import java.net.HttpURLConnection;
19 | import java.net.ServerSocket;
20 | import java.net.Socket;
21 | import java.net.URLConnection;
22 | import java.nio.channels.Selector;
23 | import java.nio.charset.Charset;
24 | import java.util.zip.ZipFile;
25 |
26 |
27 | /**
28 | * IO工具类
29 | *
30 | * @author biezhi
31 | * @since 1.0
32 | */
33 | public final class IOKit {
34 |
35 | public static final String LINE_SEPARATOR;
36 |
37 | private static final int EOF = -1;
38 |
39 | static {
40 | // avoid security issues
41 | StringWriter buf = new StringWriter(4); // NOSONAR
42 | PrintWriter out = new PrintWriter(buf);
43 | out.println();
44 | LINE_SEPARATOR = buf.toString();
45 | }
46 |
47 | /**
48 | * The default buffer size to use.
49 | */
50 | public static final int DEFAULT_BUFFER_SIZE = 0x1000;
51 |
52 | private IOKit() {
53 | }
54 |
55 | public static String toString(InputStream input) throws IOException {
56 | StringWriter sw = new StringWriter();
57 | copy(input, sw);
58 | return sw.toString();
59 | }
60 |
61 | public static String toString(File file) throws IOException {
62 | try {
63 | BufferedReader reader = new BufferedReader(new FileReader(file));
64 | StringBuilder data = readFromBufferedReader(reader);
65 | reader.close();
66 | return new String(data.toString().getBytes(), "utf-8");
67 | } catch (IOException ex) {
68 | throw new RuntimeException("File " + file + " not found.");
69 | }
70 | }
71 |
72 | private static StringBuilder readFromBufferedReader(BufferedReader reader) throws IOException {
73 | StringBuilder builder = new StringBuilder();
74 | char[] buffer = new char[DEFAULT_BUFFER_SIZE];
75 | int numRead = 0;
76 | while((numRead = reader.read(buffer)) != EOF) {
77 | builder.append(String.valueOf(buffer, 0, numRead));
78 | buffer = new char[DEFAULT_BUFFER_SIZE];
79 | }
80 | return builder;
81 | }
82 |
83 |
84 |
85 |
86 | public static long copyLarge(final InputStream input, final OutputStream output)
87 | throws IOException {
88 | byte[] buffer = new byte[DEFAULT_BUFFER_SIZE];
89 | long count = 0L;
90 | int n = 0;
91 | while (EOF != (n = input.read(buffer))) {
92 | output.write(buffer, 0, n);
93 | count += n;
94 | }
95 | return count;
96 | }
97 |
98 | public static void copy(InputStream input, Writer output)
99 | throws IOException {
100 | InputStreamReader in = new InputStreamReader(input); // NOSONAR
101 | copy(in, output);
102 | }
103 |
104 | public static long copyLarge(Reader input, Writer output) throws IOException {
105 | char[] buffer = new char[DEFAULT_BUFFER_SIZE];
106 | long count = 0L;
107 | int n = 0;
108 | while (EOF != (n = input.read(buffer))) {
109 | output.write(buffer, 0, n);
110 | count += n;
111 | }
112 | return count;
113 | }
114 |
115 | public static void write(byte[] data, File file) {
116 | OutputStream os = null;
117 | try {
118 | os = new FileOutputStream(file);
119 | os.write(data);
120 | } catch (IOException e) {
121 | throw new IllegalStateException(e);
122 | } finally {
123 | closeQuietly(os);
124 | }
125 | }
126 |
127 | public static void write(char[] data, File file, String charsetName) {
128 | write(data, file, Charset.forName(charsetName));
129 | }
130 |
131 | public static void write(char[] data, File file, Charset charset) {
132 | OutputStream os = null;
133 | try {
134 | os = new FileOutputStream(file);
135 | os.write(new String(data).getBytes(charset));
136 | } catch (IOException e) {
137 | throw new IllegalStateException(e);
138 | } finally {
139 | closeQuietly(os);
140 | }
141 | }
142 |
143 | public static void write(String data, File file, String charsetName) {
144 | write(data, file, Charset.forName(charsetName));
145 | }
146 |
147 | public static void write(String data, File file, Charset charset) {
148 | OutputStream os = null;
149 | try {
150 | os = new FileOutputStream(file);
151 | os.write(data.getBytes(charset));
152 | } catch (IOException e) {
153 | throw new IllegalStateException(e);
154 | } finally {
155 | closeQuietly(os);
156 | }
157 | }
158 |
159 | public static int copy(InputStream input, OutputStream output)
160 | throws IOException {
161 | long count = copyLarge(input, output);
162 | if (count > Integer.MAX_VALUE) {
163 | return -1;
164 | }
165 | return (int) count;
166 | }
167 |
168 | public static int copy(InputStream input, Writer output, String charsetName)
169 | throws IOException {
170 | return copy(new InputStreamReader(input, Charset.forName(charsetName)),
171 | output);
172 | }
173 |
174 | public static int copy(InputStream input, Writer output, Charset charset)
175 | throws IOException {
176 | return copy(new InputStreamReader(input, charset), output);
177 | }
178 |
179 | public static int copy(Reader input, Writer output) throws IOException {
180 | long count = copyLarge(input, output);
181 | if (count > Integer.MAX_VALUE) {
182 | return -1;
183 | }
184 | return (int) count;
185 | }
186 |
187 | public static void closeQuietly(ZipFile obj) {
188 | try {
189 | if (obj != null) {
190 | obj.close();
191 | }
192 | } catch (IOException e) {
193 | }
194 | }
195 |
196 | public static void closeQuietly(Socket socket) {
197 | try {
198 | if (socket != null) {
199 | socket.close();
200 | }
201 | } catch (IOException e) {
202 | }
203 | }
204 |
205 | public static void closeQuietly(ServerSocket socket) {
206 | try {
207 | if (socket != null) {
208 | socket.close();
209 | }
210 | } catch (IOException e) {
211 | }
212 | }
213 |
214 | public static void closeQuietly(Selector selector) {
215 | try {
216 | if (selector != null) {
217 | selector.close();
218 | }
219 | } catch (IOException e) {
220 | }
221 | }
222 |
223 | public static void closeQuietly(URLConnection conn) {
224 | if (conn != null) {
225 | if (conn instanceof HttpURLConnection) {
226 | ((HttpURLConnection) conn).disconnect();
227 | }
228 | }
229 | }
230 |
231 | public static void closeQuietly(Closeable closeable) {
232 | if (null != closeable) {
233 | try {
234 | closeable.close();
235 | } catch (IOException e) {
236 | e.printStackTrace();
237 | }
238 | }
239 | }
240 |
241 | public static String toString(Reader input) throws IOException {
242 | StringBuilder output = new StringBuilder();
243 | char[] buffer = new char[DEFAULT_BUFFER_SIZE];
244 | int n;
245 | while (EOF != (n = input.read(buffer))) {
246 | output.append(buffer, 0, n);
247 | }
248 | return output.toString();
249 | }
250 | }
251 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/Matchers.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 |
4 | import java.util.regex.Matcher;
5 | import java.util.regex.Pattern;
6 |
7 | public class Matchers {
8 |
9 | public static String match(String p, String str){
10 | Pattern pattern = Pattern.compile(p);
11 | Matcher m = pattern.matcher(str);
12 | if(m.find()){
13 | return m.group(1);
14 | }
15 | return null;
16 | }
17 |
18 | }
19 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/PropertyReader.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import java.io.File;
4 | import java.io.FileInputStream;
5 | import java.io.IOException;
6 | import java.io.InputStream;
7 | import java.io.UnsupportedEncodingException;
8 | import java.net.URL;
9 | import java.net.URLDecoder;
10 | import java.util.HashMap;
11 | import java.util.Map;
12 | import java.util.Properties;
13 |
14 | import org.slf4j.Logger;
15 | import org.slf4j.LoggerFactory;
16 |
17 | public class PropertyReader {
18 |
19 | private static final Logger LOGGER = LoggerFactory.getLogger(PropertyReader.class);
20 |
21 | private final Map config;
22 |
23 | public PropertyReader() {
24 | config = new HashMap(32);
25 | }
26 |
27 | public PropertyReader load(Properties props) {
28 | for (String key : props.stringPropertyNames()) {
29 | String value = props.getProperty(key);
30 | config.put(key, value);
31 | }
32 | return this;
33 | }
34 |
35 | /*
36 | * private String getWildcard(String str) { if (null != str && str.indexOf("${")
37 | * != -1) { int start = str.indexOf("${"); int end = str.indexOf("}"); if (start
38 | * != -1 && end != -1) { return str.substring(start + 2, end); } } return null;
39 | * }
40 | */
41 |
42 | public PropertyReader load(Map map) {
43 | config.putAll(map);
44 | return this;
45 | }
46 |
47 | /**
48 | * 从文件路径或者classpath路径中载入配置.
49 | *
50 | * @param location
51 | * - 配置文件路径
52 | * @return this
53 | */
54 | public static PropertyReader load(String location) {
55 | return new PropertyReader().loadLoaction(location);
56 | }
57 |
58 | private PropertyReader loadLoaction(String location) {
59 | if (location.startsWith("classpath:")) {
60 | location = location.substring("classpath:".length());
61 | return loadClasspath(location);
62 | } else if (location.startsWith("file:")) {
63 | location = location.substring("file:".length());
64 | return load(new File(location));
65 | } else {
66 | return loadClasspath(location);
67 | }
68 | }
69 |
70 | public void add(String location) {
71 | PropertyReader config = loadLoaction(location);
72 | if (null != config) {
73 | this.config.putAll(config.asMap());
74 | }
75 | }
76 |
77 | // 从 URL 载入
78 | public PropertyReader load(URL url) {
79 | String location = url.getPath();
80 | try {
81 | location = URLDecoder.decode(location, "utf-8");
82 | } catch (UnsupportedEncodingException e) {
83 | }
84 |
85 | try {
86 | return loadInputStream(url.openStream(), location);
87 | } catch (IOException e) {
88 | throw new IllegalStateException(e);
89 | }
90 | }
91 |
92 | // 从 classpath 下面载入
93 | private PropertyReader loadClasspath(String classpath) {
94 | if (classpath.startsWith("/")) {
95 | classpath = classpath.substring(1);
96 | }
97 | InputStream is = getDefault().getResourceAsStream(classpath);
98 | LOGGER.info("Load config [classpath:" + classpath + "]");
99 | return loadInputStream(is, classpath);
100 | }
101 |
102 | // 从 File 载入
103 | public PropertyReader load(File file) {
104 | try {
105 | LOGGER.info("Load config [file:" + file.getPath() + "]");
106 | return loadInputStream(new FileInputStream(file), file.getName());
107 | } catch (IOException e) {
108 | throw new IllegalStateException(e);
109 | }
110 | }
111 |
112 | private PropertyReader loadInputStream(InputStream is, String location) {
113 | if (is == null) {
114 | throw new IllegalStateException("InputStream not found: " + location);
115 | }
116 | location = location.toLowerCase();
117 | try {
118 | Properties config = new Properties();
119 | config.load(is);
120 | load(config);
121 | return this;
122 | } catch (IOException e) {
123 | throw new IllegalStateException(e);
124 | } finally {
125 | IOKit.closeQuietly(is);
126 | }
127 | }
128 |
129 | public PropertyReader loadSystemProperties() {
130 | return load(System.getProperties());
131 | }
132 |
133 | public PropertyReader loadSystemEnvs() {
134 | return load(System.getenv());
135 | }
136 |
137 | public Map asMap() {
138 | return this.config;
139 | }
140 |
141 | /**
142 | * Returns current thread's context class loader
143 | */
144 | private static ClassLoader getDefault() {
145 | ClassLoader loader = null;
146 | try {
147 | loader = Thread.currentThread().getContextClassLoader();
148 | } catch (Exception e) {
149 | }
150 | if (loader == null) {
151 | loader = PropertyReader.class.getClassLoader();
152 | if (loader == null) {
153 | try {
154 | // getClassLoader() returning null indicates the bootstrap
155 | // ClassLoader
156 | loader = ClassLoader.getSystemClassLoader();
157 | } catch (Exception e) {
158 | // Cannot access system ClassLoader - oh well, maybe the
159 | // caller can live with null...
160 | }
161 | }
162 | }
163 | return loader;
164 | }
165 |
166 | public String get(String key) {
167 | return config.get(key);
168 | }
169 |
170 | public String get(String key, String defaultValue) {
171 | return null != config.get(key) ? config.get(key) : defaultValue;
172 | }
173 |
174 | public Integer getInt(String key) {
175 | String value = get(key);
176 | if (isNotBlank(value)) {
177 | return Integer.valueOf(value);
178 | }
179 | return null;
180 | }
181 |
182 | public Integer getInt(String key, Integer defaultValue) {
183 | return null != getInt(key) ? getInt(key) : defaultValue;
184 | }
185 |
186 | public Long getLong(String key) {
187 | String value = get(key);
188 | if (isNotBlank(value)) {
189 | return Long.valueOf(value);
190 | }
191 | return null;
192 | }
193 |
194 | public Long getLong(String key, Long defaultValue) {
195 | return null != getLong(key) ? getLong(key) : defaultValue;
196 | }
197 |
198 | public Double getDouble(String key) {
199 | String value = get(key);
200 | if (isNotBlank(value)) {
201 | return Double.valueOf(value);
202 | }
203 | return null;
204 | }
205 |
206 | public double getDouble(String key, double defaultValue) {
207 | return null != getDouble(key) ? getDouble(key) : defaultValue;
208 | }
209 |
210 | public Boolean getBoolean(String key) {
211 | String value = get(key);
212 | if (isNotBlank(value)) {
213 | return Boolean.valueOf(value);
214 | }
215 | return null;
216 | }
217 |
218 | public Boolean getBoolean(String key, boolean defaultValue) {
219 | return null != getBoolean(key) ? getBoolean(key) : defaultValue;
220 | }
221 |
222 | public boolean isNotBlank(String str) {
223 | return str != null && str.trim().length() > 0;
224 | }
225 |
226 | }
227 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/java/com/iyuexian/wechat4j/util/TulingUtil.java:
--------------------------------------------------------------------------------
1 | package com.iyuexian.wechat4j.util;
2 |
3 | import java.io.BufferedReader;
4 | import java.io.IOException;
5 | import java.io.InputStreamReader;
6 | import java.io.OutputStreamWriter;
7 | import java.io.UnsupportedEncodingException;
8 | import java.net.HttpURLConnection;
9 | import java.net.URL;
10 | import java.security.Key;
11 | import java.security.MessageDigest;
12 |
13 | import javax.crypto.Cipher;
14 | import javax.crypto.spec.IvParameterSpec;
15 | import javax.crypto.spec.SecretKeySpec;
16 |
17 | import com.blade.kit.Base64;
18 |
19 | public class TulingUtil {
20 |
21 | /**
22 | * 向后台发送post请求
23 | *
24 | * @param param
25 | * @param url
26 | * @return
27 | * @throws IOException
28 | * @throws UnsupportedEncodingException
29 | */
30 | public static String sendPost(String param, String url) throws Exception {
31 | OutputStreamWriter out = null;
32 | BufferedReader in = null;
33 | String result = "";
34 | URL realUrl = new URL(url);
35 | HttpURLConnection conn = (HttpURLConnection) realUrl.openConnection();
36 | conn.setDoOutput(true);
37 | conn.setDoInput(true);
38 | conn.setUseCaches(false);
39 | conn.setRequestMethod("POST");
40 | conn.setConnectTimeout(50000);
41 | conn.setReadTimeout(50000);
42 | conn.setRequestProperty("Content-Type", "application/json");
43 | conn.setRequestProperty("Accept", "application/json");
44 | conn.setRequestProperty("Authorization", "token");
45 | conn.setRequestProperty("tag", "htc_new");
46 | conn.connect();
47 | out = new OutputStreamWriter(conn.getOutputStream(), "UTF-8");
48 | out.write(param);
49 | out.flush();
50 | out.close();
51 | in = new BufferedReader(new InputStreamReader(conn.getInputStream(), "UTF-8"));
52 | String line = "";
53 | while ((line = in.readLine()) != null) {
54 | result += line;
55 | }
56 | return result;
57 | }
58 |
59 | /**
60 | * 加密方法
61 | *
62 | * 说明:采用128位
63 | *
64 | * @return 加密结果
65 | * @throws Exception
66 | */
67 | public static String encrypt(String strKey, String strContent) throws Exception {
68 |
69 | Key key = new SecretKeySpec(getHash("MD5", strKey), "AES");
70 | IvParameterSpec iv = new IvParameterSpec(new byte[] { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 });
71 | Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
72 | byte[] data = strContent.getBytes("UTF-8");
73 | cipher.init(Cipher.ENCRYPT_MODE, key, iv);
74 | byte[] encryptData = cipher.doFinal(data);
75 | String encryptResult = new String(Base64.encodeBytes(encryptData));
76 | return encryptResult;
77 | }
78 |
79 | /**
80 | *
81 | * @param algorithm
82 | * @param text
83 | * @return
84 | * @throws Exception
85 | */
86 | public static byte[] getHash(String algorithm, String text) throws Exception {
87 | byte[] bytes = text.getBytes("UTF-8");
88 | final MessageDigest digest = MessageDigest.getInstance(algorithm);
89 | digest.update(bytes);
90 | return digest.digest();
91 | }
92 |
93 | /**
94 | * MD5加密算法
95 | *
96 | * 说明:32位加密算法
97 | *
98 | * @param 待加密的数据
99 | * @return 加密结果,全小写的字符串
100 | * @throws Exception
101 | */
102 | public static String MD5(String s) throws Exception {
103 | char hexDigits[] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
104 | byte[] btInput = s.getBytes("utf-8");
105 | // 获得MD5摘要算法的 MessageDigest 对象
106 | MessageDigest mdInst = MessageDigest.getInstance("MD5");
107 | // 使用指定的字节更新摘要
108 | mdInst.update(btInput);
109 | // 获得密文
110 | byte[] md = mdInst.digest();
111 | // 把密文转换成十六进制的字符串形式
112 | int j = md.length;
113 | char str[] = new char[j * 2];
114 | int k = 0;
115 | for (int i = 0; i < j; i++) {
116 | byte byte0 = md[i];
117 | str[k++] = hexDigits[byte0 >>> 4 & 0xf];
118 | str[k++] = hexDigits[byte0 & 0xf];
119 | }
120 | return new String(str);
121 | }
122 | }
123 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/resources/config.properties:
--------------------------------------------------------------------------------
1 | # media save path
2 | app.media_path=C\:/wechat
3 | app.msg_location=C\:/wechat/msg.txt
4 |
5 | db.url=jdbc\:mysql\://rm-8vbl9c7po6w334tr4o.mysql.zhangbei.rds.aliyuncs.com\:3306/xmall?&useUnicode\=true&characterEncoding\=UTF-8&autoReconnect\=true&failOverReadOnly\=false&zeroDateTimeBehavior\=convertToNull
6 | db.username=root
7 | db.pass=123456
8 |
9 | qiniu_ak=0FlyZYZsYM6xhaW2UM2gREQ2dINcz59M-PP6cIby10
10 | qiniu_sk=0Zo0gLdlp9uYsh2T312iCm4kUeKVu5_j295Wlm5O80
11 | qiuniu_img_url=http\://img.iyuexian.com/
12 | qiuniu_video_url=http\://v.iyuexian.com/
13 | qiniu_bucket_image0=image1
14 | qiniu_bucket_video=video
15 |
--------------------------------------------------------------------------------
/wechat4j-common/src/main/resources/log4j.properties:
--------------------------------------------------------------------------------
1 | log4j.rootLogger=debug,console
2 |
3 | #log4j.appender.stdout = org.apache.log4j.ConsoleAppender
4 | #log4j.appender.stdout.layout = org.apache.log4j.PatternLayout
5 | #log4j.appender.stdout.layout.ConversionPattern = %d %-5p => %m%n
6 |
7 |
8 | log4j.appender.console=org.apache.log4j.ConsoleAppender
9 | log4j.appender.console.Target=System.out
10 | log4j.appender.console.layout=org.apache.log4j.PatternLayout
11 | log4j.appender.console.layout.ConversionPattern=wechat4j-[%-5p] %d{MM-dd HH\:mm\:ss} %l\: %m %x %n
12 | #log4j.appender.console.layout.ConversionPattern=wechat4j-[%-5p] %d{MM-dd HH\:mm}:%m %n
--------------------------------------------------------------------------------
/wechat4j-common/src/main/resources/logging.properties:
--------------------------------------------------------------------------------
1 | handlers = org.apache.juli.FileHandler, java.util.logging.ConsoleHandler
2 |
3 | ############################################################
4 | # Handler specific properties.
5 | # Describes specific configuration info for Handlers.
6 | ############################################################
7 |
8 | org.apache.juli.FileHandler.level = FINE
9 | org.apache.juli.FileHandler.directory = ${catalina.base}/logs
10 | org.apache.juli.FileHandler.prefix = error-debug.
11 |
12 | java.util.logging.ConsoleHandler.level = FINE
13 | java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/.gitignore:
--------------------------------------------------------------------------------
1 | /com/
2 | /META-INF/
3 |
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/META-INF/MANIFEST.MF:
--------------------------------------------------------------------------------
1 | Manifest-Version: 1.0
2 | Built-By: hexia
3 | Build-Jdk: 1.8.0_101
4 | Created-By: Maven Integration for Eclipse
5 |
6 |
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/META-INF/maven/com.iyuexian.wechat4j/wechat4j-common/pom.properties:
--------------------------------------------------------------------------------
1 | #Generated by Maven Integration for Eclipse
2 | #Sat Jul 21 15:08:17 CST 2018
3 | version=0.0.1-SNAPSHOT
4 | groupId=com.iyuexian.wechat4j
5 | m2e.projectName=wechat4j-common
6 | m2e.projectLocation=C\:\\Users\\hexia\\git\\wechat4j\\README.md\\wechat4j-common
7 | artifactId=wechat4j-common
8 |
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/META-INF/maven/com.iyuexian.wechat4j/wechat4j-common/pom.xml:
--------------------------------------------------------------------------------
1 |
3 | 4.0.0
4 | com.iyuexian.wechat4j
5 | wechat4j-common
6 | jar
7 | 0.0.1-SNAPSHOT
8 | wechat4j Maven Webapp
9 | http://maven.apache.org
10 |
11 |
12 | junit
13 | junit
14 | 4.13.1
15 | test
16 |
17 |
18 | com.bladejava
19 | blade-kit
20 | 1.3.4
21 |
22 |
23 | org.slf4j
24 | slf4j-log4j12
25 | 1.7.21
26 |
27 |
28 | com.alibaba
29 | fastjson
30 | 1.2.44
31 |
32 |
33 | commons-io
34 | commons-io
35 | 2.7
36 |
37 |
38 | mysql
39 | mysql-connector-java
40 | 8.0.16
41 |
42 |
43 | org.sql2o
44 | sql2o
45 | 1.6.0-RC3
46 |
47 |
48 |
49 | com.qiniu
50 | qiniu-java-sdk
51 | 7.0.2
52 |
53 |
54 |
55 |
56 | wechat4j
57 |
58 |
59 | org.apache.maven.plugins
60 | maven-shade-plugin
61 |
62 |
63 | package
64 |
65 | shade
66 |
67 |
68 |
69 |
70 | com.iyuexian.wechat4j.demo.Demo1
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 | org.apache.maven.plugins
79 | maven-compiler-plugin
80 |
81 | 1.8
82 | 1.8
83 |
84 | -parameters
85 |
86 |
87 |
88 |
89 | compile
90 |
91 |
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/WechatStartup$1.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/WechatStartup$1.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/WechatStartup.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/WechatStartup.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/BaseRequest.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/BaseRequest.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/ChatRoom.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/ChatRoom.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/ChatRoomMember.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/ChatRoomMember.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/ContactUser.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/ContactUser.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/GroupMember.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/GroupMember.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/Msg.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/bean/Msg.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Constant.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Constant.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums$FileType.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums$FileType.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums$MsgType.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums$MsgType.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums$OS.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums$OS.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/config/Enums.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/core/WechatApiUtil.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/core/WechatApiUtil.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/core/WechatMeta.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/core/WechatMeta.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/demo/Demo1.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/demo/Demo1.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/exception/WechatException.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/exception/WechatException.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/ContactManager.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/ContactManager.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/ContactUserUtil.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/ContactUserUtil.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/FileHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/FileHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/FriendAddTask.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/FriendAddTask.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/MessageListener.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/MessageListener.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/QRCodeWindow$1.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/QRCodeWindow$1.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/QRCodeWindow.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/QRCodeWindow.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/QrUtil.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/QrUtil.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/Storage.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/Storage.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/Task$1.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/Task$1.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/Task.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/Task.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot$InputText.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot$InputText.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot$Location.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot$Location.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot$UserInfo.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot$UserInfo.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TulingRobot.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TxtMessageRobot.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/TxtMessageRobot.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/WxLocalCache$CacheItem.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/WxLocalCache$CacheItem.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/WxLocalCache$Holder.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/WxLocalCache$Holder.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/WxLocalCache.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/WxLocalCache.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/AbstractMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/AbstractMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/IMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/IMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/MessageManager.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/MessageManager.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/MpMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/MpMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/PictureMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/PictureMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/TxtMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/TxtMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/VideoMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/VideoMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/VoiceMessageHandler.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/message/VoiceMessageHandler.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/FilePipeLine.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/FilePipeLine.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/MessagePipeLine.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/MessagePipeLine.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/PipeLineManager$Holder.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/PipeLineManager$Holder.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/PipeLineManager.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/plugin/storage/PipeLineManager.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Converter.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Converter.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/CookieUtil.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/CookieUtil.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/DigestUtils.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/DigestUtils.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Emptys$NullPlaceholder.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Emptys$NullPlaceholder.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Emptys.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Emptys.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/FileUploadHelper.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/FileUploadHelper.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/FileUtil.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/FileUtil.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/HttpClient.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/HttpClient.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/IOKit.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/IOKit.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Matchers.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/Matchers.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/PropertyReader.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/PropertyReader.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/TulingUtil.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/classes/com/iyuexian/wechat4j/util/TulingUtil.class
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/config.properties:
--------------------------------------------------------------------------------
1 | # media save path
2 | app.media_path=C\:/wechat
3 | app.msg_location=C\:/wechat/msg.txt
4 |
5 | db.url=jdbc\:mysql\://rm-8vbl9c7po6w334tr4o.mysql.zhangbei.rds.aliyuncs.com\:3306/xmall?&useUnicode\=true&characterEncoding\=UTF-8&autoReconnect\=true&failOverReadOnly\=false&zeroDateTimeBehavior\=convertToNull
6 | db.username=root
7 | db.pass=123456
8 |
9 | qiniu_ak=0FlyZYZsYM6xhaW2UM2gREQ2dINcz59M-PP6cIby10
10 | qiniu_sk=0Zo0gLdlp9uYsh2T312iCm4kUeKVu5_j295Wlm5O80
11 | qiuniu_img_url=http\://img.iyuexian.com/
12 | qiuniu_video_url=http\://v.iyuexian.com/
13 | qiniu_bucket_image0=image1
14 | qiniu_bucket_video=video
15 |
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/log4j.properties:
--------------------------------------------------------------------------------
1 | log4j.rootLogger=debug,console
2 |
3 | #log4j.appender.stdout = org.apache.log4j.ConsoleAppender
4 | #log4j.appender.stdout.layout = org.apache.log4j.PatternLayout
5 | #log4j.appender.stdout.layout.ConversionPattern = %d %-5p => %m%n
6 |
7 |
8 | log4j.appender.console=org.apache.log4j.ConsoleAppender
9 | log4j.appender.console.Target=System.out
10 | log4j.appender.console.layout=org.apache.log4j.PatternLayout
11 | log4j.appender.console.layout.ConversionPattern=wechat4j-[%-5p] %d{MM-dd HH\:mm\:ss} %l\: %m %x %n
12 | #log4j.appender.console.layout.ConversionPattern=wechat4j-[%-5p] %d{MM-dd HH\:mm}:%m %n
--------------------------------------------------------------------------------
/wechat4j-common/target/classes/logging.properties:
--------------------------------------------------------------------------------
1 | handlers = org.apache.juli.FileHandler, java.util.logging.ConsoleHandler
2 |
3 | ############################################################
4 | # Handler specific properties.
5 | # Describes specific configuration info for Handlers.
6 | ############################################################
7 |
8 | org.apache.juli.FileHandler.level = FINE
9 | org.apache.juli.FileHandler.directory = ${catalina.base}/logs
10 | org.apache.juli.FileHandler.prefix = error-debug.
11 |
12 | java.util.logging.ConsoleHandler.level = FINE
13 | java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
--------------------------------------------------------------------------------
/wechat4j-common/target/maven-archiver/pom.properties:
--------------------------------------------------------------------------------
1 | #Generated by Maven
2 | #Sat Mar 31 11:49:25 CST 2018
3 | version=0.0.1-SNAPSHOT
4 | groupId=com.iyuexian.wechat4j
5 | artifactId=wechat4j-common
6 |
--------------------------------------------------------------------------------
/wechat4j-common/target/maven-status/maven-compiler-plugin/compile/default-compile/createdFiles.lst:
--------------------------------------------------------------------------------
1 | com\iyuexian\wechat4j\plugin\QrUtil$1.class
2 | com\iyuexian\wechat4j\util\Emptys$1.class
3 | com\iyuexian\wechat4j\plugin\storage\PipeLineManager$1.class
4 |
--------------------------------------------------------------------------------
/wechat4j-common/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst:
--------------------------------------------------------------------------------
1 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\storage\MessagePipeLine.java
2 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\bean\ContactUser.java
3 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\Converter.java
4 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\CookieUtil.java
5 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\FriendAddTask.java
6 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\TxtMessageRobot.java
7 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\FileUtil.java
8 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\config\MsgType.java
9 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\demo\Demo1.java
10 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\TxtMessageHandler.java
11 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\MessageListener.java
12 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\VoiceMessageHandler.java
13 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\QrUtil.java
14 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\storage\FilePipeLine.java
15 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\FileUploadHelper.java
16 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\AbstractMessageHandler.java
17 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\Storage.java
18 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\DigestUtils.java
19 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\ContactUserUtil.java
20 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\WxLocalCache.java
21 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\IOKit.java
22 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\core\WechatMeta.java
23 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\exception\WechatException.java
24 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\MpMessageHandler.java
25 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\TulingUtil.java
26 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\bean\ChatRoomMember.java
27 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\TulingRobot.java
28 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\bean\ChatRoom.java
29 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\bean\GroupMember.java
30 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\Task.java
31 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\MessageManager.java
32 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\HttpClient.java
33 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\ContactManager.java
34 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\QRCodeWindow.java
35 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\PictureMessageHandler.java
36 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\WechatStartup.java
37 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\IMessageHandler.java
38 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\Matchers.java
39 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\message\VideoMessageHandler.java
40 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\FileHandler.java
41 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\config\Constant.java
42 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\config\Enums.java
43 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\bean\Msg.java
44 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\Emptys.java
45 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\core\WechatApiUtil.java
46 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\plugin\storage\PipeLineManager.java
47 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\bean\BaseRequest.java
48 | D:\dev\work\eclipse-workspace2\wechat4j-common\src\main\java\com\iyuexian\wechat4j\util\PropertyReader.java
49 |
--------------------------------------------------------------------------------
/wechat4j-common/target/maven-status/maven-compiler-plugin/testCompile/default-testCompile/inputFiles.lst:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/maven-status/maven-compiler-plugin/testCompile/default-testCompile/inputFiles.lst
--------------------------------------------------------------------------------
/wechat4j-common/target/original-wechat4j.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/original-wechat4j.jar
--------------------------------------------------------------------------------
/wechat4j-common/target/wechat4j-common-0.0.1-SNAPSHOT-shaded.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/wechat4j-common-0.0.1-SNAPSHOT-shaded.jar
--------------------------------------------------------------------------------
/wechat4j-common/target/wechat4j.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/hexiangtao/wechat4j/ae79c9ea52d6eed17fa0f1126f2229c3407ecc18/wechat4j-common/target/wechat4j.jar
--------------------------------------------------------------------------------