微信分享,终结版,及报错config:fail,Error: invalid signature"错误解决
程序员文章站
2022-03-26 18:22:53
...
/** * 获取access_token */ public static final String WX_SHARE_TOKEN = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET"; /** * TICKET */ public static final String WX_SHARE_TICKET = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=ACCESS_TOKEN&type=jsapi";
public void getWxShareParameter(String url) { try { url = URLDecoder.decode(url, "UTF-8"); } catch (UnsupportedEncodingException e) { log.error("微信分享获取url错误", e); } log.info("微信分享信息,url = " + url); //从缓存中取 RedisUtils redisUtils = SpringContextHolder.getBean("redisUtils"); String accessTokenString; //获取AccessToken String returnCode = redisUtils.getString("ACCESS_TOKEN"); if (StringUtils.isBlank(returnCode)) { String accessTokenUrl = WX_SHARE_TOKEN .replace("APPID", 公众号id) .replace("APPSECRET", 公众号secret); JSONObject accessToken = restTemplate.getForObject(accessTokenUrl, JSONObject.class); log.info("微信分享信息,accessToken = " + JSON.toJSONString(accessToken)); accessTokenString = accessToken.getString("access_token"); // 放入缓存,有效期两小时 redisUtils.set("ACCESS_TOKEN", accessTokenString, 7200); } else { accessTokenString = returnCode; } log.info("微信分享信息" + accessTokenString); if (StringUtils.isNotBlank(accessTokenString)) { String jsapiTicket; //从缓存中取 String ticket = redisUtils.getString("JSAPI_TICKET"); if (StringUtils.isBlank(ticket)) { String ticketUrl = WX_SHARE_TICKET .replace("ACCESS_TOKEN", accessTokenString); JSONObject ticketObject = restTemplate.getForObject(ticketUrl, JSONObject.class); log.info("微信分享信息" + JSON.toJSONString(ticketObject)); jsapiTicket = ticketObject.getString("ticket"); log.info("微信分享信息" + jsapiTicket); // 放入缓存,有效期两小时 redisUtils.set("JSAPI_TICKET", jsapiTicket, 7200); } else { jsapiTicket = ticket; } if (StringUtils.isNotBlank(jsapiTicket)) { Map<String, String> data = new HashMap<>(); String noncestr = getRandomString(16); String timestamp = Long.toString(System.currentTimeMillis() / 1000); //注意这里参数名必须全部小写,且必须有序 data.put("jsapi_ticket", jsapiTicket); data.put("noncestr", noncestr); data.put("timestamp", timestamp); data.put("url", url); String dataString = createLinkString(data); String resSign = DigestUtils.sha1Hex(dataString); data.put("paySign", resSign); data.put("appId", payProperties.getWeixinAppId()); return ResultBody.ok().data(data); } } }
//随机字符串生成 private String getRandomString(int length) { //length表示生成字符串的长度 String base = "abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"; StringBuilder sb = new StringBuilder(); for (int i = 0; i < length; i++) { int number = RandomUtils.nextInt(0, base.length()); sb.append(base.charAt(number)); } return sb.toString(); }
private String createLinkString(Map<String, String> params) { List<String> keys = new ArrayList<>(params.keySet()); Collections.sort(keys); String prestr = ""; for (int i = 0; i < keys.size(); i++) { String key = keys.get(i); String value = params.get(key); if (i == keys.size() - 1) {// 拼接时,不包括最后一个&字符 prestr = prestr + key + "=" + value; } else { prestr = prestr + key + "=" + value + "&"; } } return prestr; }
前端代码
前提首先要有一个公众号和已经备案好的域名,再公众号里面设置