前提:公衆號必須通過認證前端
登陸公衆號 ------> 公衆號配置 ------> 功能設置java
找到「JS接口安全域名」,配置域名(域名必須通過認證)web
具體規則以下redis
【以百度域名爲例,下面輸入框中填寫的就是www.baidu.com(不知道只寫baidu.com能不能行)】spring
【若是填寫的指定路徑,那麼分享的頁面需在此路徑下】apache
控制層json
注:api
其中HttpUtils 中只使用了httpGet 來請求微信api接口安全
RedisClient把token和ticket保存進redis,限制過時時間微信
getSiteConfig僅僅用來獲取appid和secrect
加密的工具類在控制層的代碼下面
package com.mingtai.yuqing.common.controller; import com.alibaba.fastjson.JSONObject; import com.mingtai.base.model.ApiResult; import com.mingtai.yuqing.common.redis.RedisClient; import com.mingtai.yuqing.common.util.HttpUtils; import com.mingtai.yuqing.plat.tenant.service.ITenantService; import org.apache.commons.lang.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import java.util.UUID; import static com.mingtai.yuqing.common.util.SHA1.SHA1; @RestController @RequestMapping("/wx/js/") public class WxJsConfigController { @Autowired private ITenantService tenantService; private static final Integer siteId = 180; private String token = null; private String appId = null; private String secret = null; private String ticket = null; /** * 獲取微信JS配置信息 * @param url * @param datetime * @return * @throws Exception */ @RequestMapping("getConfig") public ApiResult getConfig(String url, String datetime) throws Exception { String key = "wx.ticket." + this.siteId; String nowTicket = RedisClient.get(key); getSiteConfig(); if (StringUtils.isBlank(nowTicket)) { getAccessToken(); getTicket(key); } else { this.ticket = nowTicket; } //隨機字符串 String nonceStr = UUID.randomUUID().toString().replace("-", "").substring(0, 16); //時間戳 String timestamp = datetime; //生成內容 url = url + "&t=" + datetime; String str = "jsapi_ticket=" + this.ticket + "&noncestr=" + nonceStr + "×tamp=" + timestamp + "&url=" + url; String signature = SHA1(str); JSONObject jsonObject = new JSONObject(); jsonObject.put("appId", this.appId); jsonObject.put("timestamp", timestamp); jsonObject.put("nonceStr", nonceStr); jsonObject.put("signature", signature); return new ApiResult(jsonObject); } public void getAccessToken() throws Exception { String key = "wx.token." + this.siteId; String accessToken = RedisClient.get(key); if (StringUtils.isBlank(accessToken)) { String tokenUrl = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET"; tokenUrl = tokenUrl.replace("APPID", this.appId).replace("APPSECRET", this.secret); String result = HttpUtils.doGet(tokenUrl); JSONObject json = JSONObject.parseObject(result); String newToken = json.getString("access_token"); Integer expireTime = json.getInteger("expires_in"); this.token = newToken; RedisClient.set(key, newToken, expireTime - 10); } else { this.token = accessToken; } } public void getTicket(String key) throws Exception { String url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=" + this.token + "&type=jsapi"; String nowTicket = RedisClient.get(key); String result = HttpUtils.doGet(url); JSONObject json = JSONObject.parseObject(result); nowTicket = json.getString("ticket"); Integer expireTime = json.getInteger("expires_in"); this.ticket = nowTicket; RedisClient.set(key, nowTicket, expireTime - 10); } private void getSiteConfig() { String allConfig = tenantService.getTenantById(this.siteId).getTeExpandField(); JSONObject jsonObject = JSONObject.parseObject(allConfig); this.appId = jsonObject.getString("appId"); this.secret = jsonObject.getString("secret"); } }
工具類
package com.mingtai.yuqing.common.util; import java.io.UnsupportedEncodingException; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; public class SHA1 { public static String SHA1(String decript) throws UnsupportedEncodingException { try { MessageDigest digest = MessageDigest.getInstance("SHA-1"); digest.update(decript.getBytes("utf-8")); byte messageDigest[] = digest.digest(); StringBuffer hexString = new StringBuffer(); //轉爲十六進制 for (int i = 0; i < messageDigest.length; i++) { String shaHex = Integer.toHexString(messageDigest[i] & 0xFF); if (shaHex.length() < 2) { hexString.append(0); } hexString.append(shaHex); } return hexString.toString(); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } return ""; } }
注:需先調用wxJsConfig方法
//微信js配置 wxJsConfig: function (config) { wx.config({ appId: config.appId, timestamp: config.timestamp, nonceStr: config.nonceStr, signature: config.signature, jsApiList: [ 'updateAppMessageShareData', 'updateTimelineShareData', 'onMenuShareAppMessage', //舊的接口,即將廢棄 'onMenuShareTimeline' //舊的接口,即將廢棄 ] }); }, //微信分享 wxJsShare: function (data) { //自定義「分享給朋友」及「分享到QQ」按鈕的分享內容 wx.ready(function () { wx.updateAppMessageShareData({ title: data.title, desc: data.desc, link: data.link, imgUrl: data.imgUrl, success: function () { console.log("自定義分享1"); } }); }); //自定義「分享到朋友圈」及「分享到QQ空間」按鈕的分享內容 wx.ready(function () { wx.updateTimelineShareData({ title: data.title, link: data.link, imgUrl: data.imgUrl, success: function () { console.log("自定義分享2"); } }); }); }
注:只做補充,具體問題解決方法見官方JS文檔----附錄5
(1)能夠使用「微信開發者工具」來調試
(2)「js-sdk 沒有此SDK或暫不支持此SDK模擬」。
微信開發者工具不支持此方法的調用,用手機上的微信是沒問題的。
例如:updateAppMessageShareData