From 135b1318f5f61c1d5f97cdbb09244f7d6d00c3c9 Mon Sep 17 00:00:00 2001 From: jinyu Date: Tue, 5 Jul 2016 18:49:27 +0800 Subject: [PATCH] =?UTF-8?q?=E5=88=9D=E5=A7=8B=E5=8C=96=E5=BC=80=E6=94=BE?= =?UTF-8?q?=E5=B9=B3=E5=8F=B0=E7=AC=AC=E4=B8=89=E6=96=B9=E7=BB=84=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGE.md | 8 +- .../foxinmy/weixin4j/token/TicketManager.java | 49 +++++--- weixin4j-mp/CHANGE.md | 14 ++- .../foxinmy/weixin4j/mp/api/ComponentApi.java | 71 +++++++++++ .../WeixinComponentPreCodeCreator.java | 49 ++++++++ .../WeixinComponentTokenCreator.java | 48 ++++++++ .../foxinmy/weixin4j/mp/type/URLConsts.java | 15 ++- weixin4j-qy/CHANGE.md | 6 +- .../com/foxinmy/weixin4j/qy/WeixinProxy.java | 8 +- .../foxinmy/weixin4j/qy/WeixinSuiteProxy.java | 39 +++---- .../com/foxinmy/weixin4j/qy/api/SuiteApi.java | 70 +++++------ .../qy/suite/WeixinSuiteTokenCreator.java | 11 +- .../mp/component/ComponentEventType.java | 28 +++++ .../mp/component/ComponentMessage.java | 110 ++++++++++++++++++ .../server/ext/SuiteMessageHandler.java | 49 ++++++++ 15 files changed, 481 insertions(+), 94 deletions(-) rename weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/SuiteTicketManager.java => weixin4j-base/src/main/java/com/foxinmy/weixin4j/token/TicketManager.java (53%) create mode 100644 weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/ComponentApi.java create mode 100644 weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentPreCodeCreator.java create mode 100644 weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentTokenCreator.java create mode 100644 weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentEventType.java create mode 100644 weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentMessage.java create mode 100644 weixin4j-server/src/test/java/com/foxinmy/weixin4j/server/ext/SuiteMessageHandler.java diff --git a/CHANGE.md b/CHANGE.md index f306065e..b9c11ed2 100644 --- a/CHANGE.md +++ b/CHANGE.md @@ -705,7 +705,7 @@ * 2016-05-28 - + 重构Cache实现 + + weixin4j-base:重构Cache实现 * 2016-05-30 @@ -717,4 +717,8 @@ * 2016-06-20 - + version upgrade to 1.7.0 \ No newline at end of file + + version upgrade to 1.7.0 + +* 2016-07-05 + + + weixin4j-mp:初始化开放平台第三方组件TokenCreator \ No newline at end of file diff --git a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/SuiteTicketManager.java b/weixin4j-base/src/main/java/com/foxinmy/weixin4j/token/TicketManager.java similarity index 53% rename from weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/SuiteTicketManager.java rename to weixin4j-base/src/main/java/com/foxinmy/weixin4j/token/TicketManager.java index 9aa3977c..82ee829d 100644 --- a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/SuiteTicketManager.java +++ b/weixin4j-base/src/main/java/com/foxinmy/weixin4j/token/TicketManager.java @@ -1,29 +1,45 @@ -package com.foxinmy.weixin4j.qy.suite; +package com.foxinmy.weixin4j.token; import com.foxinmy.weixin4j.cache.CacheStorager; import com.foxinmy.weixin4j.exception.WeixinException; import com.foxinmy.weixin4j.model.Token; -import com.foxinmy.weixin4j.token.TokenCreator; /** - * 应用套件ticket的存取 + * 第三方应用ticket的存取 * - * @className SuiteTicketManager + * @className TicketManager * @author jinyu(foxinmy@gmail.com) * @date 2015年6月22日 * @since JDK 1.6 * @see */ -public class SuiteTicketManager { +public class TicketManager { - private final String suiteId; - private final String suiteSecret; + /** + * 第三方ID + */ + private final String id; + /** + * 第三方secret + */ + private final String secret; + /** + * ticket存储策略 + */ private final CacheStorager cacheStorager; - public SuiteTicketManager(String suiteId, String suiteSecret, - CacheStorager cacheStorager) { - this.suiteId = suiteId; - this.suiteSecret = suiteSecret; + /** + * + * @param id + * 第三方ID + * @param secret + * 第三方secret + * @param cacheStorager + * ticket存储策略 + */ + public TicketManager(String id, String secret, CacheStorager cacheStorager) { + this.id = id; + this.secret = secret; this.cacheStorager = cacheStorager; } @@ -43,8 +59,7 @@ public class SuiteTicketManager { * @return */ public String getCacheKey() { - return String.format("%sqy_suite_ticket_%s", - TokenCreator.CACHEKEY_PREFIX, suiteId); + return String.format("%sthird_party_ticket_%s", TokenCreator.CACHEKEY_PREFIX, id); } /** @@ -58,12 +73,12 @@ public class SuiteTicketManager { cacheStorager.caching(getCacheKey(), token); } - public String getSuiteId() { - return this.suiteId; + public String getId() { + return id; } - public String getSuiteSecret() { - return this.suiteSecret; + public String getSecret() { + return secret; } public CacheStorager getCacheStorager() { diff --git a/weixin4j-mp/CHANGE.md b/weixin4j-mp/CHANGE.md index feabb8e1..2f202616 100644 --- a/weixin4j-mp/CHANGE.md +++ b/weixin4j-mp/CHANGE.md @@ -220,4 +220,16 @@ * 2016-05-07 - + version upgrade to 1.6.9 \ No newline at end of file + + version upgrade to 1.6.9 + +* 2016-05-30 + + + 新增接口调用次数清零接口 + +* 2016-06-20 + + + version upgrade to 1.7.0 + +* 2016-07-05 + + + 初始化开放平台第三方组件TokenCreator \ No newline at end of file diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/ComponentApi.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/ComponentApi.java new file mode 100644 index 00000000..f3001549 --- /dev/null +++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/api/ComponentApi.java @@ -0,0 +1,71 @@ +package com.foxinmy.weixin4j.mp.api; + +import com.foxinmy.weixin4j.mp.component.WeixinComponentPreCodeCreator; +import com.foxinmy.weixin4j.mp.component.WeixinComponentTokenCreator; +import com.foxinmy.weixin4j.token.TicketManager; +import com.foxinmy.weixin4j.token.TokenManager; + +/** + * 第三方应用组件 + * + * @className ComponentApi + * @author jinyu(foxinmy@gmail.com) + * @date 2015年6月17日 + * @since JDK 1.6 + * @see 第三方应用组件概述 + */ +public class ComponentApi extends MpApi { + /** + * 应用套件token + */ + private final TokenManager tokenManager; + /** + * 应用套件ticket + */ + private final TicketManager ticketManager; + /** + * 应用套件pre_code + */ + private final TokenManager preCodeManager; + + /** + * + * @param ticketManager + * 组件ticket存取 + */ + public ComponentApi(TicketManager ticketManager) { + this.ticketManager = ticketManager; + this.tokenManager = new TokenManager(new WeixinComponentTokenCreator(ticketManager), + ticketManager.getCacheStorager()); + this.preCodeManager = new TokenManager(new WeixinComponentPreCodeCreator(tokenManager, ticketManager.getId()), + ticketManager.getCacheStorager()); + } + + /** + * 应用组件token + * + * @return + */ + public TokenManager getTokenManager() { + return this.tokenManager; + } + + /** + * 应用组件ticket + * + * @return + */ + public TicketManager getTicketManager() { + return this.ticketManager; + } + + /** + * 应用组件预授权码 + * + * @return + */ + public TokenManager getPreCodeManager() { + return this.preCodeManager; + } +} diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentPreCodeCreator.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentPreCodeCreator.java new file mode 100644 index 00000000..1d742923 --- /dev/null +++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentPreCodeCreator.java @@ -0,0 +1,49 @@ +package com.foxinmy.weixin4j.mp.component; + +import com.alibaba.fastjson.JSONObject; +import com.foxinmy.weixin4j.exception.WeixinException; +import com.foxinmy.weixin4j.http.weixin.WeixinResponse; +import com.foxinmy.weixin4j.model.Token; +import com.foxinmy.weixin4j.mp.type.URLConsts; +import com.foxinmy.weixin4j.token.TokenCreator; +import com.foxinmy.weixin4j.token.TokenManager; + +/** + * 微信企业号应用套件预授权码创建 + * + * @className WeixinComponentPreCodeCreator + * @author jinyu(foxinmy@gmail.com) + * @date 2016年7月5日 + * @since JDK 1.6 + */ +public class WeixinComponentPreCodeCreator extends TokenCreator { + + private final TokenManager componentTokenManager; + private final String componentId; + + /** + * + * @param componentTokenManager + * 应用套件的token + * @param componentId + * 应用组件ID + */ + public WeixinComponentPreCodeCreator(TokenManager componentTokenManager, String componentId) { + this.componentTokenManager = componentTokenManager; + this.componentId = componentId; + } + + @Override + public String key0() { + return String.format("mp_component_precode_%s", componentId); + } + + @Override + public Token create() throws WeixinException { + WeixinResponse response = weixinExecutor.post( + String.format(URLConsts.COMPONENET_PRE_CODE_URL, componentTokenManager.getAccessToken()), + String.format("{\"component_appid\":\"%s\"}", componentId)); + JSONObject result = response.getAsJson(); + return new Token(result.getString("pre_auth_code"), result.getLongValue("expires_in") * 1000l); + } +} diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentTokenCreator.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentTokenCreator.java new file mode 100644 index 00000000..de3cadce --- /dev/null +++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/component/WeixinComponentTokenCreator.java @@ -0,0 +1,48 @@ +package com.foxinmy.weixin4j.mp.component; + +import com.alibaba.fastjson.JSONObject; +import com.foxinmy.weixin4j.exception.WeixinException; +import com.foxinmy.weixin4j.http.weixin.WeixinResponse; +import com.foxinmy.weixin4j.model.Token; +import com.foxinmy.weixin4j.mp.type.URLConsts; +import com.foxinmy.weixin4j.token.TicketManager; +import com.foxinmy.weixin4j.token.TokenCreator; + +/** + * 微信公众号应用组件凭证创建 + * + * @className WeixinComponentTokenCreator + * @author jinyu(foxinmy@gmail.com) + * @date 2016年7月5日 + * @since JDK 1.6 + */ +public class WeixinComponentTokenCreator extends TokenCreator { + private final TicketManager ticketManager; + + /** + * + * @param ticketManager + * 组件ticket存取 + */ + public WeixinComponentTokenCreator(TicketManager ticketManager) { + this.ticketManager = ticketManager; + } + + @Override + public String key0() { + return String.format("mp_component_token_%s", ticketManager.getId()); + } + + @Override + public Token create() throws WeixinException { + JSONObject obj = new JSONObject(); + obj.put("component_appid", ticketManager.getId()); + obj.put("component_appsecret", ticketManager.getSecret()); + obj.put("component_verify_ticket", ticketManager.getTicket()); + WeixinResponse response = weixinExecutor.post( + URLConsts.COMPONENT_TOKEN_URL, obj.toJSONString()); + obj = response.getAsJson(); + return new Token(obj.getString("suite_access_token"), + obj.getLongValue("expires_in") * 1000l); + } +} diff --git a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/type/URLConsts.java b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/type/URLConsts.java index 0283b754..b5f57e5d 100644 --- a/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/type/URLConsts.java +++ b/weixin4j-mp/src/main/java/com/foxinmy/weixin4j/mp/type/URLConsts.java @@ -14,11 +14,18 @@ public final class URLConsts { /** * 公众平台获取token的url */ - public static final String ASSESS_TOKEN_URL = BASE_URL - + "/token?grant_type=client_credential&appid=%s&secret=%s"; + public static final String ASSESS_TOKEN_URL = BASE_URL + "/token?grant_type=client_credential&appid=%s&secret=%s"; /** * 公众平台jssdk获取token的url */ - public static final String JS_TICKET_URL = BASE_URL - + "/ticket/getticket?access_token=%s&type=%s"; + public static final String JS_TICKET_URL = BASE_URL + "/ticket/getticket?access_token=%s&type=%s"; + /** + * 开发平台获取token的url + */ + public static final String COMPONENT_TOKEN_URL = BASE_URL + "/component/api_component_token"; + /** + * 开发平台获取预授权码的url + */ + public static final String COMPONENET_PRE_CODE_URL = BASE_URL + + "/component/api_create_preauthcode?component_access_token=%s"; } diff --git a/weixin4j-qy/CHANGE.md b/weixin4j-qy/CHANGE.md index d897359b..183b6bee 100644 --- a/weixin4j-qy/CHANGE.md +++ b/weixin4j-qy/CHANGE.md @@ -183,4 +183,8 @@ * 2016-05-07 - + version upgrade to 1.6.9 \ No newline at end of file + + version upgrade to 1.6.9 + +* 2016-06-20 + + + version upgrade to 1.7.0 \ No newline at end of file diff --git a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinProxy.java b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinProxy.java index d7e06127..a025f591 100644 --- a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinProxy.java +++ b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinProxy.java @@ -140,16 +140,16 @@ public class WeixinProxy { * @param perCodeManager * 第三方套件永久授权码 * {@link com.foxinmy.weixin4j.qy.api.SuiteApi#getPerCodeManager(String)} - * @param suitetokenManager + * @param perTokenManager * 第三方套件凭证token - * {@link com.foxinmy.weixin4j.qy.api.SuiteApi#getTokenSuiteManager(String)} + * {@link com.foxinmy.weixin4j.qy.api.SuiteApi#getPerTokenManager(String)} * @see com.foxinmy.weixin4j.qy.api.SuiteApi * @see WeixinSuiteProxy#getWeixinProxy(String, String) */ public WeixinProxy(SuitePerCodeManager perCodeManager, - TokenManager suiteTokenManager) { + TokenManager perTokenManager) { this(new TokenManager(new WeixinTokenSuiteCreator(perCodeManager, - suiteTokenManager), perCodeManager.getCacheStorager())); + perTokenManager), perCodeManager.getCacheStorager())); this.settings = new Weixin4jSettings(new WeixinAccount( perCodeManager.getAuthCorpId(), null)); } diff --git a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinSuiteProxy.java b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinSuiteProxy.java index c751d6ff..d1627cde 100644 --- a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinSuiteProxy.java +++ b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/WeixinSuiteProxy.java @@ -14,11 +14,11 @@ import com.foxinmy.weixin4j.qy.api.ProviderApi; import com.foxinmy.weixin4j.qy.api.SuiteApi; import com.foxinmy.weixin4j.qy.model.OUserInfo; import com.foxinmy.weixin4j.qy.model.WeixinQyAccount; -import com.foxinmy.weixin4j.qy.suite.SuiteTicketManager; import com.foxinmy.weixin4j.qy.token.WeixinProviderTokenCreator; import com.foxinmy.weixin4j.qy.type.LoginTargetType; import com.foxinmy.weixin4j.qy.type.URLConsts; import com.foxinmy.weixin4j.setting.Weixin4jSettings; +import com.foxinmy.weixin4j.token.TicketManager; import com.foxinmy.weixin4j.token.TokenManager; import com.foxinmy.weixin4j.util.StringUtil; import com.foxinmy.weixin4j.util.Weixin4jConfigUtil; @@ -54,8 +54,8 @@ public class WeixinSuiteProxy { * 默认使用文件方式保存token、使用weixin4j.properties配置的账号信息 */ public WeixinSuiteProxy() { - this(new Weixin4jSettings(JSON.parseObject( - Weixin4jConfigUtil.getValue("account"), WeixinQyAccount.class))); + this(new Weixin4jSettings( + JSON.parseObject(Weixin4jConfigUtil.getValue("account"), WeixinQyAccount.class))); } /** @@ -69,22 +69,16 @@ public class WeixinSuiteProxy { if (suites != null && !suites.isEmpty()) { this.suiteMap = new HashMap(suites.size()); for (WeixinAccount suite : suites) { - this.suiteMap.put( - suite.getId(), - new SuiteApi( - new SuiteTicketManager(suite.getId(), suite - .getSecret(), settings - .getCacheStorager0()))); + this.suiteMap.put(suite.getId(), new SuiteApi( + new TicketManager(suite.getId(), suite.getSecret(), settings.getCacheStorager0()))); } this.suiteMap.put(null, suiteMap.get(suites.get(0).getId())); } if (StringUtil.isNotBlank(settings.getAccount().getId()) - && StringUtil.isNotBlank(settings.getAccount() - .getProviderSecret())) { + && StringUtil.isNotBlank(settings.getAccount().getProviderSecret())) { this.providerApi = new ProviderApi( - new TokenManager(new WeixinProviderTokenCreator(settings - .getAccount().getId(), settings.getAccount() - .getProviderSecret()), settings.getCacheStorager0()), + new TokenManager(new WeixinProviderTokenCreator(settings.getAccount().getId(), + settings.getAccount().getProviderSecret()), settings.getCacheStorager0()), settings.getCacheStorager0()); } } @@ -132,8 +126,7 @@ public class WeixinSuiteProxy { * 推送suite_ticket协议 * @throws WeixinException */ - public void cacheTicket(String suiteId, String suiteTicket) - throws WeixinException { + public void cacheTicket(String suiteId, String suiteTicket) throws WeixinException { suite(suiteId).getTicketManager().cachingTicket(suiteTicket); } @@ -148,8 +141,7 @@ public class WeixinSuiteProxy { * @throws WeixinException */ public String getSuiteAuthorizeURL(String suiteId) throws WeixinException { - String redirectUri = Weixin4jConfigUtil - .getValue("suite.oauth.redirect.uri"); + String redirectUri = Weixin4jConfigUtil.getValue("suite.oauth.redirect.uri"); return getSuiteAuthorizeURL(suiteId, redirectUri, "state"); } @@ -169,11 +161,9 @@ public class WeixinSuiteProxy { * @return 请求授权的URL * @throws WeixinException */ - public String getSuiteAuthorizeURL(String suiteId, String redirectUri, - String state) throws WeixinException { + public String getSuiteAuthorizeURL(String suiteId, String redirectUri, String state) throws WeixinException { try { - return String.format(URLConsts.SUITE_OAUTH_URL, suiteId, - suite(suiteId).getTicketManager().getTicket(), + return String.format(URLConsts.SUITE_OAUTH_URL, suiteId, suite(suiteId).getTicketManager().getTicket(), URLEncoder.encode(redirectUri, Consts.UTF_8.name()), state); } catch (UnsupportedEncodingException e) { ; @@ -215,8 +205,7 @@ public class WeixinSuiteProxy { * 获取登录企业号官网的url * @throws WeixinException */ - public String getLoginUrl(String corpId, LoginTargetType targetType, - int agentId) throws WeixinException { + public String getLoginUrl(String corpId, LoginTargetType targetType, int agentId) throws WeixinException { return providerApi.getLoginUrl(corpId, targetType, agentId); } @@ -232,7 +221,7 @@ public class WeixinSuiteProxy { */ public WeixinProxy getWeixinProxy(String suiteId, String authCorpId) { return new WeixinProxy(suite(suiteId).getPerCodeManager(authCorpId), - suite(suiteId).getSuiteTokenManager()); + suite(suiteId).getPerTokenManager(authCorpId)); } public final static String VERSION = "1.7.0"; diff --git a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/api/SuiteApi.java b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/api/SuiteApi.java index 709d4d41..8f6ff973 100644 --- a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/api/SuiteApi.java +++ b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/api/SuiteApi.java @@ -11,10 +11,10 @@ import com.foxinmy.weixin4j.qy.model.AgentSetter; import com.foxinmy.weixin4j.qy.model.OUserInfo; import com.foxinmy.weixin4j.qy.model.User; import com.foxinmy.weixin4j.qy.suite.SuitePerCodeManager; -import com.foxinmy.weixin4j.qy.suite.SuiteTicketManager; import com.foxinmy.weixin4j.qy.suite.WeixinSuitePreCodeCreator; import com.foxinmy.weixin4j.qy.suite.WeixinSuiteTokenCreator; import com.foxinmy.weixin4j.qy.suite.WeixinTokenSuiteCreator; +import com.foxinmy.weixin4j.token.TicketManager; import com.foxinmy.weixin4j.token.TokenCreator; import com.foxinmy.weixin4j.token.TokenManager; @@ -32,29 +32,29 @@ public class SuiteApi extends QyApi { /** * 应用套件token */ - private final TokenManager suiteTokenManager; + private final TokenManager tokenManager; /** * 应用套件ticket */ - private final SuiteTicketManager suiteTicketManager; + private final TicketManager ticketManager; /** * 应用套件pre_code */ - private final TokenManager suitePreCodeManager; + private final TokenManager preCodeManager; /** * - * @param suiteTicketManager + * @param ticketManager * 套件ticket存取 */ - public SuiteApi(SuiteTicketManager suiteTicketManager) { - this.suiteTicketManager = suiteTicketManager; - this.suiteTokenManager = new TokenManager(new WeixinSuiteTokenCreator( - suiteTicketManager), suiteTicketManager.getCacheStorager()); - this.suitePreCodeManager = new TokenManager( - new WeixinSuitePreCodeCreator(suiteTokenManager, - suiteTicketManager.getSuiteId()), - suiteTicketManager.getCacheStorager()); + public SuiteApi(TicketManager ticketManager) { + this.ticketManager = ticketManager; + this.tokenManager = new TokenManager(new WeixinSuiteTokenCreator( + ticketManager), ticketManager.getCacheStorager()); + this.preCodeManager = new TokenManager( + new WeixinSuitePreCodeCreator(tokenManager, + ticketManager.getId()), + ticketManager.getCacheStorager()); } /** @@ -62,8 +62,8 @@ public class SuiteApi extends QyApi { * * @return */ - public TokenManager getSuiteTokenManager() { - return this.suiteTokenManager; + public TokenManager getTokenManager() { + return this.tokenManager; } /** @@ -71,8 +71,8 @@ public class SuiteApi extends QyApi { * * @return */ - public SuiteTicketManager getTicketManager() { - return this.suiteTicketManager; + public TicketManager getTicketManager() { + return this.ticketManager; } /** @@ -81,7 +81,7 @@ public class SuiteApi extends QyApi { * @return */ public TokenManager getPreCodeManager() { - return this.suitePreCodeManager; + return this.preCodeManager; } /** @@ -93,8 +93,8 @@ public class SuiteApi extends QyApi { */ public SuitePerCodeManager getPerCodeManager(String authCorpId) { return new SuitePerCodeManager(authCorpId, - suiteTicketManager.getSuiteId(), - suiteTicketManager.getCacheStorager()); + ticketManager.getId(), + ticketManager.getCacheStorager()); } /** @@ -104,10 +104,10 @@ public class SuiteApi extends QyApi { * 授权方corpid * @return 企业号token */ - public TokenManager getTokenSuiteManager(String authCorpId) { + public TokenManager getPerTokenManager(String authCorpId) { return new TokenManager(new WeixinTokenSuiteCreator( - getPerCodeManager(authCorpId), suiteTokenManager), - suiteTicketManager.getCacheStorager()); + getPerCodeManager(authCorpId), tokenManager), + ticketManager.getCacheStorager()); } /** @@ -124,13 +124,13 @@ public class SuiteApi extends QyApi { public JsonResult setSuiteSession(int... appids) throws WeixinException { String suite_set_session_uri = getRequestUri("suite_set_session_uri"); JSONObject para = new JSONObject(); - para.put("pre_auth_code", suitePreCodeManager.getAccessToken()); + para.put("pre_auth_code", preCodeManager.getAccessToken()); JSONObject appid = new JSONObject(); appid.put("appid", appids); para.put("session_info", appid); WeixinResponse response = weixinExecutor.post( String.format(suite_set_session_uri, - suiteTokenManager.getAccessToken()), + tokenManager.getAccessToken()), para.toJSONString()); return response.getAsJsonResult(); } @@ -151,11 +151,11 @@ public class SuiteApi extends QyApi { throws WeixinException { String suite_get_permanent_uri = getRequestUri("suite_get_permanent_uri"); JSONObject obj = new JSONObject(); - obj.put("suite_id", suiteTicketManager.getSuiteId()); + obj.put("suite_id", ticketManager.getId()); obj.put("auth_code", authCode); WeixinResponse response = weixinExecutor .post(String.format(suite_get_permanent_uri, - suiteTokenManager.getAccessToken()), obj.toJSONString()); + tokenManager.getAccessToken()), obj.toJSONString()); obj = response.getAsJson(); obj.put("corp_info", obj.remove("auth_corp_info")); obj.put("user_info", obj.remove("auth_user_info")); @@ -165,10 +165,10 @@ public class SuiteApi extends QyApi { .getCorpInfo().getCorpId()); // 缓存微信企业号access_token TokenCreator tokenCreator = new WeixinTokenSuiteCreator( - suitePerCodeManager, suiteTokenManager); + suitePerCodeManager, tokenManager); Token token = new Token(obj.getString("access_token"), obj.getLongValue("expires_in") * 1000l); - suiteTicketManager.getCacheStorager() + ticketManager.getCacheStorager() .caching(tokenCreator.key(), token); // 缓存微信企业号永久授权码 suitePerCodeManager.cachingPermanentCode(obj @@ -190,13 +190,13 @@ public class SuiteApi extends QyApi { public OUserInfo getOAuthInfo(String authCorpId) throws WeixinException { String suite_get_authinfo_uri = getRequestUri("suite_get_authinfo_uri"); JSONObject obj = new JSONObject(); - obj.put("suite_id", suiteTicketManager.getSuiteId()); + obj.put("suite_id", ticketManager.getId()); obj.put("auth_corpid", authCorpId); obj.put("permanent_code", getPerCodeManager(authCorpId) .getPermanentCode()); WeixinResponse response = weixinExecutor .post(String.format(suite_get_authinfo_uri, - suiteTokenManager.getAccessToken()), obj.toJSONString()); + tokenManager.getAccessToken()), obj.toJSONString()); obj = response.getAsJson(); obj.put("corp_info", obj.remove("auth_corp_info")); obj.put("user_info", obj.remove("auth_user_info")); @@ -220,14 +220,14 @@ public class SuiteApi extends QyApi { throws WeixinException { String suite_get_agent_uri = getRequestUri("suite_get_agent_uri"); JSONObject obj = new JSONObject(); - obj.put("suite_id", suiteTicketManager.getSuiteId()); + obj.put("suite_id", ticketManager.getId()); obj.put("auth_corpid", authCorpId); obj.put("permanent_code", getPerCodeManager(authCorpId) .getPermanentCode()); obj.put("agentid", agentid); WeixinResponse response = weixinExecutor .post(String.format(suite_get_agent_uri, - suiteTokenManager.getAccessToken()), obj.toJSONString()); + tokenManager.getAccessToken()), obj.toJSONString()); JSONObject jsonObj = response.getAsJson(); AgentInfo agent = JSON.toJavaObject(jsonObj, AgentInfo.class); agent.setAllowUsers(JSON.parseArray( @@ -258,14 +258,14 @@ public class SuiteApi extends QyApi { throws WeixinException { String suite_set_agent_uri = getRequestUri("suite_set_agent_uri"); JSONObject obj = new JSONObject(); - obj.put("suite_id", suiteTicketManager.getSuiteId()); + obj.put("suite_id", ticketManager.getId()); obj.put("auth_corpid", authCorpId); obj.put("permanent_code", getPerCodeManager(authCorpId) .getPermanentCode()); obj.put("agent", agentSet); WeixinResponse response = weixinExecutor.post( String.format(suite_set_agent_uri, - suiteTokenManager.getAccessToken()), + tokenManager.getAccessToken()), JSON.toJSONString(obj, AgentApi.typeFilter)); return response.getAsJsonResult(); } diff --git a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/WeixinSuiteTokenCreator.java b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/WeixinSuiteTokenCreator.java index 8d4e3c72..54c638d9 100644 --- a/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/WeixinSuiteTokenCreator.java +++ b/weixin4j-qy/src/main/java/com/foxinmy/weixin4j/qy/suite/WeixinSuiteTokenCreator.java @@ -5,6 +5,7 @@ import com.foxinmy.weixin4j.exception.WeixinException; import com.foxinmy.weixin4j.http.weixin.WeixinResponse; import com.foxinmy.weixin4j.model.Token; import com.foxinmy.weixin4j.qy.type.URLConsts; +import com.foxinmy.weixin4j.token.TicketManager; import com.foxinmy.weixin4j.token.TokenCreator; /** @@ -20,27 +21,27 @@ import com.foxinmy.weixin4j.token.TokenCreator; */ public class WeixinSuiteTokenCreator extends TokenCreator { - private final SuiteTicketManager ticketManager; + private final TicketManager ticketManager; /** * * @param ticketManager * 套件ticket存取 */ - public WeixinSuiteTokenCreator(SuiteTicketManager ticketManager) { + public WeixinSuiteTokenCreator(TicketManager ticketManager) { this.ticketManager = ticketManager; } @Override public String key0() { - return String.format("qy_suite_token_%s", ticketManager.getSuiteId()); + return String.format("qy_suite_token_%s", ticketManager.getId()); } @Override public Token create() throws WeixinException { JSONObject obj = new JSONObject(); - obj.put("suite_id", ticketManager.getSuiteId()); - obj.put("suite_secret", ticketManager.getSuiteSecret()); + obj.put("suite_id", ticketManager.getId()); + obj.put("suite_secret", ticketManager.getSecret()); obj.put("suite_ticket", ticketManager.getTicket()); WeixinResponse response = weixinExecutor.post( URLConsts.SUITE_TOKEN_URL, obj.toJSONString()); diff --git a/weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentEventType.java b/weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentEventType.java new file mode 100644 index 00000000..9507814b --- /dev/null +++ b/weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentEventType.java @@ -0,0 +1,28 @@ +package com.foxinmy.weixin4j.mp.component; + +/** + * 应用组件回调事件 + * + * @className ComponentEventType + * @author jinyu(foxinmy@gmail.com) + * @date 2016年7月5日 + * @since JDK 1.6 + */ +public enum ComponentEventType { + /** + * 推送ticket + */ + component_verify_ticket, + /** + * 取消授权 + */ + unauthorized, + /** + * 授权成功 + */ + authorized, + /** + * 授权更新 + */ + updateauthorized +} diff --git a/weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentMessage.java b/weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentMessage.java new file mode 100644 index 00000000..d9e3623a --- /dev/null +++ b/weixin4j-server/src/main/java/com/foxinmy/weixin4j/mp/component/ComponentMessage.java @@ -0,0 +1,110 @@ +package com.foxinmy.weixin4j.mp.component; + +import java.io.Serializable; +import java.util.Date; + +import javax.xml.bind.annotation.XmlAccessType; +import javax.xml.bind.annotation.XmlAccessorType; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; +import javax.xml.bind.annotation.XmlTransient; + +/** + * 组件消息 + * + * @className ComponentMessage + * @author jinyu(foxinmy@gmail.com) + * @date 2016年7月5日 + * @since JDK 1.6 + */ +@XmlRootElement(name = "xml") +@XmlAccessorType(XmlAccessType.FIELD) +public class ComponentMessage implements Serializable { + + private static final long serialVersionUID = -7243616276403632118L; + /** + * 第三方平台appid + */ + @XmlElement(name = "AppId") + private String appId; + /** + * 事件类型 + */ + @XmlElement(name = "InfoType") + private String eventType; + /** + * 时间戳 + */ + @XmlElement(name = "CreateTime") + private long createTime; + /** + * Ticket内容 + */ + @XmlElement(name = "ComponentVerifyTicket") + private String verifyTicket; + /** + * 授权方的Appid + */ + @XmlElement(name = "AuthorizerAppid") + private String authAppId; + /** + * 授权码,可用于换取公众号的接口调用凭据 + */ + @XmlElement(name = "AuthorizationCode") + private String authCode; + /** + * 授权码过期时间 + */ + @XmlElement(name = "AuthorizationCodeExpiredTime") + private long authCodeExpiredTime; + + public String getAppId() { + return appId; + } + + public String getEventType() { + return eventType; + } + + @XmlTransient + public ComponentEventType getFormatEventType() { + return ComponentEventType.valueOf(eventType); + } + + public long getCreateTime() { + return createTime; + } + + @XmlTransient + public Date getFormatCreateTime() { + return createTime > 0l ? new Date(createTime * 1000l) : null; + } + + public String getVerifyTicket() { + return verifyTicket; + } + + public String getAuthAppId() { + return authAppId; + } + + public String getAuthCode() { + return authCode; + } + + public long getAuthCodeExpiredTime() { + return authCodeExpiredTime; + } + + @XmlTransient + public Date getFormatAuthCodeExpiredTime() { + return authCodeExpiredTime > 0l ? new Date(authCodeExpiredTime * 1000l) : null; + } + + @Override + public String toString() { + return "ComponentMessage [appId=" + appId + ", eventType=" + eventType + ", createTime=" + createTime + + ", verifyTicket=" + verifyTicket + ", authAppId=" + authAppId + ", authCode=" + authCode + + ", authCodeExpiredTime=" + authCodeExpiredTime + "]"; + } +} diff --git a/weixin4j-server/src/test/java/com/foxinmy/weixin4j/server/ext/SuiteMessageHandler.java b/weixin4j-server/src/test/java/com/foxinmy/weixin4j/server/ext/SuiteMessageHandler.java new file mode 100644 index 00000000..d9e9f30a --- /dev/null +++ b/weixin4j-server/src/test/java/com/foxinmy/weixin4j/server/ext/SuiteMessageHandler.java @@ -0,0 +1,49 @@ +package com.foxinmy.weixin4j.server.ext; + +import java.util.Set; + +import com.foxinmy.weixin4j.exception.WeixinException; +import com.foxinmy.weixin4j.handler.WeixinMessageHandler; +import com.foxinmy.weixin4j.qy.suite.SuiteEventType; +import com.foxinmy.weixin4j.qy.suite.SuiteMessage; +import com.foxinmy.weixin4j.request.WeixinMessage; +import com.foxinmy.weixin4j.request.WeixinRequest; +import com.foxinmy.weixin4j.response.BlankResponse; +import com.foxinmy.weixin4j.response.WeixinResponse; + +/** + * 企业号套件消息处理 + * + * @className SuiteMessageHandler + * @author jy + * @date 2015年6月25日 + * @since JDK 1.6 + */ +public class SuiteMessageHandler implements WeixinMessageHandler { + + @Override + public boolean canHandle(WeixinRequest request, WeixinMessage message, Set nodeNames) + throws WeixinException { + return nodeNames.contains("suiteid"); + } + + @Override + public WeixinResponse doHandle(WeixinRequest request, WeixinMessage message, Set nodeNames) + throws WeixinException { + SuiteMessage suiteMessage = null; // 转换为 SuiteMessage + SuiteEventType eventType = suiteMessage.getFormatEventType(); + if (eventType == SuiteEventType.suite_ticket) { + // do something + } else if (eventType == SuiteEventType.change_auth) { + // do something + } else if (eventType == SuiteEventType.cancel_auth) { + // do something + } + return BlankResponse.global; + } + + @Override + public int weight() { + return 0; + } +}