微信小程序 获取openid和session_key
来源:互联网 发布:陕西省国家税务局网络 编辑:程序博客网 时间:2024/05/17 01:02
前言:最近自己一直再弄微信小程序,磕磕绊绊中也算把小程序的java接口开发走了一遍,这里总结一下自己学习过的知识,多积累才不容易忘记。这是第一篇的微信小程序java接口开发博客,会按照一个小程序从登录到请求接口返回数据,到最后的微信小程序支付的流程完成总结。
微信官方文档:小程序-开放接口-登录
一、小程序wx.login(OBJECT)
注:这里很不要脸的直接抄袭微信小程序API接口文档
1 wx.login(OBJECT)
调用接口获取登录凭证(code)进而换取用户登录态信息,包括用户的唯一标识(openid) 及本次登录的 会话密钥(session_key)。用户数据的加解密通讯需要依赖会话密钥完成。
(1)OBJECT参数说明:
(2)success返回参数说明:
(3)示例代码:
//app.jsApp({ onLaunch: function() { wx.login({ success: function(res) { if (res.code) { //发起网络请求 wx.request({ url: 'https://test.com/onLogin', data: { code: res.code } }) } else { console.log('获取用户登录态失败!' + res.errMsg) } } }); }})
二、java接口
1 code 换取 openid和session_key
这是一个 HTTPS 接口,开发者服务器使用登录凭证 code 获取 session_key 和 openid。其中 session_key 是对用户数据进行加密签名的密钥。
(1)接口地址:
https://api.weixin.qq.com/sns/jscode2session?appid=APPID&secret=SECRET&js_code=JSCODE&grant_type=authorization_code
(2)请求参数:
(3)返回参数:
(4)返回说明:
//正常返回的JSON数据包{ "openid": "OPENID", "session_key": "SESSIONKEY"}//错误时返回JSON数据包(示例为Code无效){ "errcode": 40029, "errmsg": "invalid code"}
2 java接口
(1)Controller接口类
/** * 获取openId * 开发人员:wangql * 开发时间:2017-6-14 * @param params * @param request * @param response */ @ResponseBody @RequestMapping(value="/getOpenId",method = RequestMethod.POST) public Map<String, Object> getOpenId(HttpServletRequest request,HttpServletResponse response){ Map<String, Object> map = new HashMap<String, Object>(); String status = "1"; String msg = "ok"; String WX_URL = "https://api.weixin.qq.com/sns/jscode2session?appid=APPID&secret=SECRET&js_code=JSCODE&grant_type=authorization_code"; try { String code = request.getParameter("code"); if(StringUtils.isBlank(code)){ status = "0";//失败状态 msg = "code为空"; }else { String requestUrl = WX_URL.replace("APPID", WeixinConstants.APPID). replace("SECRET", WeixinConstants.APP_SECRECT).replace("JSCODE", code). replace("authorization_code", WeixinConstants.AUTHORIZATION_CODE); logger.info(requestUrl); // 发起GET请求获取凭证 JSONObject jsonObject = CommonUtil.httpsRequest(requestUrl, "GET", null); if (jsonObject != null) { try { map.put("openid", jsonObject.getString("openid")); map.put("session_key", jsonObject.getString("session_key")); } catch (JSONException e) { // 获取token失败 status = "0"; msg = "code无效"; } }else { status = "0"; msg = "code无效"; } } map.put("status", status); map.put("msg", msg); } catch (Exception e) { logger.error(e.getMessage(),e); return AnalyzeMoblieData.errorResponse(); } return map; }
(2)http请求工具类
import java.io.BufferedReader;import java.io.IOException;import java.io.InputStream;import java.io.InputStreamReader;import java.io.OutputStream;import java.io.UnsupportedEncodingException;import java.net.ConnectException;import java.net.URL;import java.util.Iterator;import java.util.Map;import javax.net.ssl.HttpsURLConnection;import javax.net.ssl.SSLContext;import javax.net.ssl.SSLSocketFactory;import javax.net.ssl.TrustManager;import org.apache.commons.httpclient.HttpClient;import org.apache.commons.httpclient.HttpMethod;import org.apache.commons.httpclient.NameValuePair;import org.apache.commons.httpclient.methods.PostMethod;import org.apache.commons.httpclient.params.HttpMethodParams;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import net.sf.json.JSONException;import net.sf.json.JSONObject;/** * 类名: CommonUtil.java</br> * 描述: http请求工具类</br> * 开发人员:wangql</br> * 创建时间: 2017-6-12</br> */public class CommonUtil { private static Logger log = LoggerFactory.getLogger(CommonUtil.class); /** * 发送https请求 * @param requestUrl 请求地址 * @param requestMethod 请求方式(GET、POST) * @param outputStr 提交的数据 * @return JSONObject(通过JSONObject.get(key)的方式获取json对象的属性值) */ public static JSONObject httpsRequest(String requestUrl, String requestMethod, String outputStr) { JSONObject jsonObject = null; 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 conn = (HttpsURLConnection) url.openConnection(); conn.setSSLSocketFactory(ssf); conn.setDoOutput(true); conn.setDoInput(true); conn.setUseCaches(false); // 设置请求方式(GET/POST) conn.setRequestMethod(requestMethod); // 当outputStr不为null时向输出流写数据 if (null != outputStr) { OutputStream outputStream = conn.getOutputStream(); // 注意编码格式 outputStream.write(outputStr.getBytes("UTF-8")); outputStream.close(); } // 从输入流读取返回内容 InputStream inputStream = conn.getInputStream(); InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "utf-8"); BufferedReader bufferedReader = new BufferedReader(inputStreamReader); String str = null; StringBuffer buffer = new StringBuffer(); while ((str = bufferedReader.readLine()) != null) { buffer.append(str); } // 释放资源 bufferedReader.close(); inputStreamReader.close(); inputStream.close(); inputStream = null; conn.disconnect(); jsonObject = JSONObject.fromObject(buffer.toString()); } catch (ConnectException ce) { log.error("连接超时:{}", ce); } catch (Exception e) { log.error("https请求异常:{}", e); } return jsonObject; }}
(3)信任管理器类
import java.security.cert.CertificateException;import java.security.cert.X509Certificate;import javax.net.ssl.X509TrustManager;/** * 类名: MyX509TrustManager.java</br> * 描述: 信任管理器</br> * 开发人员:wangql</br> * 创建时间: 2017-6-12</br> */public class MyX509TrustManager implements X509TrustManager { // 检查客户端证书 public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { } // 检查服务器端证书 public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { } // 返回受信任的X509证书数组 public X509Certificate[] getAcceptedIssuers() { return null; }}
3 登录态维护
通过 wx.login() 获取到用户登录态之后,需要维护登录态。开发者要注意不应该直接把 session_key、openid 等字段作为用户的标识或者 session 的标识,而应该自己派发一个 session 登录态(请参考登录时序图)。对于开发者自己生成的 session,应该保证其安全性且不应该设置较长的过期时间。session 派发到小程序客户端之后,可将其存储在 storage ,用于后续通信使用。
总结:其实小程序获取openid和session_key原理非常简单,就是按照指定地址指定参数发送http的get请求。我们只要按照接口文档先使用wx.login获取js_code,然后再向https://api.weixin.qq.com/sns/jscode2session地址发送带appid、secret、js_code和grant_type的参数即可。关键是java如何发送安全的http请求,这里是关键的地方。
参考文章
微信小程序API 登录
- 微信小程序 获取session_key和openid
- 微信小程序 获取session_key和openid
- 微信小程序 获取openid和session_key
- 微信小程序 获取session_key和openid
- 微信小程序获取openid和session_key
- 微信小程序 code 拿到session_key 和openid
- 【微信小程序】获取openid
- 微信小程序获取openid
- 微信小程序获取获取openid
- 获得session_key和openId(加解密、签名系列)
- 微信小程序获取用户openId
- 微信小程序获取用户openid
- 微信小程序 获取openid客户端
- 微信小程序获取用户openid
- 微信小程序获取用户OpenId
- 微信小程序获取openid服务器端代码
- 微信小程序开发(四)获取用户openid
- 微信小程序 获取openid 存入数据库 C#
- 设备像素比devicePixelRatio:
- Unity3D 渲染路径
- hihoCoder1049—后序遍历(递归)
- BitMap算法用于磁盘文件排序的原理与实现
- thrift使用总结
- 微信小程序 获取openid和session_key
- Virtual Box配置CentOS7网络(图文教程)
- linux 查看磁盘空间大小
- JavaScript 将 JSON 字符串转换成 JSON 对象的数组
- 根据手机屏幕来调节图片的高度
- 转shared_ptr的小文 ,shared_ptr 赋值为a, 再赋值为b, a 的引用会减1, b 的引用加1
- 23中设计模式之组合模式
- Activiti工作流引擎的使用
- Git之diff和status