diff --git a/cloud-common-wechat/pom.xml b/cloud-common-wechat/pom.xml new file mode 100644 index 0000000..efc2849 --- /dev/null +++ b/cloud-common-wechat/pom.xml @@ -0,0 +1,22 @@ + + + + cm-cloud + com.cm + 1.0.1-SNAPSHOT + + 4.0.0 + + cloud-common-wechat + + + + com.cm + cloud-common + 1.0.1-SNAPSHOT + + + + \ No newline at end of file diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/WechatFilterConfig.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/WechatFilterConfig.java new file mode 100644 index 0000000..8bb9ed7 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/WechatFilterConfig.java @@ -0,0 +1,31 @@ +package com.cm.common.wechat.config; + +import com.cm.common.wechat.filter.WechatFilter; +import org.springframework.boot.web.servlet.FilterRegistrationBean; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatFilterConfig + * @Description: 微信过滤器 + * @Author: WangGeng + * @Date: 2020/3/2 11:24 下午 + * @Version: 1.0 + **/ +@Configuration +public class WechatFilterConfig { + + @Bean + public FilterRegistrationBean wechatFilterRegister() { + FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean(); + filterRegistrationBean.setFilter(new WechatFilter()); + filterRegistrationBean.addUrlPatterns("/wechat/**", "/wechatroute/**"); + filterRegistrationBean.setName("wechatFilter"); + filterRegistrationBean.setOrder(2); + return filterRegistrationBean; + } + +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/pojo/WechatOfficialAccountAuthorizeProperties.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/pojo/WechatOfficialAccountAuthorizeProperties.java new file mode 100644 index 0000000..6d0b1ea --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/pojo/WechatOfficialAccountAuthorizeProperties.java @@ -0,0 +1,89 @@ +package com.cm.common.wechat.config.pojo; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.context.annotation.Configuration; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatOfficialAccountAuthorizeProperties + * @Description: 微信公众号授权配置 + * @Author: WangGeng + * @Date: 2020/3/2 3:15 下午 + * @Version: 1.0 + **/ +public class WechatOfficialAccountAuthorizeProperties { + private String authorizeUrl; + private String accessTokenUrl; + private String accessTokenRefreshUrl; + private String userinfoUrl; + private String responseType; + private String scope; + private String state; + private String grantType; + + public String getAuthorizeUrl() { + return authorizeUrl == null ? "" : authorizeUrl.trim(); + } + + public void setAuthorizeUrl(String authorizeUrl) { + this.authorizeUrl = authorizeUrl; + } + + public String getAccessTokenUrl() { + return accessTokenUrl == null ? "" : accessTokenUrl.trim(); + } + + public void setAccessTokenUrl(String accessTokenUrl) { + this.accessTokenUrl = accessTokenUrl; + } + + public String getAccessTokenRefreshUrl() { + return accessTokenRefreshUrl == null ? "" : accessTokenRefreshUrl.trim(); + } + + public void setAccessTokenRefreshUrl(String accessTokenRefreshUrl) { + this.accessTokenRefreshUrl = accessTokenRefreshUrl; + } + + public String getUserinfoUrl() { + return userinfoUrl == null ? "" : userinfoUrl.trim(); + } + + public void setUserinfoUrl(String userinfoUrl) { + this.userinfoUrl = userinfoUrl; + } + + public String getResponseType() { + return responseType == null ? "" : responseType.trim(); + } + + public void setResponseType(String responseType) { + this.responseType = responseType; + } + + public String getScope() { + return scope == null ? "" : scope.trim(); + } + + public void setScope(String scope) { + this.scope = scope; + } + + public String getState() { + return state == null ? "" : state.trim(); + } + + public void setState(String state) { + this.state = state; + } + + public String getGrantType() { + return grantType == null ? "" : grantType.trim(); + } + + public void setGrantType(String grantType) { + this.grantType = grantType; + } +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/pojo/WechatOfficialAccountProperties.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/pojo/WechatOfficialAccountProperties.java new file mode 100644 index 0000000..d5a56a3 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/config/pojo/WechatOfficialAccountProperties.java @@ -0,0 +1,66 @@ +package com.cm.common.wechat.config.pojo; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.context.annotation.Configuration; +import org.springframework.stereotype.Component; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatProperties + * @Description: 微信配置 + * @Author: WangGeng + * @Date: 2020/3/1 2:22 下午 + * @Version: 1.0 + **/ +@Configuration +@ConfigurationProperties(prefix = "open-platform.wechat.official-account") +public class WechatOfficialAccountProperties { + + private WechatOfficialAccountAuthorizeProperties authorize; + private String accessTokenUrl; + private String appId; + private String appSecret; + private String grantType; + + public WechatOfficialAccountAuthorizeProperties getAuthorize() { + return authorize; + } + + public void setAuthorize(WechatOfficialAccountAuthorizeProperties authorize) { + this.authorize = authorize; + } + + public String getAccessTokenUrl() { + return accessTokenUrl == null ? "" : accessTokenUrl.trim(); + } + + public void setAccessTokenUrl(String accessTokenUrl) { + this.accessTokenUrl = accessTokenUrl; + } + + public String getAppId() { + return appId == null ? "" : appId.trim(); + } + + public void setAppId(String appId) { + this.appId = appId; + } + + public String getAppSecret() { + return appSecret == null ? "" : appSecret.trim(); + } + + public void setAppSecret(String appSecret) { + this.appSecret = appSecret; + } + + public String getGrantType() { + return grantType == null ? "" : grantType.trim(); + } + + public void setGrantType(String grantType) { + this.grantType = grantType; + } +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/filter/WechatFilter.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/filter/WechatFilter.java new file mode 100644 index 0000000..7d03010 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/filter/WechatFilter.java @@ -0,0 +1,54 @@ +package com.cm.common.wechat.filter; + +import com.cm.common.constants.ISystemConstant; +import com.cm.common.wechat.manager.officialaccount.WechatOfficialAccountManager; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.util.StringUtils; + +import javax.servlet.*; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import java.io.IOException; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatFilter + * @Description: 微信过滤器 + * @Author: WangGeng + * @Date: 2020/3/1 11:25 上午 + * @Version: 1.0 + **/ +public class WechatFilter implements Filter { + + private static final Logger LOG = LoggerFactory.getLogger(WechatFilter.class); + + @Override + public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { + HttpServletRequest request = (HttpServletRequest) servletRequest; + HttpServletResponse response = (HttpServletResponse) servletResponse; + String requestUri = request.getRequestURI(); + // 如果参数都存在,标识从服务器重定向回页面,获取AccessToken后放行 + String codeParameter = request.getParameter("code"); + String stateParameter = request.getParameter("state"); + if (!StringUtils.isEmpty(codeParameter) && !StringUtils.isEmpty(stateParameter)) { + try { + WechatOfficialAccountManager.getInstance().setUserAccessToken(codeParameter, stateParameter, request.getSession()); + } catch (Exception e) { + LOG.error("设置微信公众号session异常"); + } + return; + } + // 判断session是否存在 + Object accessToken = request.getSession().getAttribute(ISystemConstant.SESSION_WECHAT_ACCESS_TOKEN); + // session 不存在重定向登录 + if (StringUtils.isEmpty(accessToken)) { + response.sendRedirect(WechatOfficialAccountManager.getInstance().getAuthorizeUrl(requestUri)); + return; + } + filterChain.doFilter(request, response); + } + +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/manager/officialaccount/WechatOfficialAccountManager.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/manager/officialaccount/WechatOfficialAccountManager.java new file mode 100644 index 0000000..d4ebb14 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/manager/officialaccount/WechatOfficialAccountManager.java @@ -0,0 +1,207 @@ +package com.cm.common.wechat.manager.officialaccount; + +import com.cm.common.constants.ISystemConstant; +import com.cm.common.exception.SearchException; +import com.cm.common.exception.WechatAccessTokenException; +import com.cm.common.exception.WechatAccessTokenForUserException; +import com.cm.common.exception.WechatUserInfoException; +import com.cm.common.utils.AesUtil; +import com.cm.common.utils.http.RestRequestUtil; +import com.cm.common.wechat.config.pojo.WechatOfficialAccountProperties; +import com.cm.common.wechat.pojo.WechatOfficialAccountAccessToken; +import com.cm.common.wechat.pojo.WechatOfficialAccountAccessTokenForUser; +import com.cm.common.wechat.pojo.WechatOfficialAccountUser; +import com.cm.common.wechat.pojo.WechatOfficialAccountUserInfo; +import org.apache.commons.codec.binary.Base64; +import org.apache.commons.lang3.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.boot.web.client.RestTemplateBuilder; +import org.springframework.http.HttpEntity; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.web.client.RestTemplate; + +import javax.servlet.http.HttpSession; +import java.util.HashMap; +import java.util.Map; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatOfficialAccountManager + * @Description: 公众号管理器 + * @Author: WangGeng + * @Date: 2020/3/1 3:02 下午 + * @Version: 1.0 + **/ +public class WechatOfficialAccountManager { + + private static final Logger LOG = LoggerFactory.getLogger(WechatOfficialAccountManager.class); + private static WechatOfficialAccountManager wechatOfficialAccountManager = WechatOfficialAccountManagerBuilder.wechatOfficialAccountManager; + + private WechatOfficialAccountProperties wechatOfficialAccountProperties; + private String accessToken; + private long updateTime = 0L; + + public static WechatOfficialAccountManager getInstance() { + return wechatOfficialAccountManager; + } + + public String getAccessToken() { + return accessToken; + } + + /** + * 刷新AccessToken,超过1小时30分刷新一次 + */ + public void refreshAccessToken() { + long currentTime = System.currentTimeMillis(); + if ((currentTime - this.updateTime) >= 5400000) { + LOG.debug("刷新公众号 AccessToken 开始"); + this.accessToken = getNewAccessToken(); + this.updateTime = System.currentTimeMillis(); + LOG.debug("刷新公众号 AccessToken 结束"); + } + } + + /** + * 获得新AccessToken + * + * @return + */ + private String getNewAccessToken() { + RestTemplate restTemplate = new RestTemplateBuilder().build(); + Map params = new HashMap<>(3); + params.put("grant_type", wechatOfficialAccountProperties.getGrantType()); + params.put("appid", wechatOfficialAccountProperties.getAppId()); + params.put("secret", wechatOfficialAccountProperties.getAppSecret()); + String url = new StringBuilder(wechatOfficialAccountProperties.getAccessTokenUrl()).append("?grant_type={grant_type}&appid={appid}&secret={secret}").toString(); + WechatOfficialAccountAccessToken wechatOfficialAccountAccessToken = restTemplate.getForObject(url, WechatOfficialAccountAccessToken.class, params); + if (wechatOfficialAccountAccessToken == null) { + throw new WechatAccessTokenException("获取 AccessToken 失败"); + } + if (wechatOfficialAccountAccessToken.getErrcode() != null && wechatOfficialAccountAccessToken.getErrcode() != 0) { + throw new WechatAccessTokenException(String.format("获取AccessToken失败,错误码:%s,错误信息:%s", wechatOfficialAccountAccessToken.getErrcode(), wechatOfficialAccountAccessToken.getErrmsg())); + } + return wechatOfficialAccountAccessToken.getAccess_token(); + } + + public void setWechatOfficialAccountProperties(WechatOfficialAccountProperties wechatOfficialAccountProperties) { + this.wechatOfficialAccountProperties = wechatOfficialAccountProperties; + } + + /** + * 重定向url + * + * @param requestUri + * @return + */ + public String getAuthorizeUrl(String requestUri) { + StringBuilder authorizeUrl = new StringBuilder(wechatOfficialAccountProperties.getAuthorize().getAuthorizeUrl()); + authorizeUrl.append("?appid=").append(wechatOfficialAccountProperties.getAppId()); + authorizeUrl.append("&scope=").append(wechatOfficialAccountProperties.getAuthorize().getScope()); + authorizeUrl.append("&state=").append(wechatOfficialAccountProperties.getAuthorize().getState()); + authorizeUrl.append("&redirect_uri=").append(requestUri); + authorizeUrl.append("&response_type=code#wechat_redirect"); + return authorizeUrl.toString(); + } + + /** + * 设置用户信息 + * + * @param code + * @param state + * @param session + */ + public void setUserAccessToken(String code, String state, HttpSession session) throws Exception { + if (!StringUtils.equals(state, wechatOfficialAccountProperties.getAuthorize().getState())) { + WechatOfficialAccountAccessTokenForUser wechatOfficialAccountAccessTokenForUser = getUserAccessToken(code); + WechatOfficialAccountUserInfo wechatOfficialAccountUserInfo = getUserInfo(wechatOfficialAccountAccessTokenForUser.getAccess_token(), wechatOfficialAccountAccessTokenForUser.getOpenid()); + WechatOfficialAccountUser wechatOfficialAccountUser = new WechatOfficialAccountUser(); + // 绑定用户 | 登录 + String wechatSignInfo = AesUtil.aesCommonEncoder("WECHAT_SIGN_INFO", Base64.encodeBase64String(new StringBuilder(wechatOfficialAccountAccessTokenForUser.getOpenid()).append("_WenG_").append(wechatOfficialAccountProperties.getAppId()).toString().getBytes("UTF-8"))); + String token = getAppToken(wechatSignInfo); + wechatOfficialAccountUser.setToken(token); + wechatOfficialAccountUser.setWechatOfficialAccountAccessTokenForUser(wechatOfficialAccountAccessTokenForUser); + wechatOfficialAccountUser.setWechatOfficialAccountUserInfo(wechatOfficialAccountUserInfo); + session.setAttribute(ISystemConstant.SESSION_WECHAT_ACCESS_TOKEN, wechatOfficialAccountUser); + return; + } + } + + /** + * 获取AppToken + * + * @param wechatSignInfo + * @return + */ + public String getAppToken(String wechatSignInfo) { + RestTemplate restTemplate = new RestTemplate(); + Map params = new HashMap<>(1); + params.put("signInfo", wechatSignInfo); + HttpEntity> requestBody = new HttpEntity<>(params); + ResponseEntity result = restTemplate.postForEntity("", requestBody, Map.class); + if (HttpStatus.OK.value() != result.getStatusCodeValue()) { + throw new SearchException("获取Token失败"); + } + Map body = result.getBody(); + return (String) body.get("data"); + } + + /** + * 获取用户AccessToken + * + * @param code + * @return + */ + public WechatOfficialAccountAccessTokenForUser getUserAccessToken(String code) { + Map params = new HashMap<>(4); + params.put("appid", wechatOfficialAccountProperties.getAppId()); + params.put("secret", wechatOfficialAccountProperties.getAppSecret()); + params.put("code", code); + params.put("grant_type", wechatOfficialAccountProperties.getAuthorize().getGrantType()); + StringBuilder url = new StringBuilder(wechatOfficialAccountProperties.getAuthorize().getAccessTokenUrl()); + url.append("?appid={appid}&secret={secret}&code={code}&grant_type={grant_type}"); + RestTemplate restTemplate = new RestTemplate(); + WechatOfficialAccountAccessTokenForUser wechatOfficialAccountAccessTokenForUser = restTemplate.getForObject(url.toString(), WechatOfficialAccountAccessTokenForUser.class, params); + if (wechatOfficialAccountAccessTokenForUser == null) { + LOG.error("获取用户AccessToken异常"); + throw new WechatAccessTokenForUserException("获取用户AccessToken异常"); + } + if (wechatOfficialAccountAccessTokenForUser.getErrcode() != null && wechatOfficialAccountAccessTokenForUser.getErrcode() != 0) { + throw new WechatAccessTokenForUserException(String.format("获取用户AccessToken失败,错误码:%s,错误信息:%s", wechatOfficialAccountAccessTokenForUser.getErrcode(), wechatOfficialAccountAccessTokenForUser.getErrmsg())); + } + return wechatOfficialAccountAccessTokenForUser; + } + + /** + * 获取用户信息 + * + * @param accessToken + * @param openid + * @return + */ + public WechatOfficialAccountUserInfo getUserInfo(String accessToken, String openid) { + Map params = new HashMap<>(2); + params.put("access_token", accessToken); + params.put("openid", openid); + StringBuilder url = new StringBuilder(wechatOfficialAccountProperties.getAuthorize().getUserinfoUrl()); + url.append("?access_token={access_token}&openid={openid}&lang=zh_CN"); + RestTemplate restTemplate = new RestTemplate(); + WechatOfficialAccountUserInfo wechatOfficialAccountUserInfo = restTemplate.getForObject(url.toString(), WechatOfficialAccountUserInfo.class, params); + if (wechatOfficialAccountUserInfo == null) { + throw new WechatUserInfoException("获取微信用户信息失败"); + } + if (wechatOfficialAccountUserInfo.getErrcode() != null && wechatOfficialAccountUserInfo.getErrcode() != 0) { + throw new WechatAccessTokenForUserException(String.format("获取用户信息失败,错误码:%s,错误信息:%s", wechatOfficialAccountUserInfo.getErrcode(), wechatOfficialAccountUserInfo.getErrmsg())); + } + return wechatOfficialAccountUserInfo; + } + + private static class WechatOfficialAccountManagerBuilder { + public static WechatOfficialAccountManager wechatOfficialAccountManager = new WechatOfficialAccountManager(); + } + +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountAccessToken.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountAccessToken.java new file mode 100644 index 0000000..6fbfd62 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountAccessToken.java @@ -0,0 +1,51 @@ +package com.cm.common.wechat.pojo; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatOfficialAccountResult + * @Description: 微信公众号返回结果 + * @Author: WangGeng + * @Date: 2020/3/1 5:22 下午 + * @Version: 1.0 + **/ +public class WechatOfficialAccountAccessToken { + + private String access_token; + private Integer expires_in; + private Integer errcode; + private String errmsg; + + public String getAccess_token() { + return access_token == null ? "" : access_token.trim(); + } + + public void setAccess_token(String access_token) { + this.access_token = access_token; + } + + public Integer getExpires_in() { + return expires_in; + } + + public void setExpires_in(Integer expires_in) { + this.expires_in = expires_in; + } + + public Integer getErrcode() { + return errcode; + } + + public void setErrcode(Integer errcode) { + this.errcode = errcode; + } + + public String getErrmsg() { + return errmsg == null ? "" : errmsg.trim(); + } + + public void setErrmsg(String errmsg) { + this.errmsg = errmsg; + } +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountAccessTokenForUser.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountAccessTokenForUser.java new file mode 100644 index 0000000..bc9160f --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountAccessTokenForUser.java @@ -0,0 +1,78 @@ +package com.cm.common.wechat.pojo; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatOfficialAccountAccessTokenForUser + * @Description: 微信公众号用户accessToken + * @Author: WangGeng + * @Date: 2020/3/2 12:09 下午 + * @Version: 1.0 + **/ +public class WechatOfficialAccountAccessTokenForUser { + + private String access_token; + private Integer expires_in; + private String refresh_token; + private String openid; + private String scope; + private Integer errcode; + private String errmsg; + + public String getAccess_token() { + return access_token == null ? "" : access_token.trim(); + } + + public void setAccess_token(String access_token) { + this.access_token = access_token; + } + + public Integer getExpires_in() { + return expires_in; + } + + public void setExpires_in(Integer expires_in) { + this.expires_in = expires_in; + } + + public String getRefresh_token() { + return refresh_token == null ? "" : refresh_token.trim(); + } + + public void setRefresh_token(String refresh_token) { + this.refresh_token = refresh_token; + } + + public String getOpenid() { + return openid == null ? "" : openid.trim(); + } + + public void setOpenid(String openid) { + this.openid = openid; + } + + public String getScope() { + return scope == null ? "" : scope.trim(); + } + + public void setScope(String scope) { + this.scope = scope; + } + + public Integer getErrcode() { + return errcode; + } + + public void setErrcode(Integer errcode) { + this.errcode = errcode; + } + + public String getErrmsg() { + return errmsg == null ? "" : errmsg.trim(); + } + + public void setErrmsg(String errmsg) { + this.errmsg = errmsg; + } +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountUser.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountUser.java new file mode 100644 index 0000000..10439aa --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountUser.java @@ -0,0 +1,55 @@ +package com.cm.common.wechat.pojo; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatOfficialAccountUser + * @Description: 微信公众号用户信息 + * @Author: WangGeng + * @Date: 2020/3/2 1:56 下午 + * @Version: 1.0 + **/ +public class WechatOfficialAccountUser { + + private String token; + private WechatOfficialAccountAccessTokenForUser wechatOfficialAccountAccessTokenForUser; + private WechatOfficialAccountUserInfo wechatOfficialAccountUserInfo; + + public String getToken() { + return token == null ? "" : token.trim(); + } + + public void setToken(String token) { + this.token = token; + } + + public WechatOfficialAccountAccessTokenForUser getWechatOfficialAccountAccessTokenForUser() { + return wechatOfficialAccountAccessTokenForUser; + } + + public void setWechatOfficialAccountAccessTokenForUser(WechatOfficialAccountAccessTokenForUser wechatOfficialAccountAccessTokenForUser) { + this.wechatOfficialAccountAccessTokenForUser = wechatOfficialAccountAccessTokenForUser; + } + + public WechatOfficialAccountUserInfo getWechatOfficialAccountUserInfo() { + return wechatOfficialAccountUserInfo; + } + + public void setWechatOfficialAccountUserInfo(WechatOfficialAccountUserInfo wechatOfficialAccountUserInfo) { + this.wechatOfficialAccountUserInfo = wechatOfficialAccountUserInfo; + } + + @Override + public String toString() { + final StringBuilder sb = new StringBuilder("{"); + sb.append("\"token\":") + .append("\"").append(token).append("\""); + sb.append(",\"wechatOfficialAccountAccessTokenForUser\":") + .append(wechatOfficialAccountAccessTokenForUser); + sb.append(",\"wechatOfficialAccountUserInfo\":") + .append(wechatOfficialAccountUserInfo); + sb.append('}'); + return sb.toString(); + } +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountUserInfo.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountUserInfo.java new file mode 100644 index 0000000..ff6cb41 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/pojo/WechatOfficialAccountUserInfo.java @@ -0,0 +1,117 @@ +package com.cm.common.wechat.pojo; + +import io.swagger.annotations.ApiModel; +import io.swagger.annotations.ApiModelProperty; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatOfficialAccountUserInfo + * @Description: 微信公众号用户信息 + * @Author: WangGeng + * @Date: 2020/3/2 12:14 下午 + * @Version: 1.0 + **/ +public class WechatOfficialAccountUserInfo { + + private String openid; + private String nickname; + private String sex; + private String province; + private String city; + private String country; + private String headimgurl; + private String[] privilege; + private String unionid; + private Integer errcode; + private String errmsg; + + public String getOpenid() { + return openid == null ? "" : openid.trim(); + } + + public void setOpenid(String openid) { + this.openid = openid; + } + + public String getNickname() { + return nickname == null ? "" : nickname.trim(); + } + + public void setNickname(String nickname) { + this.nickname = nickname; + } + + public String getSex() { + return sex == null ? "" : sex.trim(); + } + + public void setSex(String sex) { + this.sex = sex; + } + + public String getProvince() { + return province == null ? "" : province.trim(); + } + + public void setProvince(String province) { + this.province = province; + } + + public String getCity() { + return city == null ? "" : city.trim(); + } + + public void setCity(String city) { + this.city = city; + } + + public String getCountry() { + return country == null ? "" : country.trim(); + } + + public void setCountry(String country) { + this.country = country; + } + + public String getHeadimgurl() { + return headimgurl == null ? "" : headimgurl.trim(); + } + + public void setHeadimgurl(String headimgurl) { + this.headimgurl = headimgurl; + } + + public String[] getPrivilege() { + return privilege; + } + + public void setPrivilege(String[] privilege) { + this.privilege = privilege; + } + + public String getUnionid() { + return unionid == null ? "" : unionid.trim(); + } + + public void setUnionid(String unionid) { + this.unionid = unionid; + } + + public Integer getErrcode() { + return errcode; + } + + public void setErrcode(Integer errcode) { + this.errcode = errcode; + } + + public String getErrmsg() { + return errmsg == null ? "" : errmsg.trim(); + } + + public void setErrmsg(String errmsg) { + this.errmsg = errmsg; + } +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/startup/WechatStartUp.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/startup/WechatStartUp.java new file mode 100644 index 0000000..05a3ce0 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/startup/WechatStartUp.java @@ -0,0 +1,34 @@ +package com.cm.common.wechat.startup; + +import com.cm.common.wechat.config.pojo.WechatOfficialAccountProperties; +import com.cm.common.wechat.manager.officialaccount.WechatOfficialAccountManager; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.ApplicationArguments; +import org.springframework.boot.ApplicationRunner; +import org.springframework.context.annotation.Configuration; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatStartUp + * @Description: 微信启动项 + * @Author: WangGeng + * @Date: 2020/3/1 5:05 下午 + * @Version: 1.0 + **/ +@Configuration +public class WechatStartUp implements ApplicationRunner { + + @Autowired + private WechatOfficialAccountProperties wechatOfficialAccountProperties; + + @Override + public void run(ApplicationArguments args) throws Exception { + // 初始化公众号AccessToken + WechatOfficialAccountManager wechatOfficialAccountManager = WechatOfficialAccountManager.getInstance(); + wechatOfficialAccountManager.setWechatOfficialAccountProperties(wechatOfficialAccountProperties); + wechatOfficialAccountManager.refreshAccessToken(); + } + +} diff --git a/cloud-common-wechat/src/main/java/com/cm/common/wechat/task/WechatTask.java b/cloud-common-wechat/src/main/java/com/cm/common/wechat/task/WechatTask.java new file mode 100644 index 0000000..462b2b4 --- /dev/null +++ b/cloud-common-wechat/src/main/java/com/cm/common/wechat/task/WechatTask.java @@ -0,0 +1,32 @@ +package com.cm.common.wechat.task; + +import com.cm.common.wechat.config.pojo.WechatOfficialAccountProperties; +import com.cm.common.wechat.manager.officialaccount.WechatOfficialAccountManager; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Configuration; +import org.springframework.scheduling.annotation.EnableScheduling; +import org.springframework.scheduling.annotation.Scheduled; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatTask + * @Description: 微信定时任务 + * @Author: WangGeng + * @Date: 2020/3/1 2:55 下午 + * @Version: 1.0 + **/ +@Configuration +@EnableScheduling +public class WechatTask { + + /** + * 刷新公众号AccessToken,每10分钟刷新一次 + */ + @Scheduled(cron = "0 0/10 * * * ?") + public void refreshOfficialAccountAccessToken() { + WechatOfficialAccountManager.getInstance().refreshAccessToken(); + } + +} diff --git a/cloud-common/src/main/java/com/cm/common/base/AbstractService.java b/cloud-common/src/main/java/com/cm/common/base/AbstractService.java index c02aef0..f32bcfb 100644 --- a/cloud-common/src/main/java/com/cm/common/base/AbstractService.java +++ b/cloud-common/src/main/java/com/cm/common/base/AbstractService.java @@ -59,6 +59,16 @@ public abstract class AbstractService { setSave(appTokenUser.getId(), params); } + /** + * 设置新增基础信息 + * + * @param params + * @param userId + */ + protected void setSaveInfoByUserId(Map params, String userId) { + setSave(userId, params); + } + /** * 设置新增 * @@ -95,6 +105,16 @@ public abstract class AbstractService { setUpdate(appTokenUser.getId(), params); } + /** + * 设置更新基础信息 + * + * @param params + * @param userId + */ + protected void setUpdateInfoByUserId(Map params, String userId) { + setUpdate(userId, params); + } + /** * 设置修改 * diff --git a/cloud-common/src/main/java/com/cm/common/constants/ISystemConstant.java b/cloud-common/src/main/java/com/cm/common/constants/ISystemConstant.java index 8d9d760..8f59bb0 100644 --- a/cloud-common/src/main/java/com/cm/common/constants/ISystemConstant.java +++ b/cloud-common/src/main/java/com/cm/common/constants/ISystemConstant.java @@ -28,6 +28,10 @@ public interface ISystemConstant { * 路由接口前缀 */ String ROUTE_TAGS_PREFIX = "路由接口-"; + /** + * 微信接口前缀 + */ + String API_TAGS_WECHAT_PREFIX = "微信接口-"; /** * api前缀 */ @@ -36,6 +40,10 @@ public interface ISystemConstant { * 路由前缀 */ String ROUTE_PREFIX = "/route"; + /** + * 放行后缀 + */ + String RELEASE_SUFFIX = "release"; /** * 资源前缀 */ @@ -52,6 +60,14 @@ public interface ISystemConstant { * APP放行后缀 */ String APP_RELEASE_SUFFIX = "release"; + /** + * 微信前缀 + */ + String WECHAT_PREFIX = "/wechat"; + /** + * 微信路由前缀 + */ + String WECHAT_ROUTE_PREFIX = "/wechatroute"; /** * true */ @@ -112,4 +128,12 @@ public interface ISystemConstant { * admin */ String ADMIN = "admin"; + /** + * session微信 + */ + String SESSION_WECHAT = "SESSION_WECHAT"; + /** + * session的AccessToken + */ + String SESSION_WECHAT_ACCESS_TOKEN = "SESSION_WECHAT_ACCESS_TOKEN"; } diff --git a/cloud-common/src/main/java/com/cm/common/exception/WechatAccessTokenException.java b/cloud-common/src/main/java/com/cm/common/exception/WechatAccessTokenException.java new file mode 100644 index 0000000..e948ac8 --- /dev/null +++ b/cloud-common/src/main/java/com/cm/common/exception/WechatAccessTokenException.java @@ -0,0 +1,35 @@ +package com.cm.common.exception; + +import com.cm.common.exception.base.SystemException; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatAccessTokenException + * @Description: 微信accessToken异常 + * @Author: WangGeng + * @Date: 2020/3/2 3:42 下午 + * @Version: 1.0 + **/ +public class WechatAccessTokenException extends SystemException { + + public WechatAccessTokenException() { + } + + public WechatAccessTokenException(String message) { + super(message); + } + + public WechatAccessTokenException(String message, boolean withMsg) { + super(message, withMsg); + } + + public WechatAccessTokenException(String message, Throwable cause) { + super(message, cause); + } + + public WechatAccessTokenException(Throwable cause) { + super(cause); + } +} diff --git a/cloud-common/src/main/java/com/cm/common/exception/WechatAccessTokenForUserException.java b/cloud-common/src/main/java/com/cm/common/exception/WechatAccessTokenForUserException.java new file mode 100644 index 0000000..e864ad5 --- /dev/null +++ b/cloud-common/src/main/java/com/cm/common/exception/WechatAccessTokenForUserException.java @@ -0,0 +1,35 @@ +package com.cm.common.exception; + +import com.cm.common.exception.base.SystemException; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatAccessTokenForUserException + * @Description: 微信公众号用户AccessToken异常 + * @Author: WangGeng + * @Date: 2020/3/2 3:43 下午 + * @Version: 1.0 + **/ +public class WechatAccessTokenForUserException extends SystemException { + + public WechatAccessTokenForUserException() { + } + + public WechatAccessTokenForUserException(String message) { + super(message); + } + + public WechatAccessTokenForUserException(String message, boolean withMsg) { + super(message, withMsg); + } + + public WechatAccessTokenForUserException(String message, Throwable cause) { + super(message, cause); + } + + public WechatAccessTokenForUserException(Throwable cause) { + super(cause); + } +} diff --git a/cloud-common/src/main/java/com/cm/common/exception/WechatUserInfoException.java b/cloud-common/src/main/java/com/cm/common/exception/WechatUserInfoException.java new file mode 100644 index 0000000..f469d17 --- /dev/null +++ b/cloud-common/src/main/java/com/cm/common/exception/WechatUserInfoException.java @@ -0,0 +1,34 @@ +package com.cm.common.exception; + +import com.cm.common.exception.base.SystemException; + +/** + * When you feel like quitting. Think about why you started + * 当你想要放弃的时候,想想当初你为何开始 + * + * @ClassName: WechatUserInfoException + * @Description: 微信用户异常 + * @Author: WangGeng + * @Date: 2020/3/2 3:44 下午 + * @Version: 1.0 + **/ +public class WechatUserInfoException extends SystemException { + public WechatUserInfoException() { + } + + public WechatUserInfoException(String message) { + super(message); + } + + public WechatUserInfoException(String message, boolean withMsg) { + super(message, withMsg); + } + + public WechatUserInfoException(String message, Throwable cause) { + super(message, cause); + } + + public WechatUserInfoException(Throwable cause) { + super(cause); + } +} diff --git a/pom.xml b/pom.xml index 7641f01..15f7861 100644 --- a/pom.xml +++ b/pom.xml @@ -16,6 +16,7 @@ cloud-common-plugin-oauth cloud-common-plugin-dynamic cloud-common-plugin-dictionary + cloud-common-wechat pom 成迈云