首页 > 编程 > Java > 正文

Java微信分享接口开发详解

2019-11-26 09:03:33
字体:
来源:转载
供稿:网友

本文实例为大家分享了Java微信分享接口开发的具体代码,供大家参考,具体内容如下

Java微信分享,步骤是

1、根据当前的url,获取signature,nonceStr,timestamp 和appId。
2、通过signature,nonceStr,timestamp 和appId来配置微信 wx.config。
3、通过wx.ready实现微信分享功能。

1、html端

引入微信JS-SDK.

<script src="http://res.wx.qq.com/open/js/jweixin-1.0.0.js"></script>
//分享核心js代码$(document).ready(function () {  //通过ajax,在页面加载的时候获取微信分享接口signature,nonceStr,timestamp 和appId  $.ajax({    type: "post",    url: "/weixin/share",    dataType: "json",    data:"url="+window.location.href,    success: function (data) {      wx.config({        debug: false,        appId: data.appId,        timestamp: data.timestamp,        nonceStr: data.nonceStr,        signature: data.signature,        jsApiList: ['onMenuShareAppMessage', 'onMenuShareTimeline', 'hideAllNonBaseMenuItem', 'showMenuItems']        // 功能列表,我们要使用JS-SDK的什么功能      });      wx.ready(function () {        // 获取“分享给朋友”按钮点击状态及自定义分享内容接口        wx.onMenuShareAppMessage({          title: "分享自定义标题", // 分享标题          desc: "分享自定义描述", // 分享描述          link: "http://localhost/weixin/share?openId=1",//分享点击之后的链接          imgUrl:'/images/photo/1.jpg', // 分享图标          type: 'link', // 分享类型,music、video或link,不填默认为link          success: function () {            //成功之后的回调          }        });        wx.hideAllNonBaseMenuItem();        wx.showMenuItems({          menuList: ['menuItem:share:appMessage', 'menuItem:share:timeline'] // 要隐藏的菜单项,只能隐藏“传播类”和“保护类”按钮,所有menu项见附录3        });        wx.onMenuShareTimeline({          title: "分享自定义标题", // 分享标题          desc: "分享自定义描述", // 分享描述          link: "http://localhost/weixin/share?openId=1",//分享点击之后的链接          imgUrl:'/images/photo/1.jpg', // 分享图标          type: 'link', // 分享类型,music、video或link,不填默认为link          success: function () {            //成功之后的回调          }          cancel: function () {            // 用户取消分享后执行的回调函数          }        });      });      wx.error(function (res) {        //打印错误消息。及把 debug:false,设置为debug:ture就可以直接在网页上看到弹出的错误提示      });    }  })});

2、Java代码,获取 signature,nonceStr,timestamp 和appId

@RequestMapping(value = "/share", method = RequestMethod.POST)  @ResponseBody  public Map<String, Object> share(HttpServletRequest request) {    String urlTemp = "http://" + request.getServerName() + request.getContextPath();    String urlpath = "http://" + request.getServerName();    String appUrl = request.getParameter("url");    if (request.getParameter("code") != null) {      appUrl += "&code=" + request.getParameter("code");    }    if (request.getParameter("state") != null) {      appUrl += "&state=" + request.getParameter("state");    }    return WxConfigUtil.getSignature(appUrl, ContentValues.APPID, ContentValues.SECRET, urlTemp, urlpath);  }

工具类我就把整个贴上来了,其中有些方法是没有用到的。

getSignature()整个方法是微信分享中的核心方法,用来获取signature,nonceStr,timestamp 和appId这几个核心参数。

