开发小程序需要在公众平台注册一个小程序账号,然后获取到小程序的AppID和AppSecret。就可以进行第三方登陆授权开发。

一、需求

拥有第三方微信登录功能,并获取到用户信息。

二、开发流程

小程序:

1. 微信小程序通过wx.login
API进行登录获取code。由于AppID和AppSecret不能泄露给用户,根据code获取openid需要在服务端完成,所以需要将code发送给服务端

(服务端),并且带上授权临时票据code参数;

2.
服务端通过code和appid、APPSecret获取到openid和SessionKey。服务端需要返回自定义登录态给前端,不能返回SessionKey

3. 前端保存自定义登录态,获取用户信息时携带自定义登录态给后端。



获取Token的流程

三、开发使用的技术及工具

1、.后端采用IDEA2017 进行开发

2、前端使用微信开发者工具V1.02进行开发

3、使用fastJson对json数据进行处理

四、具体实现步骤 <>

1.前端(小程序)

目录结构如下:



1)自定义的全局变量
globalData: {     userInfo: null,     sessionkey:null   }
自定义userInfo用于存储用户信息

sessionKey用于存储服务端发回给客户端的sessionkey

2)index加载时进行登录

用户登录后,服务端会返回一个sessionkey给客户端保存,如果为空,说明没有登录过,需要调用wx.login进行登录。

调用wx.login后,微信会返回一个code给小程序,小程序需要通过这个code发送给自身的服务端来获取sessionkey和openid信息。
onLoad: function() {     var serverUrl = app.serverUrl;     //
加载时,检查当前用户信息是否登录     if (app.globalData.sessionkey != null) { // 已经登录了       //
是否授权       wx.getSetting({         success: function(res) {           if
(res.authSetting['scope.userInfo']) {             // 已经授权,可以直接调用 getUserInfo
获取头像昵称             wx.getUserInfo({               success: function(res) {
                app.globalData.userInfo = JSON.parse(res.rawData);
              }             })           } else {             // 还没有授权,则需要授权
            wx.redirectTo({               url: '../authorization/authorization'
            })           }         }       })     } else { // 还没有登录       //
提示用户登录授权       wx.login({         success: res => {           // 发送 res.code
到后台换取 openId, sessionKey, unionId           if (res.code) {             //
发送请求,服务端能获取到openid和unionid,之前登录过则可以获取到之前的用户信息。             wx.request({
              url: serverUrl + '/miniprogram/login/' + res.code, //请求路径
              method: "GET",               success: function(res) {
                app.globalData.sessionkey = res.data;                 // 进入授权
                wx.redirectTo({                   url:
'../authorization/authorization'                 })               }            
})           }         }       })     } },
登录成功后,重定向到授权页面

3)授权页面authorization.wxml
<view class='tag-title'>   <image mode="widthFix" style=' width:
200rpx;height: 200rpx;margin-top:150rpx' src="/images/logo.jpg"></image>
</view> <view wx:if="{{canIUse}}">   <view
style='text-align:center;margin-top:50rpx'>     允许微信授权后,可体验更多功能</view>   <view>
    <button open-type='getUserInfo' bindgetuserinfo="bindGetUserInfo"
>授权登录</button>     <button bindtap='navigateBack'>返回首页</button>   </view>
</view> <view wx:else style='text-align:center;margin-top:50rpx'>  
您的微信版本过低,请升级后再次体验</view>

Button的open-type为getUserInfo时,点击后会调用bindgetuserinfo属性配置的函数,同时带上用户基本信息(不包括Openid等)

4)用户信息发送给后端
// 授权登录按钮   bindGetUserInfo: function(e) {     let that = this;     var
serverUrl = app.serverUrl;     console.log(e.detail.userInfo)     if
(e.detail.userInfo) {  // 成功获取到信息       app.globalData.userInfo =
e.detail.userInfo       // 这里可以将用户信息发送给后台       // 获取到sessionkey       if
(app.globalData.sessionkey!=null){         wx.request({           url:
serverUrl + '/miniprogram/userinfo', //请求路径,           method: "GET",          
data: {             // openid: this.openid,             // unionid:
this.unionid,             key: app.globalData.sessionkey,             nickname:
app.globalData.userInfo.nickName, //获取昵称             gender:
app.globalData.userInfo.gender, //获取性别             province:
app.globalData.userInfo.province, //获取省份             city:
app.globalData.userInfo.city, //获取城市             country:
app.globalData.userInfo.country, //获取国家             avatarUrl:
app.globalData.userInfo.avatarUrl, //这些是用户的基本信息             language:
app.globalData.userInfo.language           },           success: function (res)
{             if (res.data.code == 0) {  // 请求成功               debugger
              app.globalData.userInfo = res.data.data; // 以数据库中返回的数据为准
              // 获取用户信息成功               wx.switchTab({                 url:
'../mine/mine'               })             }           }         })      
}else{         this.showZanTopTips('错误:SessionKey为null');       }     } else {
      this.showZanTopTips('您拒绝了微信授权');     }   }, }));
