1.获取code
用户点击登录按钮后,微信会弹出授权界面,用户同意授权后,
微信会返回一个临时的 code
。
这个code是一次性的,并且只会返回一次
2.通过 code
获取 openid
和 session_key
:
将获取到的 code
发送到微信的授权服务器接口(https://api.weixin.qq.com/sns/oauth2/access_token
),并且需要传递你的 app_id
和 app_secret
。
微信服务器会返回一个 access_token
(用于后续调用微信API验证)以及 openid
和 session_key
。其中,openid
是用户在你应用中的唯一标识,session_key
用于加解密用户的敏感数据。
3.校验access_token和opnid
使用 access_token
和 openid
你可以验证用户的身份,并获取一些用户信息,如昵称、头像等。
如果需要访问微信开放平台的其他API(如用户的社交信息),可以使用 access_token
。
4.注册或登录
如果是第一次登录,根据openid在自己的数据库创建一个用户
如果已经登陆过,则直接跳转登录状态
reg(){
let that = this;
console.log(that.formData);
if(!that.formData.phone){
uni.showToast({
title:'请绑定手机号',
icon:'fail'
});
return ;
}
if(!that.formData.nickname){
uni.showToast({
title:'请绑定昵称',
icon:'fail'
});
return ;
}
/* if(!that.formData.avatarUrl){
uni.showToast({
title:'请选择头像',
icon:'fail'
});
return ;
} */
wx.login().then(res=>{
//登录code
that.formData.weChatCode.code = res.code;
//创建账户
return that.createAccount();
}).then(res=>{
//上传头像
return that.saveAvatar();
}).then(res=>{
uni.showToast({
title:'注册成功!',
icon:'success'
})
let lastPage = '/pages/index/index';
let globalData = getApp().globalData;
if(globalData.lastPage){
lastPage = globalData.lastPage;
delete globalData.lastPage;
}
setTimeout(()=>{
uni.redirectTo({
url:lastPage
});
},2500);
});
},
createAccount(tokenCode){
let that = this;
return this.post(this.api.updateAccount,this.formData).then(res=>{
let data = res.data;
let globalData = getApp().globalData;
console.log('createAccount',res);
if(data.code==200){
globalData.token = res.header["token"];
wx.setStorageSync("userInfo", JSON.stringify(res.data.data))
that.userInfo = res.data.data;
return Promise.resolve(that.userInfo);
}else{
uni.showModal({
title:data.msg
});
return Promise.reject(res);
}
})
}
}
}
const login = function() {
return new Promise((resovle, fail) => {
//添加promis 异步转同步
wx.login({
success (res) {
if (res.code) {
http.post(api.login,{code:res.code})
.then((res)=>{
// 判断登录http状态吗,防止循环重试
if(res.statusCode == 200 && res.data.result) {
let globalData = getApp().globalData;
globalData.token = res.header["token"];
globalData.userInfo = res.data.data;
wx.setStorageSync("userInfo", JSON.stringify(res.data.data))
console.log("登录成功");
let pages = getCurrentPages();
let currentPage = pages[0].$page.fullPath;
resovle(res.data.data);
} else {
console.log('未注册!');
fail(-1);
}
},res=>{
console.log('网络故障,服务器故障!');
uni.showToast({
title:'网络故障,请重新打开小程序!'
});
fail(-2);
});
} else {
console.log('获取微信code失败!' + res.errMsg)
uni.showToast({
title:'网络故障,请重新打开小程序!'
});
fail(-3);
}
},fail(res) {
console.log(res)
}
});//wx.login
});//promise
}
微信登录凭证认证,并获取session_key
*
* @param
* @return
*/
@ApiOperation(value = "微信登录验证")
@ApiImplicitParams({
@ApiImplicitParam(name = "code", value = "登录凭证", required = true, paramType = "query"),
})
@PostMapping("/login")
@ResponseBody
public ResultData login(@RequestBody WeChatLoginDTO weChatLoginDTO, HttpServletRequest req, HttpServletResponse res) {
try {
Subject currentSubject = SecurityUtils.getSubject();
AccountEntity user = (AccountEntity) currentSubject.getPrincipal();
if (user != null) {
Arrays.stream(req.getCookies()).forEach(item->{res.addCookie(item);});
return ResultData.build().success(user);
}
log.debug("wechat token {}",weChatLoginDTO.getCode());
WeChatToken weChatToken = weChatService.getWeChatToken(weChatLoginDTO.getCode());
if (weChatToken == null) {
throw new BusinessException("未认证成功");
}
AccountEntity accountEntity = accountBiz.queryByWxOpenId(weChatToken.getOpenId());
if(accountEntity==null) {
return ResultData.build().error("未注册");
}
String localKey = weChatService.genLocalKey(weChatToken.getOpenId());
accountBiz.saveOrUpdate(accountEntity);
accountEntity.setLocalKey(localKey);
Subject subject = SecurityUtils.getSubject();
String sign = JWTUtil.sign(localKey,localKey);
log.debug("jwt sign {}",sign);
JWTToken token = new JWTToken(sign);
subject.login(token);
res.setHeader("token", sign);
if(accountEntity!=null) {
accountEntity.setWxOpenid(null);
SpringUtil.getApplicationContext().publishEvent(new LoginEvent(accountEntity));
return ResultData.build().success(accountEntity);
}else {
return ResultData.build().error("未注册");
}
}catch (Exception e) {
log.error("WX-shirologinerror:",e);
return ResultData.build().error("系统错误:"+e.getMessage());
// throw new BusinessException("shir 认证失败");
}
}
/**
* 用户信息更新
*
* @param
* @return
*/
@ApiOperation(value = "用户信息更新")
@ApiImplicitParams({
@ApiImplicitParam(name = "code", value = "登录凭证", required = true, paramType = "query"),
})
@PostMapping("/updateAccount")
@ResponseBody
public ResultData updateAccount(@RequestBody RegisterUserInfoDTO registerUserInfoDTO,HttpServletResponse httpResponse) {
log.debug("wechat token {}",registerUserInfoDTO.getWeChatCode().getCode());
AccountEntity accountEntity;
try {
accountEntity = weChatService.updateAccount(registerUserInfoDTO);
// WeChatToken weChatToken = new WeChatToken();
// weChatToken.setPhone(accountEntity.getPhone());
// weChatToken.setNickname(accountEntity.getNickname());
// weChatToken.setOpenId(accountEntity.getWxOpenid());
String sign = JWTUtil.sign(accountEntity.getLocalKey(),accountEntity.getLocalKey());
log.debug("jwt sign {}",sign);
JWTToken token = new JWTToken(sign);
Subject subject = SecurityUtils.getSubject();
subject.login(token);
httpResponse.setHeader("token", sign);
accountEntity.setWxOpenid("");
accountEntity.setWxSessionKey("");
return ResultData.build().success(accountEntity);
} catch (Exception e) {
log.error("WX-shirologinerror:"+e.getMessage());
e.printStackTrace();
return ResultData.build().error(e.getMessage());
}
}