package com.blog.common.util;import com.alibaba.fastjson.JSONObject;import com.blog.common.model.Token;import javax.net.ssl.HttpsURLConnection;import javax.net.ssl.SSLContext;import javax.net.ssl.SSLSocketFactory;import javax.net.ssl.TrustManager;import java.io.BufferedReader;import java.io.InputStream;import java.io.InputStreamReader;import java.io.OutputStream;import java.net.ConnectException;import java.net.URL;import java.security.MessageDigest;import java.security.NoSuchAlgorithmException;import java.util.Arrays;import java.util.HashMap;import java.util.Map;/** * 公众平台通用接口工具类 * * @author james * @date 2015-02-27 */public class WxConfigUtil {  // 获取access_token的接口地址(GET) 限2000(次/天)  public final static String access_token_url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET";  // 获取jsapi_ticket的接口地址(GET) 限2000(次/天)  public final static String jsapi_ticket_url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=ACCESS_TOKEN&type=jsapi";  // 缓存添加的时间  public static String cacheAddTime = null;  // token,ticket缓存  public static Map<String, Token> TOKEN_TICKET_CACHE = new HashMap<String, Token>();  // token对应的key  private static final String TOKEN = "token";  // ticket对应的key  private static final String TICKET = "ticket";  /**   * 外部获取签名入口类   *   * @param appUrl  应用的url   * @return   */  public static Map<String, Object> getSignature(String appUrl, String appId, String secret, String url, String urlpath) {    // 生成签名的随机串    String noncestr = RandomUtil.getStringRandom(4);    if (appUrl == null || "".equals(appUrl)) {      return null;    }    String signature = null;    Token accessTocken = getToken(appId, secret, System.currentTimeMillis() / 1000);    Token accessTicket = getTicket(accessTocken.getToken(), System.currentTimeMillis() / 1000);    signature = signature(accessTicket.getTicket(), cacheAddTime, noncestr, appUrl);    System.out.println("-=-=-=-=-=-=-=-=appUrl:" + appUrl);    System.out.println("-=-=-=-=-=-=-=-=token:" + accessTocken.getToken());    System.out.println("-=-=-=-=-=-=-=-=ticket:" + accessTicket.getTicket());    System.out.println("-=-=-=-=-=-=-=-=signature:" + signature);    System.out.println("-=-=-=-=-=-=-=-=timestamp:" + cacheAddTime);    Map<String, Object> map = new HashMap<>();    map.put("appId", appId);    map.put("timestamp", cacheAddTime);    map.put("nonceStr", noncestr);    map.put("appUrl", appUrl);    map.put("signature", signature);    map.put("url", url);    map.put("urlpath", urlpath);    return map;  }  /**   * 获得Token   *   * @return   */  public static String getToken(String appId, String secret) {    Token accessTocken = getToken(appId, secret, System.currentTimeMillis() / 1000);    return accessTocken.getToken();  }  /**   * 签名   *   * @param timestamp   * @return   */  private static String signature(String jsapi_ticket, String timestamp, String noncestr, String url) {    jsapi_ticket = "jsapi_ticket=" + jsapi_ticket;    timestamp = "timestamp=" + timestamp;    noncestr = "noncestr=" + noncestr;    url = "url=" + url;    String[] arr = new String[]{jsapi_ticket, noncestr, timestamp, url};    // 将token、timestamp、nonce,url参数进行字典序排序    Arrays.sort(arr);    StringBuilder content = new StringBuilder();    for (int i = 0; i < arr.length; i++) {      content.append(arr[i]);      if (i != arr.length - 1) {        content.append("&");      }    }    MessageDigest md = null;    String tmpStr = null;    try {      md = MessageDigest.getInstance("SHA-1");      // 将三个参数字符串拼接成一个字符串进行sha1加密      byte[] digest = md.digest(content.toString().getBytes());      tmpStr = byteToStr(digest);    } catch (NoSuchAlgorithmException e) {      e.printStackTrace();    }    content = null;    return tmpStr;  }  /**   * 获取access_token   *   * @param appid   凭证   * @param appsecret 密钥   * @return   */  public static Token getToken(String appid, String appsecret, long currentTime) {    Token tockenTicketCache = getTokenTicket(TOKEN);    Token Token = null;    if (tockenTicketCache != null && (currentTime - tockenTicketCache.getAddTime() <= tockenTicketCache.getExpiresIn())) {// 缓存存在并且没过期      System.out.println("==========缓存中token已获取时长为:" + (currentTime - tockenTicketCache.getAddTime()) + "毫秒,可以重新使用");      return tockenTicketCache;    }    System.out.println("==========缓存中token不存在或已过期===============");    String requestUrl = access_token_url.replace("APPID", appid).replace("APPSECRET", appsecret);    JSONObject jsonObject = httpRequest(requestUrl, "GET", null);    // 如果请求成功    if (null != jsonObject) {      Token = new Token();      Token.setToken(jsonObject.getString("access_token"));      Token.setExpiresIn(jsonObject.getIntValue("expires_in") / 2);// 正常过期时间是7200秒,此处设置3600秒读取一次      System.out.println("==========tocket缓存过期时间为:" + Token.getExpiresIn() + "毫秒");      Token.setAddTime(currentTime);      updateToken(TOKEN, Token);    }    return Token;  }  /**   * 获取ticket   *   * @param token   * @return   */  private static Token getTicket(String token, long currentTime) {    Token tockenTicketCache = getTokenTicket(TICKET);    Token Token = null;    if (tockenTicketCache != null && (currentTime - tockenTicketCache.getAddTime() <= tockenTicketCache.getExpiresIn())) {// 缓存中有ticket      System.out.println("==========缓存中ticket已获取时长为:" + (currentTime - tockenTicketCache.getAddTime()) + "毫秒,可以重新使用");      return tockenTicketCache;    }    System.out.println("==========缓存中ticket不存在或已过期===============");    String requestUrl = jsapi_ticket_url.replace("ACCESS_TOKEN", token);    JSONObject jsonObject = httpRequest(requestUrl, "GET", null);    // 如果请求成功    if (null != jsonObject) {      Token = new Token();      Token.setTicket(jsonObject.getString("ticket"));      Token.setExpiresIn(jsonObject.getIntValue("expires_in") / 2);// 正常过期时间是7200秒,此处设置3600秒读取一次      System.out.println("==========ticket缓存过期时间为:" + Token.getExpiresIn() + "毫秒");      Token.setAddTime(currentTime);      updateToken(TICKET, Token);    }    return Token;  }  /**   * 发起https请求并获取结果   *   * @param requestUrl  请求地址   * @param requestMethod 请求方式(GET、POST)   * @param outputStr   提交的数据   * @return JSONObject(通过JSONObject.get(key)的方式获取json对象的属性值)   */  private static JSONObject httpRequest(String requestUrl, String requestMethod, String outputStr) {    JSONObject jsonObject = null;    StringBuffer buffer = new StringBuffer();    try {      // 创建SSLContext对象,并使用我们指定的信任管理器初始化      TrustManager[] tm = {new MyX509TrustManager()};      SSLContext sslContext = SSLContext.getInstance("SSL", "SunJSSE");      sslContext.init(null, tm, new java.security.SecureRandom());      // 从上述SSLContext对象中得到SSLSocketFactory对象      SSLSocketFactory ssf = sslContext.getSocketFactory();      URL url = new URL(requestUrl);      HttpsURLConnection httpUrlConn = (HttpsURLConnection) url.openConnection();      httpUrlConn.setSSLSocketFactory(ssf);      httpUrlConn.setDoOutput(true);      httpUrlConn.setDoInput(true);      httpUrlConn.setUseCaches(false);      // 设置请求方式(GET/POST)      httpUrlConn.setRequestMethod(requestMethod);      if ("GET".equalsIgnoreCase(requestMethod))        httpUrlConn.connect();      // 当有数据需要提交时      if (null != outputStr) {        OutputStream outputStream = httpUrlConn.getOutputStream();        // 注意编码格式,防止中文乱码        outputStream.write(outputStr.getBytes("UTF-8"));        outputStream.close();      }      // 将返回的输入流转换成字符串      InputStream inputStream = httpUrlConn.getInputStream();      InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "utf-8");      BufferedReader bufferedReader = new BufferedReader(inputStreamReader);      String str = null;      while ((str = bufferedReader.readLine()) != null) {        buffer.append(str);      }      bufferedReader.close();      inputStreamReader.close();      // 释放资源      inputStream.close();      inputStream = null;      httpUrlConn.disconnect();      jsonObject = JSONObject.parseObject(buffer.toString());      // jsonObject = JSONObject.fromObject(buffer.toString());    } catch (ConnectException ce) {      System.out.println("Weixin server connection timed out.");    } catch (Exception e) {      System.out.println("https request error:{}" + e.getMessage());    }    return jsonObject;  }  /**   * 将字节数组转换为十六进制字符串   *   * @param byteArray   * @return   */  private static String byteToStr(byte[] byteArray) {    String strDigest = "";    for (int i = 0; i < byteArray.length; i++) {      strDigest += byteToHexStr(byteArray[i]);    }    return strDigest;  }  /**   * 将字节转换为十六进制字符串   *   * @param mByte   * @return   */  private static String byteToHexStr(byte mByte) {    char[] Digit = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'};    char[] tempArr = new char[2];    tempArr[0] = Digit[(mByte >>> 4) & 0X0F];    tempArr[1] = Digit[mByte & 0X0F];    String s = new String(tempArr);    return s;  }  /**   * 从缓存中读取token或者ticket   *   * @return   */  private static Token getTokenTicket(String key) {    if (TOKEN_TICKET_CACHE != null && TOKEN_TICKET_CACHE.get(key) != null) {      System.out.println("==========从缓存中获取到了" + key + "成功===============");      return TOKEN_TICKET_CACHE.get(key);    }    return null;  }  /**   * 更新缓存中token或者ticket   *   * @return   */  private static void updateToken(String key, Token accessTocken) {    if (TOKEN_TICKET_CACHE != null && TOKEN_TICKET_CACHE.get(key) != null) {      TOKEN_TICKET_CACHE.remove(key);      System.out.println("==========从缓存中删除" + key + "成功===============");    }    TOKEN_TICKET_CACHE.put(key, accessTocken);    cacheAddTime = String.valueOf(accessTocken.getAddTime());// 更新缓存修改的时间    System.out.println("==========更新缓存中" + key + "成功===============");  }}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持武林网。

发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表