diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/WeixinProxy.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/WeixinProxy.java
index 13a19ed2..c9b6e871 100644
--- a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/WeixinProxy.java
+++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/WeixinProxy.java
@@ -33,6 +33,7 @@ import com.foxinmy.weixin4j.mp.model.Group;
import com.foxinmy.weixin4j.mp.model.KfAccount;
import com.foxinmy.weixin4j.mp.model.KfChatRecord;
import com.foxinmy.weixin4j.mp.model.KfSession;
+import com.foxinmy.weixin4j.mp.model.KfSession.kfSessionCounter;
import com.foxinmy.weixin4j.mp.model.Menu;
import com.foxinmy.weixin4j.mp.model.MenuMatchRule;
import com.foxinmy.weixin4j.mp.model.MenuSetting;
@@ -234,9 +235,6 @@ public class WeixinProxy {
/**
* 上传媒体文件
* 此接口只包含图片、语音、缩略图、视频(临时)四种媒体类型的上传
- *
- * 正常情况下返回{"type":"TYPE","media_id":"MEDIA_ID","created_at":123456789},
- * 否则抛出异常.
*
*
* @param isMaterial
@@ -244,7 +242,7 @@ public class WeixinProxy {
* @param is
* 媒体数据流
* @param fileName
- * 文件名
+ * 文件名 为空时将自动生成
* @return 上传到微信服务器返回的媒体标识
* @see
@@ -688,18 +686,18 @@ public class WeixinProxy {
}
/**
- * 获取未接入会话列表:获取当前正在等待队列中的会话列表,此接口最多返回最早进入队列的100个未接入会话。
- * 缺陷:没有count字段
+ * 获取未接入会话列表:获取当前正在等待队列中的会话列表,此接口最多返回最早进入队列的100个未接入会话
*
* @return 会话列表
* @throws WeixinException
* @see com.foxinmy.weixin4j.mp.api.CustomApi
* @see com.foxinmy.weixin4j.mp.model.KfSession
+ * @see com.foxinmy.weixin4j.mp.model.KfSession.kfSessionCounter
* @see
* 获取客服的会话列表
*/
- public List listKfWaitSession() throws WeixinException {
+ public kfSessionCounter listKfWaitSession() throws WeixinException {
return customApi.listKfWaitSession();
}
diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/CustomApi.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/CustomApi.java
index de20a99c..b237e943 100644
--- a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/CustomApi.java
+++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/CustomApi.java
@@ -19,6 +19,7 @@ import com.foxinmy.weixin4j.model.Token;
import com.foxinmy.weixin4j.mp.model.KfAccount;
import com.foxinmy.weixin4j.mp.model.KfChatRecord;
import com.foxinmy.weixin4j.mp.model.KfSession;
+import com.foxinmy.weixin4j.mp.model.KfSession.kfSessionCounter;
import com.foxinmy.weixin4j.token.TokenHolder;
import com.foxinmy.weixin4j.util.DigestUtil;
import com.foxinmy.weixin4j.util.FileUtil;
@@ -54,11 +55,11 @@ public class CustomApi extends MpApi {
* @throws WeixinException
* @see com.foxinmy.weixin4j.mp.model.KfChatRecord
* @see 查询客服聊天记录
- * @see 查询客服聊天记录
+ * @see
+ * 查询客服聊天记录
*/
- public List getKfChatRecord(Date startTime, Date endTime,
- Pageable pageable) throws WeixinException {
+ public List getKfChatRecord(Date startTime, Date endTime, Pageable pageable) throws WeixinException {
List records = new ArrayList();
String kf_chatrecord_uri = getRequestUri("kf_chatrecord_uri");
Token token = tokenHolder.getToken();
@@ -68,8 +69,7 @@ public class CustomApi extends MpApi {
for (int i = 0; i < (int) Math.ceil(pageable.getPageSize() / 50d); i++) {
obj.put("pagesize", Math.min(50, pageable.getPageSize()));
obj.put("pageindex", pageable.getPageNumber());
- WeixinResponse response = weixinExecutor.post(
- String.format(kf_chatrecord_uri, token.getAccessToken()),
+ WeixinResponse response = weixinExecutor.post(String.format(kf_chatrecord_uri, token.getAccessToken()),
obj.toJSONString());
String text = response.getAsJson().getString("recordlist");
@@ -78,8 +78,8 @@ public class CustomApi extends MpApi {
}
records.addAll(JSON.parseArray(text, KfChatRecord.class));
- pageable = new Pageable(pageable.getPageNumber() + 1, Math.min(50,
- Math.max(1, pageable.getPageSize() - ((i + 1) * 50))));
+ pageable = new Pageable(pageable.getPageNumber() + 1,
+ Math.min(50, Math.max(1, pageable.getPageSize() - ((i + 1) * 50))));
}
return records;
}
@@ -93,24 +93,22 @@ public class CustomApi extends MpApi {
* @return 多客服信息列表
* @see com.foxinmy.weixin4j.mp.model.KfAccount
* @see 获取客服基本信息
- * @see 获取客服基本信息
+ * @see
+ * 获取客服基本信息
* @see 获取在线客服接待信息
* @throws WeixinException
*/
- public List listKfAccount(boolean isOnline)
- throws WeixinException {
+ public List listKfAccount(boolean isOnline) throws WeixinException {
Token token = tokenHolder.getToken();
String text = "";
if (isOnline) {
String kf_onlinelist_uri = getRequestUri("kf_onlinelist_uri");
- WeixinResponse response = weixinExecutor.get(String.format(
- kf_onlinelist_uri, token.getAccessToken()));
+ WeixinResponse response = weixinExecutor.get(String.format(kf_onlinelist_uri, token.getAccessToken()));
text = response.getAsJson().getString("kf_online_list");
} else {
String kf_list_uri = getRequestUri("kf_list_uri");
- WeixinResponse response = weixinExecutor.get(String.format(
- kf_list_uri, token.getAccessToken()));
+ WeixinResponse response = weixinExecutor.get(String.format(kf_list_uri, token.getAccessToken()));
text = response.getAsJson().getString("kf_list");
}
return JSON.parseArray(text, KfAccount.class);
@@ -128,19 +126,18 @@ public class CustomApi extends MpApi {
* 客服账号登录密码
* @return 处理结果
* @throws WeixinException
- * @see 新增客服账号
+ * @see
+ * 新增客服账号
*/
- public JsonResult createKfAccount(String id, String name, String pwd)
- throws WeixinException {
+ public JsonResult createKfAccount(String id, String name, String pwd) throws WeixinException {
JSONObject obj = new JSONObject();
obj.put("kf_account", id);
obj.put("nickname", name);
obj.put("password", DigestUtil.MD5(pwd));
String kf_create_uri = getRequestUri("kf_create_uri");
Token token = tokenHolder.getToken();
- WeixinResponse response = weixinExecutor.post(
- String.format(kf_create_uri, token.getAccessToken()),
+ WeixinResponse response = weixinExecutor.post(String.format(kf_create_uri, token.getAccessToken()),
obj.toJSONString());
return response.getAsJsonResult();
}
@@ -157,19 +154,18 @@ public class CustomApi extends MpApi {
* 客服账号登录密码
* @return 处理结果
* @throws WeixinException
- * @see 新增客服账号
+ * @see
+ * 新增客服账号
*/
- public JsonResult updateKfAccount(String id, String name, String pwd)
- throws WeixinException {
+ public JsonResult updateKfAccount(String id, String name, String pwd) throws WeixinException {
JSONObject obj = new JSONObject();
obj.put("kf_account", id);
obj.put("nickname", name);
obj.put("password", DigestUtil.MD5(pwd));
String kf_update_uri = getRequestUri("kf_update_uri");
Token token = tokenHolder.getToken();
- WeixinResponse response = weixinExecutor.post(
- String.format(kf_update_uri, token.getAccessToken()),
+ WeixinResponse response = weixinExecutor.post(String.format(kf_update_uri, token.getAccessToken()),
obj.toJSONString());
return response.getAsJsonResult();
}
@@ -189,15 +185,13 @@ public class CustomApi extends MpApi {
* >邀请绑定客服帐号
* @throws WeixinException
*/
- public JsonResult inviteKfAccount(String kfAccount, String inviteAccount)
- throws WeixinException {
+ public JsonResult inviteKfAccount(String kfAccount, String inviteAccount) throws WeixinException {
JSONObject obj = new JSONObject();
obj.put("kf_account", kfAccount);
obj.put("invite_wx", inviteAccount);
String kf_invite_uri = getRequestUri("kf_invite_uri");
Token token = tokenHolder.getToken();
- WeixinResponse response = weixinExecutor.post(
- String.format(kf_invite_uri, token.getAccessToken()),
+ WeixinResponse response = weixinExecutor.post(String.format(kf_invite_uri, token.getAccessToken()),
obj.toJSONString());
return response.getAsJsonResult();
}
@@ -213,11 +207,11 @@ public class CustomApi extends MpApi {
* 文件名 为空时将自动生成
* @return 处理结果
* @throws WeixinException
- * @see 上传客服头像
+ * @see
+ * 上传客服头像
*/
- public JsonResult uploadKfAvatar(String accountId, InputStream is,
- String fileName) throws WeixinException {
+ public JsonResult uploadKfAvatar(String accountId, InputStream is, String fileName) throws WeixinException {
if (StringUtil.isBlank(fileName)) {
fileName = ObjectId.get().toHexString();
}
@@ -226,11 +220,8 @@ public class CustomApi extends MpApi {
}
Token token = tokenHolder.getToken();
String kf_avatar_uri = getRequestUri("kf_avatar_uri");
- WeixinResponse response = weixinExecutor
- .post(String.format(kf_avatar_uri, token.getAccessToken(),
- accountId),
- new FormBodyPart("media", new InputStreamBody(is,
- ContentType.IMAGE_JPG.getMimeType(), fileName)));
+ WeixinResponse response = weixinExecutor.post(String.format(kf_avatar_uri, token.getAccessToken(), accountId),
+ new FormBodyPart("media", new InputStreamBody(is, ContentType.IMAGE_JPG.getMimeType(), fileName)));
return response.getAsJsonResult();
}
@@ -242,14 +233,14 @@ public class CustomApi extends MpApi {
* 完整客服账号,格式为:账号前缀@公众号微信号
* @return 处理结果
* @throws WeixinException
- * @see 删除客服账号
+ * @see
+ * 删除客服账号
*/
public JsonResult deleteKfAccount(String id) throws WeixinException {
Token token = tokenHolder.getToken();
String kf_delete_uri = getRequestUri("kf_delete_uri");
- WeixinResponse response = weixinExecutor.get(String.format(
- kf_delete_uri, token.getAccessToken(), id));
+ WeixinResponse response = weixinExecutor.get(String.format(kf_delete_uri, token.getAccessToken(), id));
return response.getAsJsonResult();
}
@@ -269,19 +260,18 @@ public class CustomApi extends MpApi {
* 附加信息,文本会展示在客服人员的多客服客户端
* @return 处理结果
* @throws WeixinException
- * @see 创建会话
+ * @see
+ * 创建会话
*/
- public JsonResult createKfSession(String userOpenId, String kfAccount,
- String text) throws WeixinException {
+ public JsonResult createKfSession(String userOpenId, String kfAccount, String text) throws WeixinException {
Token token = tokenHolder.getToken();
String kfsession_create_uri = getRequestUri("kfsession_create_uri");
JSONObject obj = new JSONObject();
obj.put("openid", userOpenId);
obj.put("kf_account", kfAccount);
obj.put("text", text);
- WeixinResponse response = weixinExecutor.post(
- String.format(kfsession_create_uri, token.getAccessToken()),
+ WeixinResponse response = weixinExecutor.post(String.format(kfsession_create_uri, token.getAccessToken()),
obj.toJSONString());
return response.getAsJsonResult();
@@ -298,19 +288,18 @@ public class CustomApi extends MpApi {
* 附加信息,文本会展示在客服人员的多客服客户端
* @return 处理结果
* @throws WeixinException
- * @see 关闭会话
+ * @see
+ * 关闭会话
*/
- public JsonResult closeKfSession(String userOpenId, String kfAccount,
- String text) throws WeixinException {
+ public JsonResult closeKfSession(String userOpenId, String kfAccount, String text) throws WeixinException {
Token token = tokenHolder.getToken();
String kfsession_close_uri = getRequestUri("kfsession_close_uri");
JSONObject obj = new JSONObject();
obj.put("openid", userOpenId);
obj.put("kf_account", kfAccount);
obj.put("text", text);
- WeixinResponse response = weixinExecutor.post(
- String.format(kfsession_close_uri, token.getAccessToken()),
+ WeixinResponse response = weixinExecutor.post(String.format(kfsession_close_uri, token.getAccessToken()),
obj.toJSONString());
return response.getAsJsonResult();
@@ -324,18 +313,18 @@ public class CustomApi extends MpApi {
* @return 会话对象
* @throws WeixinException
* @see com.foxinmy.weixin4j.mp.model.KfSession
- * @see 获取会话状态
+ * @see
+ * 获取会话状态
*/
public KfSession getKfSession(String userOpenId) throws WeixinException {
Token token = tokenHolder.getToken();
String kfsession_get_uri = getRequestUri("kfsession_get_uri");
- WeixinResponse response = weixinExecutor.get(String.format(
- kfsession_get_uri, token.getAccessToken(), userOpenId));
+ WeixinResponse response = weixinExecutor
+ .get(String.format(kfsession_get_uri, token.getAccessToken(), userOpenId));
- KfSession session = response
- .getAsObject(new TypeReference() {
- });
+ KfSession session = response.getAsObject(new TypeReference() {
+ });
session.setUserOpenId(userOpenId);
return session;
}
@@ -348,39 +337,38 @@ public class CustomApi extends MpApi {
* @return 会话列表
* @throws WeixinException
* @see com.foxinmy.weixin4j.mp.model.KfSession
- * @see 获取客服的会话列表
+ * @see
+ * 获取客服的会话列表
*/
- public List listKfSession(String kfAccount)
- throws WeixinException {
+ public List listKfSession(String kfAccount) throws WeixinException {
Token token = tokenHolder.getToken();
String kfsession_list_uri = getRequestUri("kfsession_list_uri");
- WeixinResponse response = weixinExecutor.get(String.format(
- kfsession_list_uri, token.getAccessToken(), kfAccount));
+ WeixinResponse response = weixinExecutor
+ .get(String.format(kfsession_list_uri, token.getAccessToken(), kfAccount));
- List sessionList = JSON.parseArray(response.getAsJson()
- .getString("sessionlist"), KfSession.class);
+ List sessionList = JSON.parseArray(response.getAsJson().getString("sessionlist"), KfSession.class);
return sessionList;
}
/**
- * 获取未接入会话列表:获取当前正在等待队列中的会话列表,此接口最多返回最早进入队列的100个未接入会话。 缺陷:没有count字段
+ * 获取未接入会话列表:获取当前正在等待队列中的会话列表,此接口最多返回最早进入队列的100个未接入会话。
+ * 缺陷:没有count字段
*
* @return 会话列表
* @throws WeixinException
* @see com.foxinmy.weixin4j.mp.model.KfSession
- * @see 获取客服的会话列表
+ * @see com.foxinmy.weixin4j.mp.model.KfSession.kfSessionCounter
+ * @see
+ * 获取客服的会话列表
*/
- public List listKfWaitSession() throws WeixinException {
+ public kfSessionCounter listKfWaitSession() throws WeixinException {
Token token = tokenHolder.getToken();
String kfsession_wait_uri = getRequestUri("kfsession_wait_uri");
- WeixinResponse response = weixinExecutor.get(String.format(
- kfsession_wait_uri, token.getAccessToken()));
+ WeixinResponse response = weixinExecutor.get(String.format(kfsession_wait_uri, token.getAccessToken()));
- List sessionList = JSON.parseArray(response.getAsJson()
- .getString("waitcaselist"), KfSession.class);
- return sessionList;
+ return response.getAsObject(new TypeReference() {
+ });
}
}
\ No newline at end of file
diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/model/KfSession.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/model/KfSession.java
index 92e4d5a3..e59bb889 100644
--- a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/model/KfSession.java
+++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/model/KfSession.java
@@ -1,66 +1,127 @@
-package com.foxinmy.weixin4j.mp.model;
-
-import java.io.Serializable;
-import java.util.Date;
-
-import com.alibaba.fastjson.annotation.JSONField;
-
-/**
- * 客服会话信息
- *
- * @className KfSession
- * @author jy
- * @date 2015年3月22日
- * @since JDK 1.6
- * @see
- */
-public class KfSession implements Serializable {
-
- private static final long serialVersionUID = 7236468333492555458L;
-
- /**
- * 客服账号
- */
- @JSONField(name = "kf_account")
- private String kfAccount;
- /**
- * 用户ID
- */
- @JSONField(name = "openid")
- private String userOpenId;
- /**
- * 创建时间
- */
- @JSONField(name = "createtime")
- private Date createTime;
-
- public String getKfAccount() {
- return kfAccount;
- }
-
- public void setKfAccount(String kfAccount) {
- this.kfAccount = kfAccount;
- }
-
- public String getUserOpenId() {
- return userOpenId;
- }
-
- public void setUserOpenId(String userOpenId) {
- this.userOpenId = userOpenId;
- }
-
- public Date getCreateTime() {
- return createTime;
- }
-
- public void setCreateTime(Date createTime) {
- this.createTime = createTime;
- }
-
- @Override
- public String toString() {
- return "KfSession [kfAccount=" + kfAccount + ", userOpenId="
- + userOpenId + ", createTime=" + createTime + "]";
- }
-}
+package com.foxinmy.weixin4j.mp.model;
+
+import java.io.Serializable;
+import java.util.Date;
+import java.util.Iterator;
+import java.util.List;
+
+import com.alibaba.fastjson.annotation.JSONField;
+
+/**
+ * 客服会话信息
+ *
+ * @className KfSession
+ * @author jy
+ * @date 2015年3月22日
+ * @since JDK 1.6
+ * @see
+ */
+public class KfSession implements Serializable {
+
+ private static final long serialVersionUID = 7236468333492555458L;
+
+ /**
+ * 客服账号
+ */
+ @JSONField(name = "kf_account")
+ private String kfAccount;
+ /**
+ * 用户ID
+ */
+ @JSONField(name = "openid")
+ private String userOpenId;
+ /**
+ * 创建时间
+ */
+ @JSONField(name = "createtime")
+ private Date createTime;
+ /**
+ * 最后一条消息的时间,在`获取未接入会话列表`接口中有值
+ */
+ @JSONField(name = "latest_time")
+ private Date latestTime;
+
+ public String getKfAccount() {
+ return kfAccount;
+ }
+
+ public void setKfAccount(String kfAccount) {
+ this.kfAccount = kfAccount;
+ }
+
+ public String getUserOpenId() {
+ return userOpenId;
+ }
+
+ public void setUserOpenId(String userOpenId) {
+ this.userOpenId = userOpenId;
+ }
+
+ public Date getCreateTime() {
+ return createTime;
+ }
+
+ public void setCreateTime(Date createTime) {
+ this.createTime = createTime;
+ }
+
+ public Date getLatestTime() {
+ return latestTime;
+ }
+
+ public void setLatestTime(Date latestTime) {
+ this.latestTime = latestTime;
+ }
+
+ /**
+ * 会话计数,如 未接入会话列表
+ *
+ * @className: kfSessionCounter
+ * @description:
+ * @author jinyu
+ * @date 2016年4月15日
+ * @since JDK 1.6
+ * @see
+ */
+ public static class kfSessionCounter implements Iterable, Serializable {
+
+ private static final long serialVersionUID = -2200434961546270829L;
+
+ @JSONField(name = "count")
+ private int count;
+ @JSONField(name = "waitcaselist")
+ private List kfSessions;
+
+ @Override
+ public Iterator iterator() {
+ return kfSessions.iterator();
+ }
+
+ public int getCount() {
+ return count;
+ }
+
+ public void setCount(int count) {
+ this.count = count;
+ }
+
+ public List getKfSessions() {
+ return kfSessions;
+ }
+
+ public void setKfSessions(List kfSessions) {
+ this.kfSessions = kfSessions;
+ }
+
+ @Override
+ public String toString() {
+ return "kfSessionCounter [count=" + count + ", kfSessions=" + kfSessions + "]";
+ }
+ }
+
+ @Override
+ public String toString() {
+ return "KfSession [kfAccount=" + kfAccount + ", userOpenId=" + userOpenId + ", createTime=" + createTime
+ + ", latestTime=" + latestTime + "]";
+ }
+}
diff --git a/weixin4j-server/src/main/java/com/foxinmy/weixin4j/dispatcher/WeixinMessageDispatcher.java b/weixin4j-server/src/main/java/com/foxinmy/weixin4j/dispatcher/WeixinMessageDispatcher.java
index 3efdde29..0c0bea83 100644
--- a/weixin4j-server/src/main/java/com/foxinmy/weixin4j/dispatcher/WeixinMessageDispatcher.java
+++ b/weixin4j-server/src/main/java/com/foxinmy/weixin4j/dispatcher/WeixinMessageDispatcher.java
@@ -178,7 +178,7 @@ public class WeixinMessageDispatcher {
* 微信消息
*/
protected void noHandlerFound(ChannelHandlerContext context,
- WeixinRequest request, Object message) {
+ WeixinRequest request, WeixinMessage message) {
logger.warn("no handler found for {}", request);
if (alwaysResponse) {
context.write(BlankResponse.global);
@@ -234,7 +234,7 @@ public class WeixinMessageDispatcher {
return m2.weight() - m1.weight();
}
});
- logger.info("matched message handler '{}'", matchedMessageHandlers);
+ logger.info("matched message handlers '{}'", matchedMessageHandlers);
return new MessageHandlerExecutor(context,
matchedMessageHandlers.get(0), getMessageInterceptors());
}