获取用户信息成功后,页面跳转到mine中显示用户详情信息

5)用户详情页mine.wxml
<view class="container more">   <view class="userinfo">     <image
bindtap="bindViewTap" class="userinfo-avatar" src="{{userInfo.avatarUrl}}"
background-size="cover"></image>     <text
class="userinfo-nickname">{{userInfo.nickName}}</text>           <text
class="userinfo-nickname">性别:{{userInfo.gender === 1 ? '男':'女'}}</text>   
       <text class="userinfo-nickname">城市:{{userInfo.city}}</text>          
<text class="userinfo-nickname">省份:{{userInfo.province}}</text>           <text
class="userinfo-nickname">国家:{{userInfo.country}}</text>           <text
class="userinfo-nickname">使用语言:{{userInfo.language}}</text>   </view> </view>
2.服务端(Java)


服务端需要做的是:接受小程序前端发送的请求,根据发送过来的code,以及服务端保存的AppId和APPSecret等向微信服务端发送请求,获取到sessionkey和openid,然后将二者关联起来保存到session存储器中(Redis),返回给前端key值。


接受小程序发送过来的key和用户基本信息,根据key从redis中获取openid,然后对数据库进行查询,若存在数据则封装后返回给前端,若无信息则向数据库中插入数据并返回给前端。

1).配置文件新增小程序相关配置

wechar.miniprogram.appid =

wechar.miniprogram.appsecret =

2)获取openid以及Sessionkey
@ResponseBody     @RequestMapping("/login/{code}")     public String
login(@PathVariable("code") String code) {         String url =
"https://api.weixin.qq.com/sns/jscode2session?" +                 "appid=" +
                env.getProperty("wechar.miniprogram.appid") +                
"&secret=" +                 env.getProperty("wechar.miniprogram.appsecret") +
                "&js_code=" +                 code +                
"&grant_type=authorization_code";         JSONObject object =
HttpClientUtils.httpGet(url);         // 请求,获取openid或unionid         //
从数据库中查询是否存储         // 成功获取         String unionid = (String)
object.get("unionid");         String openid = (String)
object.get("openid");//用户唯一标识         // 会话密钥session_key
是对用户数据进行加密签名的密钥。为了应用自身的数据安全,开发者服务器不应该把会话密钥下发到小程序,也不应该对外提供这个密钥。         String
session_key = (String) object.get("session_key");         String key =
"wecharminiprogramkey-" + UUID.randomUUID().toString().replaceAll("-", "");
        RedisPoolUtil.setEx(key, openid + "---" + session_key, 9600);        
return key; }
3).获取用户信息:

小程序能够获取用户基本信息,但是不包括openid等信息,仅有基本的昵称等信息,需要通过后端传输的key作为标识发送到前端,然后找到对应的openid来获取。
@ResponseBody @RequestMapping(value = "/userinfo", method = RequestMethod.GET)
// 获取用户信息 public Result getOpenId(String key, MiniProgramBaseUserInfo
miniProgramBaseUserInfo) {         MiniProgramBaseUserInfo result = null;
        String value = RedisPoolUtil.get(key);         if (value != null) {
            String values[] = value.split("---");             String openid =
values[0];             // 从数据库中查询是否存储(根据openid查询)             result = null; //
TODO: 这里是查数据库操作             if (result == null){ // 数据库中没有数据                 //
TODO: 向数据库中执行插入操作                 // insert  weCharUserInfo                
result = miniProgramBaseUserInfo;             }             return
Result.success(result);         return Result.error(SESSION_KEY_OVER_TIME); //
SessionKey失效     }
 

友情链接
KaDraw流程图
API参考文档
OK工具箱
云服务器优惠
阿里云优惠券
腾讯云优惠券
华为云优惠券
站点信息
问题反馈
邮箱:[email protected]
QQ群:637538335
关注微信