| @@ -8,13 +8,22 @@ import me.chanjar.weixin.common.session.WxSessionManager; | |||
| import java.util.Map; | |||
| /** | |||
| * 处理小程序推送消息的处理器接口 | |||
| * 处理小程序推送消息的处理器接口. | |||
| * | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| */ | |||
| public interface WxMaMessageHandler { | |||
| void handle(WxMaMessage message, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException; | |||
| /** | |||
| * 处理消息. | |||
| * | |||
| * @param message 输入消息 | |||
| * @param context 上下文 | |||
| * @param service 服务类 | |||
| * @param sessionManager session管理器 | |||
| * @return 输出消息 | |||
| * @throws WxErrorException 异常 | |||
| */ | |||
| WxMaXmlOutMessage handle(WxMaMessage message, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException; | |||
| } | |||
| @@ -8,17 +8,21 @@ import me.chanjar.weixin.common.session.WxSessionManager; | |||
| import java.util.Map; | |||
| /** | |||
| * 微信消息拦截器,可以用来做验证 | |||
| * 微信消息拦截器,可以用来做验证. | |||
| * | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| */ | |||
| public interface WxMaMessageInterceptor { | |||
| /** | |||
| * 拦截微信消息 | |||
| * 拦截微信消息. | |||
| * | |||
| * @param context 上下文,如果handler或interceptor之间有信息要传递,可以用这个 | |||
| * @param wxMessage . | |||
| * @param context 上下文,如果handler或interceptor之间有信息要传递,可以用这个 | |||
| * @param wxMaService . | |||
| * @param sessionManager . | |||
| * @return true代表OK,false代表不OK | |||
| * @throws WxErrorException . | |||
| */ | |||
| boolean intercept(WxMaMessage wxMessage, | |||
| Map<String, Object> context, | |||
| @@ -3,14 +3,17 @@ package cn.binarywang.wx.miniapp.message; | |||
| import cn.binarywang.wx.miniapp.bean.WxMaMessage; | |||
| /** | |||
| * 消息匹配器,用在消息路由的时候 | |||
| * 消息匹配器,用在消息路由的时候. | |||
| * | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| */ | |||
| public interface WxMaMessageMatcher { | |||
| /** | |||
| * 消息是否匹配某种模式 | |||
| * 消息是否匹配某种模式. | |||
| * | |||
| * @param message 消息 | |||
| * @return 是否匹配 | |||
| */ | |||
| boolean match(WxMaMessage message); | |||
| @@ -32,8 +32,6 @@ public class WxMaMessageRouter { | |||
| private ExecutorService executorService; | |||
| private WxMessageDuplicateChecker messageDuplicateChecker; | |||
| private WxSessionManager sessionManager; | |||
| private WxErrorExceptionHandler exceptionHandler; | |||
| @@ -43,7 +41,6 @@ public class WxMaMessageRouter { | |||
| ThreadFactory namedThreadFactory = new ThreadFactoryBuilder().setNameFormat("WxMaMessageRouter-pool-%d").build(); | |||
| this.executorService = new ThreadPoolExecutor(DEFAULT_THREAD_POOL_SIZE, DEFAULT_THREAD_POOL_SIZE, | |||
| 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), namedThreadFactory); | |||
| this.messageDuplicateChecker = new WxMessageInMemoryDuplicateChecker(); | |||
| this.sessionManager = new StandardSessionManager(); | |||
| this.exceptionHandler = new LogExceptionHandler(); | |||
| } | |||
| @@ -58,16 +55,6 @@ public class WxMaMessageRouter { | |||
| this.executorService = executorService; | |||
| } | |||
| /** | |||
| * <pre> | |||
| * 设置自定义的 {@link me.chanjar.weixin.common.api.WxMessageDuplicateChecker} | |||
| * 如果不调用该方法,默认使用 {@link me.chanjar.weixin.common.api.WxMessageInMemoryDuplicateChecker} | |||
| * </pre> | |||
| */ | |||
| public void setMessageDuplicateChecker(WxMessageDuplicateChecker messageDuplicateChecker) { | |||
| this.messageDuplicateChecker = messageDuplicateChecker; | |||
| } | |||
| /** | |||
| * <pre> | |||
| * 设置自定义的{@link me.chanjar.weixin.common.session.WxSessionManager} | |||
| @@ -93,16 +80,16 @@ public class WxMaMessageRouter { | |||
| } | |||
| /** | |||
| * 开始一个新的Route规则 | |||
| * 开始一个新的Route规则. | |||
| */ | |||
| public WxMaMessageRouterRule rule() { | |||
| return new WxMaMessageRouterRule(this); | |||
| } | |||
| /** | |||
| * 处理微信消息 | |||
| * 处理微信消息. | |||
| */ | |||
| public void route(final WxMaMessage wxMessage, final Map<String, Object> context) { | |||
| private WxMaXmlOutMessage route(final WxMaMessage wxMessage, final Map<String, Object> context) { | |||
| final List<WxMaMessageRouterRule> matchRules = new ArrayList<>(); | |||
| // 收集匹配的规则 | |||
| for (final WxMaMessageRouterRule rule : this.rules) { | |||
| @@ -115,10 +102,11 @@ public class WxMaMessageRouter { | |||
| } | |||
| if (matchRules.size() == 0) { | |||
| return; | |||
| return null; | |||
| } | |||
| final List<Future<?>> futures = new ArrayList<>(); | |||
| WxMaXmlOutMessage result = null; | |||
| for (final WxMaMessageRouterRule rule : matchRules) { | |||
| // 返回最后一个非异步的rule的执行结果 | |||
| if (rule.isAsync()) { | |||
| @@ -131,7 +119,7 @@ public class WxMaMessageRouter { | |||
| }) | |||
| ); | |||
| } else { | |||
| rule.service(wxMessage, context, this.wxMaService, this.sessionManager, this.exceptionHandler); | |||
| result = rule.service(wxMessage, context, this.wxMaService, this.sessionManager, this.exceptionHandler); | |||
| // 在同步操作结束,session访问结束 | |||
| this.log.debug("End session access: async=false, sessionId={}", wxMessage.getFromUser()); | |||
| sessionEndAccess(wxMessage); | |||
| @@ -155,18 +143,17 @@ public class WxMaMessageRouter { | |||
| } | |||
| }); | |||
| } | |||
| return result; | |||
| } | |||
| public void route(final WxMaMessage wxMessage) { | |||
| this.route(wxMessage, new HashMap<String, Object>(2)); | |||
| public WxMaXmlOutMessage route(final WxMaMessage wxMessage) { | |||
| return this.route(wxMessage, new HashMap<String, Object>(2)); | |||
| } | |||
| /** | |||
| * 对session的访问结束 | |||
| * 对session的访问结束. | |||
| */ | |||
| protected void sessionEndAccess(WxMaMessage wxMessage) { | |||
| private void sessionEndAccess(WxMaMessage wxMessage) { | |||
| InternalSession session = ((InternalSessionManager) this.sessionManager).findSession(wxMessage.getFromUser()); | |||
| if (session != null) { | |||
| session.endAccess(); | |||
| @@ -16,7 +16,6 @@ import java.util.regex.Pattern; | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| */ | |||
| public class WxMaMessageRouterRule { | |||
| private final WxMaMessageRouter routerBuilder; | |||
| private boolean async = true; | |||
| @@ -46,7 +45,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 设置是否异步执行,默认是true | |||
| * 设置是否异步执行,默认是true. | |||
| */ | |||
| public WxMaMessageRouterRule async(boolean async) { | |||
| this.async = async; | |||
| @@ -54,7 +53,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果msgType等于某值 | |||
| * 如果msgType等于某值. | |||
| */ | |||
| public WxMaMessageRouterRule msgType(String msgType) { | |||
| this.msgType = msgType; | |||
| @@ -62,7 +61,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果event等于某值 | |||
| * 如果event等于某值. | |||
| */ | |||
| public WxMaMessageRouterRule event(String event) { | |||
| this.event = event; | |||
| @@ -70,7 +69,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果eventKey等于某值 | |||
| * 如果eventKey等于某值. | |||
| */ | |||
| public WxMaMessageRouterRule eventKey(String eventKey) { | |||
| this.eventKey = eventKey; | |||
| @@ -78,7 +77,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果content等于某值 | |||
| * 如果content等于某值. | |||
| */ | |||
| public WxMaMessageRouterRule content(String content) { | |||
| this.content = content; | |||
| @@ -86,7 +85,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果content匹配该正则表达式 | |||
| * 如果content匹配该正则表达式. | |||
| */ | |||
| public WxMaMessageRouterRule rContent(String regex) { | |||
| this.rContent = regex; | |||
| @@ -94,7 +93,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果fromUser等于某值 | |||
| * 如果fromUser等于某值. | |||
| */ | |||
| public WxMaMessageRouterRule fromUser(String fromUser) { | |||
| this.fromUser = fromUser; | |||
| @@ -102,7 +101,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 如果消息匹配某个matcher,用在用户需要自定义更复杂的匹配规则的时候 | |||
| * 如果消息匹配某个matcher,用在用户需要自定义更复杂的匹配规则的时候. | |||
| */ | |||
| public WxMaMessageRouterRule matcher(WxMaMessageMatcher matcher) { | |||
| this.matcher = matcher; | |||
| @@ -110,14 +109,14 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 设置微信消息拦截器 | |||
| * 设置微信消息拦截器. | |||
| */ | |||
| public WxMaMessageRouterRule interceptor(WxMaMessageInterceptor interceptor) { | |||
| return interceptor(interceptor, (WxMaMessageInterceptor[]) null); | |||
| } | |||
| /** | |||
| * 设置微信消息拦截器 | |||
| * 设置微信消息拦截器. | |||
| */ | |||
| public WxMaMessageRouterRule interceptor(WxMaMessageInterceptor interceptor, WxMaMessageInterceptor... otherInterceptors) { | |||
| this.interceptors.add(interceptor); | |||
| @@ -130,14 +129,14 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 设置微信消息处理器 | |||
| * 设置微信消息处理器. | |||
| */ | |||
| public WxMaMessageRouterRule handler(WxMaMessageHandler handler) { | |||
| return handler(handler, (WxMaMessageHandler[]) null); | |||
| } | |||
| /** | |||
| * 设置微信消息处理器 | |||
| * 设置微信消息处理器. | |||
| */ | |||
| public WxMaMessageRouterRule handler(WxMaMessageHandler handler, WxMaMessageHandler... otherHandlers) { | |||
| this.handlers.add(handler); | |||
| @@ -150,7 +149,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 规则结束,代表如果一个消息匹配该规则,那么它将不再会进入其他规则 | |||
| * 规则结束,代表如果一个消息匹配该规则,那么它将不再会进入其他规则. | |||
| */ | |||
| public WxMaMessageRouter end() { | |||
| this.routerBuilder.getRules().add(this); | |||
| @@ -158,7 +157,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 规则结束,但是消息还会进入其他规则 | |||
| * 规则结束,但是消息还会进入其他规则. | |||
| */ | |||
| public WxMaMessageRouter next() { | |||
| this.reEnter = true; | |||
| @@ -166,7 +165,7 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 将微信自定义的事件修正为不区分大小写, | |||
| * 将微信自定义的事件修正为不区分大小写. | |||
| * 比如框架定义的事件常量为click,但微信传递过来的却是CLICK | |||
| */ | |||
| protected boolean test(WxMaMessage wxMessage) { | |||
| @@ -188,9 +187,9 @@ public class WxMaMessageRouterRule { | |||
| } | |||
| /** | |||
| * 处理微信推送过来的消息 | |||
| * 处理微信推送过来的消息. | |||
| */ | |||
| protected void service(WxMaMessage wxMessage, | |||
| protected WxMaXmlOutMessage service(WxMaMessage wxMessage, | |||
| Map<String, Object> context, | |||
| WxMaService wxMaService, | |||
| WxSessionManager sessionManager, | |||
| @@ -199,11 +198,12 @@ public class WxMaMessageRouterRule { | |||
| context = new HashMap<>(16); | |||
| } | |||
| WxMaXmlOutMessage outMessage = null; | |||
| try { | |||
| // 如果拦截器不通过 | |||
| for (WxMaMessageInterceptor interceptor : this.interceptors) { | |||
| if (!interceptor.intercept(wxMessage, context, wxMaService, sessionManager)) { | |||
| return; | |||
| return null; | |||
| } | |||
| } | |||
| @@ -213,11 +213,13 @@ public class WxMaMessageRouterRule { | |||
| if (handler == null) { | |||
| continue; | |||
| } | |||
| handler.handle(wxMessage, context, wxMaService, sessionManager); | |||
| outMessage = handler.handle(wxMessage, context, wxMaService, sessionManager); | |||
| } | |||
| } catch (WxErrorException e) { | |||
| exceptionHandler.handle(e); | |||
| } | |||
| return outMessage; | |||
| } | |||
| public WxMaMessageRouter getRouterBuilder() { | |||
| @@ -0,0 +1,60 @@ | |||
| package cn.binarywang.wx.miniapp.message; | |||
| import cn.binarywang.wx.miniapp.config.WxMaConfig; | |||
| import cn.binarywang.wx.miniapp.util.crypt.WxMaCryptUtils; | |||
| import cn.binarywang.wx.miniapp.util.xml.XStreamTransformer; | |||
| import com.thoughtworks.xstream.annotations.XStreamAlias; | |||
| import com.thoughtworks.xstream.annotations.XStreamConverter; | |||
| import lombok.AllArgsConstructor; | |||
| import lombok.Builder; | |||
| import lombok.Data; | |||
| import lombok.NoArgsConstructor; | |||
| import lombok.experimental.Accessors; | |||
| import me.chanjar.weixin.common.util.xml.XStreamCDataConverter; | |||
| import java.io.Serializable; | |||
| /** | |||
| * 微信小程序输出给微信服务器的消息. | |||
| * | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| * @date 2019-06-22 | |||
| */ | |||
| @Data | |||
| @XStreamAlias("xml") | |||
| @Accessors(chain = true) | |||
| @Builder | |||
| @AllArgsConstructor | |||
| @NoArgsConstructor | |||
| public class WxMaXmlOutMessage implements Serializable { | |||
| private static final long serialVersionUID = 4241135225946919153L; | |||
| @XStreamAlias("ToUserName") | |||
| @XStreamConverter(value = XStreamCDataConverter.class) | |||
| protected String toUserName; | |||
| @XStreamAlias("FromUserName") | |||
| @XStreamConverter(value = XStreamCDataConverter.class) | |||
| protected String fromUserName; | |||
| @XStreamAlias("CreateTime") | |||
| protected Long createTime; | |||
| @XStreamAlias("MsgType") | |||
| @XStreamConverter(value = XStreamCDataConverter.class) | |||
| protected String msgType; | |||
| @SuppressWarnings("unchecked") | |||
| public String toXml() { | |||
| return XStreamTransformer.toXml((Class<WxMaXmlOutMessage>) this.getClass(), this); | |||
| } | |||
| /** | |||
| * 转换成加密的xml格式. | |||
| */ | |||
| public String toEncryptedXml(WxMaConfig config) { | |||
| String plainXml = toXml(); | |||
| WxMaCryptUtils pc = new WxMaCryptUtils(config); | |||
| return pc.encrypt(plainXml); | |||
| } | |||
| } | |||
| @@ -1,15 +1,5 @@ | |||
| package cn.binarywang.wx.miniapp.demo; | |||
| import java.io.File; | |||
| import java.io.IOException; | |||
| import java.io.InputStream; | |||
| import java.util.Map; | |||
| import java.util.concurrent.locks.ReentrantLock; | |||
| import org.eclipse.jetty.server.Server; | |||
| import org.eclipse.jetty.servlet.ServletHandler; | |||
| import org.eclipse.jetty.servlet.ServletHolder; | |||
| import cn.binarywang.wx.miniapp.api.WxMaService; | |||
| import cn.binarywang.wx.miniapp.api.impl.WxMaServiceImpl; | |||
| import cn.binarywang.wx.miniapp.bean.WxMaKefuMessage; | |||
| @@ -20,11 +10,23 @@ import cn.binarywang.wx.miniapp.config.WxMaConfig; | |||
| import cn.binarywang.wx.miniapp.constant.WxMaConstants; | |||
| import cn.binarywang.wx.miniapp.message.WxMaMessageHandler; | |||
| import cn.binarywang.wx.miniapp.message.WxMaMessageRouter; | |||
| import cn.binarywang.wx.miniapp.message.WxMaXmlOutMessage; | |||
| import cn.binarywang.wx.miniapp.test.TestConfig; | |||
| import com.google.common.collect.Lists; | |||
| import me.chanjar.weixin.common.api.WxConsts; | |||
| import me.chanjar.weixin.common.bean.result.WxMediaUploadResult; | |||
| import me.chanjar.weixin.common.error.WxErrorException; | |||
| import me.chanjar.weixin.common.session.WxSessionManager; | |||
| import org.eclipse.jetty.server.Server; | |||
| import org.eclipse.jetty.servlet.ServletHandler; | |||
| import org.eclipse.jetty.servlet.ServletHolder; | |||
| import java.io.File; | |||
| import java.io.IOException; | |||
| import java.io.InputStream; | |||
| import java.util.Calendar; | |||
| import java.util.Map; | |||
| import java.util.concurrent.locks.ReentrantLock; | |||
| /** | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| @@ -33,29 +35,31 @@ public class WxMaDemoServer { | |||
| private static final WxMaMessageHandler logHandler = new WxMaMessageHandler() { | |||
| @Override | |||
| public void handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException { | |||
| public WxMaXmlOutMessage handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException { | |||
| System.out.println("收到消息:" + wxMessage.toString()); | |||
| service.getMsgService().sendKefuMsg(WxMaKefuMessage.newTextBuilder().content("收到信息为:" + wxMessage.toJson()) | |||
| .toUser(wxMessage.getFromUser()).build()); | |||
| return null; | |||
| } | |||
| }; | |||
| private static final WxMaMessageHandler textHandler = new WxMaMessageHandler() { | |||
| @Override | |||
| public void handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) | |||
| public WxMaXmlOutMessage handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) | |||
| throws WxErrorException { | |||
| service.getMsgService().sendKefuMsg(WxMaKefuMessage.newTextBuilder().content("回复文本消息") | |||
| .toUser(wxMessage.getFromUser()).build()); | |||
| return null; | |||
| } | |||
| }; | |||
| private static final WxMaMessageHandler picHandler = new WxMaMessageHandler() { | |||
| @Override | |||
| public void handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException { | |||
| public WxMaXmlOutMessage handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException { | |||
| try { | |||
| WxMediaUploadResult uploadResult = service.getMediaService() | |||
| .uploadMedia(WxMaConstants.MediaType.IMAGE, "png", | |||
| @@ -69,13 +73,14 @@ public class WxMaDemoServer { | |||
| } catch (WxErrorException e) { | |||
| e.printStackTrace(); | |||
| } | |||
| return null; | |||
| } | |||
| }; | |||
| private static final WxMaMessageHandler qrcodeHandler = new WxMaMessageHandler() { | |||
| @Override | |||
| public void handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException { | |||
| public WxMaXmlOutMessage handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) throws WxErrorException { | |||
| try { | |||
| final File file = service.getQrcodeService().createQrcode("123", 430); | |||
| WxMediaUploadResult uploadResult = service.getMediaService().uploadMedia(WxMaConstants.MediaType.IMAGE, file); | |||
| @@ -88,13 +93,14 @@ public class WxMaDemoServer { | |||
| } catch (WxErrorException e) { | |||
| e.printStackTrace(); | |||
| } | |||
| return null; | |||
| } | |||
| }; | |||
| private static final WxMaMessageHandler templateMsgHandler = new WxMaMessageHandler() { | |||
| @Override | |||
| public void handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) | |||
| public WxMaXmlOutMessage handle(WxMaMessage wxMessage, Map<String, Object> context, | |||
| WxMaService service, WxSessionManager sessionManager) | |||
| throws WxErrorException { | |||
| service.getMsgService().sendTemplateMsg(WxMaTemplateMessage.builder() | |||
| .templateId(templateId).data(Lists.newArrayList( | |||
| @@ -102,10 +108,22 @@ public class WxMaDemoServer { | |||
| .toUser(wxMessage.getFromUser()) | |||
| .formId("自己替换可用的formid") | |||
| .build()); | |||
| return null; | |||
| } | |||
| }; | |||
| private static final WxMaMessageHandler customerServiceMessageHandler = new WxMaMessageHandler() { | |||
| @Override | |||
| public WxMaXmlOutMessage handle(WxMaMessage message, Map<String, Object> context, WxMaService service, WxSessionManager sessionManager) { | |||
| return new WxMaXmlOutMessage() | |||
| .setMsgType(WxConsts.XmlMsgType.TRANSFER_CUSTOMER_SERVICE) | |||
| .setFromUserName(message.getToUser()) | |||
| .setCreateTime(Calendar.getInstance().getTimeInMillis() / 1000) | |||
| .setToUserName(message.getFromUser()); | |||
| } | |||
| }; | |||
| private static WxMaConfig config; | |||
| private static WxMaService service; | |||
| private static WxMaMessageRouter router; | |||
| @@ -142,7 +160,8 @@ public class WxMaDemoServer { | |||
| .rule().async(false).content("模板").handler(templateMsgHandler).end() | |||
| .rule().async(false).content("文本").handler(textHandler).end() | |||
| .rule().async(false).content("图片").handler(picHandler).end() | |||
| .rule().async(false).content("二维码").handler(qrcodeHandler).end(); | |||
| .rule().async(false).content("二维码").handler(qrcodeHandler).end() | |||
| .rule().async(false).content("转发客服").handler(customerServiceMessageHandler).end(); | |||
| } catch (IOException e) { | |||
| e.printStackTrace(); | |||
| } | |||
| @@ -5,6 +5,8 @@ import cn.binarywang.wx.miniapp.bean.WxMaMessage; | |||
| import cn.binarywang.wx.miniapp.config.WxMaConfig; | |||
| import cn.binarywang.wx.miniapp.constant.WxMaConstants; | |||
| import cn.binarywang.wx.miniapp.message.WxMaMessageRouter; | |||
| import cn.binarywang.wx.miniapp.message.WxMaXmlOutMessage; | |||
| import lombok.AllArgsConstructor; | |||
| import org.apache.commons.io.IOUtils; | |||
| import org.apache.commons.lang3.StringUtils; | |||
| @@ -18,19 +20,13 @@ import java.util.Objects; | |||
| /** | |||
| * @author <a href="https://github.com/binarywang">Binary Wang</a> | |||
| */ | |||
| @AllArgsConstructor | |||
| public class WxMaPortalServlet extends HttpServlet { | |||
| private static final long serialVersionUID = 1L; | |||
| private WxMaConfig wxMaConfig; | |||
| private WxMaService wxMaService; | |||
| private WxMaMessageRouter wxMaMessageRouter; | |||
| WxMaPortalServlet(WxMaConfig wxMaConfig, WxMaService wxMaService, | |||
| WxMaMessageRouter wxMaMessageRouter) { | |||
| this.wxMaConfig = wxMaConfig; | |||
| this.wxMaService = wxMaService; | |||
| this.wxMaMessageRouter = wxMaMessageRouter; | |||
| } | |||
| private WxMaConfig config; | |||
| private WxMaService service; | |||
| private WxMaMessageRouter messageRouter; | |||
| @Override | |||
| protected void service(HttpServletRequest request, HttpServletResponse response) | |||
| @@ -42,7 +38,7 @@ public class WxMaPortalServlet extends HttpServlet { | |||
| String nonce = request.getParameter("nonce"); | |||
| String timestamp = request.getParameter("timestamp"); | |||
| if (!this.wxMaService.checkSignature(timestamp, nonce, signature)) { | |||
| if (!this.service.checkSignature(timestamp, nonce, signature)) { | |||
| // 消息签名不正确,说明不是公众平台发过来的消息 | |||
| response.getWriter().println("非法请求"); | |||
| return; | |||
| @@ -56,7 +52,7 @@ public class WxMaPortalServlet extends HttpServlet { | |||
| } | |||
| String encryptType = request.getParameter("encrypt_type"); | |||
| final boolean isJson = Objects.equals(this.wxMaConfig.getMsgDataFormat(), WxMaConstants.MsgDataFormat.JSON); | |||
| final boolean isJson = Objects.equals(this.config.getMsgDataFormat(), WxMaConstants.MsgDataFormat.JSON); | |||
| if (StringUtils.isBlank(encryptType)) { | |||
| // 明文传输的消息 | |||
| WxMaMessage inMessage; | |||
| @@ -66,7 +62,12 @@ public class WxMaPortalServlet extends HttpServlet { | |||
| inMessage = WxMaMessage.fromXml(request.getInputStream()); | |||
| } | |||
| this.wxMaMessageRouter.route(inMessage); | |||
| final WxMaXmlOutMessage outMessage = this.messageRouter.route(inMessage); | |||
| if (outMessage != null) { | |||
| response.getWriter().write(outMessage.toXml()); | |||
| return; | |||
| } | |||
| response.getWriter().write("success"); | |||
| return; | |||
| } | |||
| @@ -76,12 +77,16 @@ public class WxMaPortalServlet extends HttpServlet { | |||
| String msgSignature = request.getParameter("msg_signature"); | |||
| WxMaMessage inMessage; | |||
| if (isJson) { | |||
| inMessage = WxMaMessage.fromEncryptedJson(request.getInputStream(), this.wxMaConfig); | |||
| inMessage = WxMaMessage.fromEncryptedJson(request.getInputStream(), this.config); | |||
| } else {//xml | |||
| inMessage = WxMaMessage.fromEncryptedXml(request.getInputStream(), this.wxMaConfig, timestamp, nonce, msgSignature); | |||
| inMessage = WxMaMessage.fromEncryptedXml(request.getInputStream(), this.config, timestamp, nonce, msgSignature); | |||
| } | |||
| this.wxMaMessageRouter.route(inMessage); | |||
| final WxMaXmlOutMessage outMessage = this.messageRouter.route(inMessage); | |||
| if (outMessage != null) { | |||
| response.getWriter().write(outMessage.toEncryptedXml(this.config)); | |||
| return; | |||
| } | |||
| response.getWriter().write("success"); | |||
| return; | |||
| } | |||