diff --git a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpKefuService.java b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpKefuService.java index c4731cb5..fc678b42 100644 --- a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpKefuService.java +++ b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpKefuService.java @@ -1,12 +1,18 @@ package me.chanjar.weixin.mp.api; -import me.chanjar.weixin.common.exception.WxErrorException; -import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfAccountRequest; -import me.chanjar.weixin.mp.bean.kefu.result.*; - import java.io.File; import java.util.Date; +import me.chanjar.weixin.common.exception.WxErrorException; +import me.chanjar.weixin.mp.bean.WxMpCustomMessage; +import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfAccountRequest; +import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfList; +import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfMsgList; +import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfOnlineList; +import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionGetResult; +import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionList; +import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionWaitCaseList; + /** * 客服接口 , * 命名采用kefu拼音的原因是: @@ -17,6 +23,14 @@ import java.util.Date; */ public interface WxMpKefuService { + /** + *
+ * 发送客服消息 + * 详情请见: 发送客服消息 + *+ */ + boolean customMessageSend(WxMpCustomMessage message) throws WxErrorException; + //*******************客服管理接口***********************// /** diff --git a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpService.java b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpService.java index 077488b7..952cf8f5 100644 --- a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpService.java +++ b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/WxMpService.java @@ -3,7 +3,6 @@ package me.chanjar.weixin.mp.api; import me.chanjar.weixin.common.bean.WxJsapiSignature; import me.chanjar.weixin.common.exception.WxErrorException; import me.chanjar.weixin.common.util.http.RequestExecutor; -import me.chanjar.weixin.mp.bean.WxMpCustomMessage; import me.chanjar.weixin.mp.bean.WxMpIndustry; import me.chanjar.weixin.mp.bean.WxMpMassGroupMessage; import me.chanjar.weixin.mp.bean.WxMpMassNews; @@ -82,14 +81,6 @@ public interface WxMpService { */ WxJsapiSignature createJsapiSignature(String url) throws WxErrorException; - /** - *
- * 发送客服消息 - * 详情请见: http://mp.weixin.qq.com/wiki/index.php?title=发送客服消息 - *- */ - void customMessageSend(WxMpCustomMessage message) throws WxErrorException; - /** *
* 上传群发用的图文消息,上传后才能群发图文消息 diff --git a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImpl.java b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImpl.java index 6d6cf14c..b65fdeaa 100644 --- a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImpl.java +++ b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImpl.java @@ -3,15 +3,18 @@ package me.chanjar.weixin.mp.api.impl; import java.io.File; import java.util.Date; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + import com.google.gson.JsonObject; import me.chanjar.weixin.common.bean.result.WxError; +import me.chanjar.weixin.common.bean.result.WxMediaUploadResult; import me.chanjar.weixin.common.exception.WxErrorException; import me.chanjar.weixin.common.util.http.MediaUploadRequestExecutor; -import me.chanjar.weixin.common.util.http.SimpleGetRequestExecutor; -import me.chanjar.weixin.common.util.http.SimplePostRequestExecutor; import me.chanjar.weixin.mp.api.WxMpKefuService; import me.chanjar.weixin.mp.api.WxMpService; +import me.chanjar.weixin.mp.bean.WxMpCustomMessage; import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfAccountRequest; import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfSessionRequest; import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfList; @@ -27,6 +30,8 @@ import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfSessionWaitCaseList; * */ public class WxMpKefuServiceImpl implements WxMpKefuService { + protected final Logger log = LoggerFactory + .getLogger(WxMpKefuServiceImpl.class); private static final String API_URL_PREFIX = "https://api.weixin.qq.com/customservice"; private WxMpService wxMpService; @@ -34,19 +39,31 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { this.wxMpService = wxMpService; } + @Override + public boolean customMessageSend(WxMpCustomMessage message) + throws WxErrorException { + String url = "https://api.weixin.qq.com/cgi-bin/message/custom/send"; + String responseContent = this.wxMpService.post(url, message.toJson()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, message.toJson(), + responseContent); + return true; + } + @Override public WxMpKfList kfList() throws WxErrorException { - String url = "https://api.weixin.qq.com/cgi-bin/customservice/getkflist"; - String responseContent = this.wxMpService - .execute(new SimpleGetRequestExecutor(), url, null); + String url = API_URL_PREFIX + "/getkflist"; + String responseContent = this.wxMpService.get(url, null); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, null, + responseContent); return WxMpKfList.fromJson(responseContent); } @Override public WxMpKfOnlineList kfOnlineList() throws WxErrorException { - String url = "https://api.weixin.qq.com/cgi-bin/customservice/getonlinekflist"; - String responseContent = this.wxMpService - .execute(new SimpleGetRequestExecutor(), url, null); + String url = API_URL_PREFIX + "/getonlinekflist"; + String responseContent = this.wxMpService.get(url, null); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, null, + responseContent); return WxMpKfOnlineList.fromJson(responseContent); } @@ -54,8 +71,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { public boolean kfAccountAdd(WxMpKfAccountRequest request) throws WxErrorException { String url = API_URL_PREFIX + "/kfaccount/add"; - this.wxMpService.execute(new SimplePostRequestExecutor(), url, - request.toJson()); + String responseContent = this.wxMpService.post(url, request.toJson()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, request.toJson(), + responseContent); return true; } @@ -63,16 +81,18 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { public boolean kfAccountUpdate(WxMpKfAccountRequest request) throws WxErrorException { String url = API_URL_PREFIX + "/kfaccount/update"; - this.wxMpService.execute(new SimplePostRequestExecutor(), url, - request.toJson()); + String responseContent = this.wxMpService.post(url, request.toJson()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, request.toJson(), + responseContent); return true; } @Override public boolean kfAccountInviteWorker(WxMpKfAccountRequest request) throws WxErrorException { String url = API_URL_PREFIX + "/kfaccount/inviteworker"; - this.wxMpService.execute(new SimplePostRequestExecutor(), url, - request.toJson()); + String responseContent = this.wxMpService.post(url, request.toJson()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, request.toJson(), + responseContent); return true; } @@ -80,14 +100,20 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { public boolean kfAccountUploadHeadImg(String kfAccount, File imgFile) throws WxErrorException { String url = API_URL_PREFIX + "/kfaccount/uploadheadimg?kf_account=" + kfAccount; - this.wxMpService.execute(new MediaUploadRequestExecutor(), url, imgFile); + WxMediaUploadResult responseContent = this.wxMpService + .execute(new MediaUploadRequestExecutor(), url, imgFile); + this.log.debug("\nurl:{}\nparams:{}&file:{}\nresponse:{}", url, kfAccount, + imgFile.getAbsolutePath(), + responseContent); return true; } @Override public boolean kfAccountDel(String kfAccount) throws WxErrorException { String url = API_URL_PREFIX + "/kfaccount/del?kf_account=" + kfAccount; - this.wxMpService.execute(new SimpleGetRequestExecutor(), url, null); + String responseContent = this.wxMpService.get(url, null); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, null, + responseContent); return true; } @@ -96,8 +122,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { throws WxErrorException { WxMpKfSessionRequest request = new WxMpKfSessionRequest(kfAccount, openid); String url = API_URL_PREFIX + "/kfsession/create"; - this.wxMpService.execute(new SimplePostRequestExecutor(), url, - request.toJson()); + String responseContent = this.wxMpService.post(url, request.toJson()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, request.toJson(), + responseContent); return true; } @@ -106,8 +133,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { throws WxErrorException { WxMpKfSessionRequest request = new WxMpKfSessionRequest(kfAccount, openid); String url = API_URL_PREFIX + "/kfsession/close"; - this.wxMpService.execute(new SimplePostRequestExecutor(), url, - request.toJson()); + String responseContent = this.wxMpService.post(url, request.toJson()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, request.toJson(), + responseContent); return true; } @@ -115,8 +143,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { public WxMpKfSessionGetResult kfSessionGet(String openid) throws WxErrorException { String url = API_URL_PREFIX + "/kfsession/getsession?openid=" + openid; - String responseContent = this.wxMpService - .execute(new SimpleGetRequestExecutor(), url, null); + String responseContent = this.wxMpService.get(url, null); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, null, + responseContent); return WxMpKfSessionGetResult.fromJson(responseContent); } @@ -124,8 +153,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { public WxMpKfSessionList kfSessionList(String kfAccount) throws WxErrorException { String url = API_URL_PREFIX + "/kfsession/getsessionlist?kf_account=" + kfAccount; - String responseContent = this.wxMpService - .execute(new SimpleGetRequestExecutor(), url, null); + String responseContent = this.wxMpService.get(url, null); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, null, + responseContent); return WxMpKfSessionList.fromJson(responseContent); } @@ -133,8 +163,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { public WxMpKfSessionWaitCaseList kfSessionGetWaitCase() throws WxErrorException { String url = API_URL_PREFIX + "/kfsession/getwaitcase"; - String responseContent = this.wxMpService - .execute(new SimpleGetRequestExecutor(), url, null); + String responseContent = this.wxMpService.get(url, null); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, null, + responseContent); return WxMpKfSessionWaitCaseList.fromJson(responseContent); } @@ -156,7 +187,9 @@ public class WxMpKefuServiceImpl implements WxMpKefuService { param.addProperty("msgid", msgId); //msgid 消息id顺序从小到大,从1开始 param.addProperty("number", number); //number 每次获取条数,最多10000条 - String responseContent = this.wxMpService.execute(new SimplePostRequestExecutor(), url, param.toString()); + String responseContent = this.wxMpService.post(url, param.toString()); + this.log.debug("\nurl:{}\nparams:{}\nresponse:{}", url, param.toString(), + responseContent); return WxMpKfMsgList.fromJson(responseContent); } diff --git a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpServiceImpl.java b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpServiceImpl.java index 2bff6482..3f2c9808 100644 --- a/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpServiceImpl.java +++ b/weixin-java-mp/src/main/java/me/chanjar/weixin/mp/api/impl/WxMpServiceImpl.java @@ -44,7 +44,6 @@ import me.chanjar.weixin.mp.api.WxMpQrcodeService; import me.chanjar.weixin.mp.api.WxMpService; import me.chanjar.weixin.mp.api.WxMpUserService; import me.chanjar.weixin.mp.api.WxMpUserTagService; -import me.chanjar.weixin.mp.bean.WxMpCustomMessage; import me.chanjar.weixin.mp.bean.WxMpIndustry; import me.chanjar.weixin.mp.bean.WxMpMassGroupMessage; import me.chanjar.weixin.mp.bean.WxMpMassNews; @@ -203,12 +202,6 @@ public class WxMpServiceImpl implements WxMpService { return jsapiSignature; } - @Override - public void customMessageSend(WxMpCustomMessage message) throws WxErrorException { - String url = "https://api.weixin.qq.com/cgi-bin/message/custom/send"; - execute(new SimplePostRequestExecutor(), url, message.toJson()); - } - @Override public WxMpMassUploadResult massNewsUpload(WxMpMassNews news) throws WxErrorException { String url = "https://api.weixin.qq.com/cgi-bin/media/uploadnews"; diff --git a/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/WxMpCustomMessageAPITest.java b/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/WxMpCustomMessageAPITest.java deleted file mode 100644 index 730ab726..00000000 --- a/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/WxMpCustomMessageAPITest.java +++ /dev/null @@ -1,44 +0,0 @@ -package me.chanjar.weixin.mp.api; - -import com.google.inject.Inject; -import me.chanjar.weixin.common.api.WxConsts; -import me.chanjar.weixin.common.exception.WxErrorException; -import me.chanjar.weixin.mp.api.impl.WxMpServiceImpl; -import me.chanjar.weixin.mp.bean.WxMpCustomMessage; -import org.testng.annotations.Guice; -import org.testng.annotations.Test; - -/*** - * 测试发送客服消息 - * @author chanjarster - * - */ -@Test(groups="customMessageAPI") -@Guice(modules = ApiTestModule.class) -public class WxMpCustomMessageAPITest { - - @Inject - protected WxMpServiceImpl wxService; - - public void testSendCustomMessage() throws WxErrorException { - ApiTestModule.WxXmlMpInMemoryConfigStorage configStorage = (ApiTestModule.WxXmlMpInMemoryConfigStorage) this.wxService.getWxMpConfigStorage(); - WxMpCustomMessage message = new WxMpCustomMessage(); - message.setMsgType(WxConsts.CUSTOM_MSG_TEXT); - message.setToUser(configStorage.getOpenId()); - message.setContent("欢迎欢迎,热烈欢迎\n换行测试\n超链接:Hello World"); - - this.wxService.customMessageSend(message); - } - - public void testSendCustomMessageWithKfAccount() throws WxErrorException { - ApiTestModule.WxXmlMpInMemoryConfigStorage configStorage = (ApiTestModule.WxXmlMpInMemoryConfigStorage) this.wxService.getWxMpConfigStorage(); - WxMpCustomMessage message = new WxMpCustomMessage(); - message.setMsgType(WxConsts.CUSTOM_MSG_TEXT); - message.setToUser(configStorage.getOpenId()); - message.setKfAccount(configStorage.getKfAccount()); - message.setContent("欢迎欢迎,热烈欢迎\n换行测试\n超链接:Hello World"); - - this.wxService.customMessageSend(message); - } - -} diff --git a/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImplTest.java b/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImplTest.java index 431792e4..21096f61 100644 --- a/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImplTest.java +++ b/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/api/impl/WxMpKefuServiceImplTest.java @@ -11,9 +11,11 @@ import org.testng.annotations.Test; import com.google.inject.Inject; +import me.chanjar.weixin.common.api.WxConsts; import me.chanjar.weixin.common.exception.WxErrorException; import me.chanjar.weixin.mp.api.ApiTestModule; import me.chanjar.weixin.mp.api.ApiTestModule.WxXmlMpInMemoryConfigStorage; +import me.chanjar.weixin.mp.bean.WxMpCustomMessage; import me.chanjar.weixin.mp.bean.kefu.request.WxMpKfAccountRequest; import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfInfo; import me.chanjar.weixin.mp.bean.kefu.result.WxMpKfList; @@ -35,6 +37,31 @@ public class WxMpKefuServiceImplTest { @Inject protected WxMpServiceImpl wxService; + public void testSendCustomMessage() throws WxErrorException { + ApiTestModule.WxXmlMpInMemoryConfigStorage configStorage = (ApiTestModule.WxXmlMpInMemoryConfigStorage) this.wxService + .getWxMpConfigStorage(); + WxMpCustomMessage message = new WxMpCustomMessage(); + message.setMsgType(WxConsts.CUSTOM_MSG_TEXT); + message.setToUser(configStorage.getOpenId()); + message.setContent( + "欢迎欢迎,热烈欢迎\n换行测试\n超链接:Hello World"); + + this.wxService.getKefuService().customMessageSend(message); + } + + public void testSendCustomMessageWithKfAccount() throws WxErrorException { + ApiTestModule.WxXmlMpInMemoryConfigStorage configStorage = (ApiTestModule.WxXmlMpInMemoryConfigStorage) this.wxService + .getWxMpConfigStorage(); + WxMpCustomMessage message = new WxMpCustomMessage(); + message.setMsgType(WxConsts.CUSTOM_MSG_TEXT); + message.setToUser(configStorage.getOpenId()); + message.setKfAccount(configStorage.getKfAccount()); + message.setContent( + "欢迎欢迎,热烈欢迎\n换行测试\n超链接:Hello World"); + + this.wxService.getKefuService().customMessageSend(message); + } + public void testKfList() throws WxErrorException { WxMpKfList kfList = this.wxService.getKefuService().kfList(); Assert.assertNotNull(kfList); @@ -123,7 +150,7 @@ public class WxMpKefuServiceImplTest { } @Test(dataProvider = "getKfAccountAndOpenid") - public void testKfSessionGet(String kfAccount, + public void testKfSessionGet(@SuppressWarnings("unused") String kfAccount, String openid) throws WxErrorException { WxMpKfSessionGetResult result = this.wxService.getKefuService() .kfSessionGet(openid); diff --git a/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/demo/DemoGuessNumberHandler.java b/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/demo/DemoGuessNumberHandler.java index 6db18923..a6fb1e53 100644 --- a/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/demo/DemoGuessNumberHandler.java +++ b/weixin-java-mp/src/test/java/me/chanjar/weixin/mp/demo/DemoGuessNumberHandler.java @@ -1,5 +1,9 @@ package me.chanjar.weixin.mp.demo; +import java.util.Map; +import java.util.Random; +import java.util.regex.Pattern; + import me.chanjar.weixin.common.exception.WxErrorException; import me.chanjar.weixin.common.session.WxSession; import me.chanjar.weixin.common.session.WxSessionManager; @@ -10,10 +14,6 @@ import me.chanjar.weixin.mp.bean.WxMpCustomMessage; import me.chanjar.weixin.mp.bean.WxMpXmlMessage; import me.chanjar.weixin.mp.bean.WxMpXmlOutMessage; -import java.util.Map; -import java.util.Random; -import java.util.regex.Pattern; - public class DemoGuessNumberHandler implements WxMpMessageHandler, WxMpMessageMatcher { private Random random = new Random(); @@ -57,14 +57,14 @@ public class DemoGuessNumberHandler implements WxMpMessageHandler, WxMpMessageMa .toUser(wxMessage.getFromUserName()) .content("请猜一个100以内的数字") .build(); - wxMpService.customMessageSend(m); + wxMpService.getKefuService().customMessageSend(m); } else { WxMpCustomMessage m = WxMpCustomMessage .TEXT() .toUser(wxMessage.getFromUserName()) .content("放弃了吗?那请重新猜一个100以内的数字") .build(); - wxMpService.customMessageSend(m); + wxMpService.getKefuService().customMessageSend(m); } session.setAttribute("guessing", Boolean.TRUE); @@ -92,7 +92,7 @@ public class DemoGuessNumberHandler implements WxMpMessageHandler, WxMpMessageMa .toUser(wxMessage.getFromUserName()) .content("小了") .build(); - wxMpService.customMessageSend(m); + wxMpService.getKefuService().customMessageSend(m); } else if (guessNumber > answer) { WxMpCustomMessage m = WxMpCustomMessage @@ -100,7 +100,7 @@ public class DemoGuessNumberHandler implements WxMpMessageHandler, WxMpMessageMa .toUser(wxMessage.getFromUserName()) .content("大了") .build(); - wxMpService.customMessageSend(m); + wxMpService.getKefuService().customMessageSend(m); } else { WxMpCustomMessage m = WxMpCustomMessage .TEXT() @@ -108,7 +108,7 @@ public class DemoGuessNumberHandler implements WxMpMessageHandler, WxMpMessageMa .content("Bingo!") .build(); session.removeAttribute("guessing"); - wxMpService.customMessageSend(m); + wxMpService.getKefuService().customMessageSend(m); } }