【2023最新】微信小程序中微信授权登录功能和退出登录功能实现讲解

这篇具有很好参考价值的文章主要介绍了【2023最新】微信小程序中微信授权登录功能和退出登录功能实现讲解。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一、讲解视频

教学视频地址: 视频地址

二、小程序前端代码

// pages/profile/profile.js
import api from "../../utils/api";
import { myRequest } from "../../utils/request";
import Notify from "@vant/weapp/notify/notify";
import Cache from "../../utils/cache";
import Tool from "../../utils/tool";


Page({

    /**
     * 页面的初始数据
     */
    data: {
        isLogin: false,
        userInfo: {
            username: "还未登录,请先登录!",
            headPic: api.BASE_URL + "/photo/view?filename=common/mine_normal.jpg"
        },
        basePhotoUrl: api.BASE_URL + "/photo/view?filename=",
        editUser: {},
        profileDialogVisible: false
    },

    /**
     * 生命周期函数--监听页面加载
     */
    onLoad: function (options) {
       this.validateLoginState();
    },

    /**
     * 生命周期函数--监听页面初次渲染完成
     */
    onReady: function () {

    },

    /**
     * 生命周期函数--监听页面显示
     */
    onShow: function () {

    },

    /**
     * 生命周期函数--监听页面隐藏
     */
    onHide: function () {

    },

    /**
     * 生命周期函数--监听页面卸载
     */
    onUnload: function () {

    },

    /**
     * 页面相关事件处理函数--监听用户下拉动作
     */
    onPullDownRefresh: function () {
        this.validateLoginState();
    },

    /**
     * 页面上拉触底事件的处理函数
     */
    onReachBottom: function () {

    },

    /**
     * 用户点击右上角分享
     */
    onShareAppMessage: function () {

    },

    // 预览图片
    previewHead: function () {
        let userInfo = this.data.userInfo;
        let basePhotoUrl = this.data.basePhotoUrl;
        wx.previewImage({
             current: userInfo.headPic === userInfo.wxHeadPic ? userInfo.wxHeadPic : basePhotoUrl + userInfo.headPic,
             urls: [userInfo.headPic === userInfo.wxHeadPic ? userInfo.wxHeadPic : basePhotoUrl + userInfo.headPic]
        })
    },
    // 验证登录状态
    validateLoginState: async function() {
        wx.showLoading({
            title: "获取登录信息...",
            mask: true
        })
        const loginUser = Cache.getCache(getApp().globalData.SESSION_KEY_LOGIN_USER);
        if(Tool.isEmpty(loginUser)) {
            wx.hideLoading();
            return;
        }
        const res = await myRequest({
            url: api.BASE_URL + "/app/user/get_login_user",
            method: "POST",
            data: {
                token: loginUser
            }
        });
        if(res.data.code === 0) {
            this.setData({
                userInfo: res.data.data,
                isLogin: true,
                editUser: res.data.data
            })
        }
        wx.hideLoading();
        wx.stopPullDownRefresh();
    },
    // 登录操作
    getLoginUser: function() {
        wx.showLoading({
            title: "正在登录...",
            mask: true
        })
        wx.getUserProfile({
            desc: "获取用户相关信息",
            success: res => {
                if(res.errMsg === "getUserProfile:ok") {
                    let username = res.userInfo.nickName;
                    let headPic = res.userInfo.avatarUrl;
                    wx.login({
                        success: async res => {
                            if (res.errMsg === "login:ok") {
                                // 调用后端接口,验证用户数据
                                const response = await myRequest({
                                    url: api.BASE_URL + "/app/user/wx_login",
                                    method: "POST",
                                    data: {
                                        wxHeadPic: headPic,
                                        wxUsername: username,
                                        code: res.code
                                    }
                                });
                                if(response.data.code === 0) {
                                    Notify({ type: "success", message: response.data.msg, duration: 1000 });
                                    Cache.setCache(getApp().globalData.SESSION_KEY_LOGIN_USER, response.data.data.token, 3600);
                                    this.setData({
                                        userInfo: response.data.data,
                                        editUser: response.data.data,
                                        isLogin: true
                                    });
                                } else {
                                    Notify({ type: "danger", message: response.data.msg, duration: 2000 });
                                }
                            } else {
                                wx.showToast({
                                    icon: "error",
                                    title: "登录失败"
                                });
                            }
                            wx.hideLoading();
                        },
                        fail: res => {
                            wx.showToast({
                                icon: "error",
                                title: "登录失败"
                            });
                            wx.hideLoading();
                        }
                    })
                } else {
                    wx.showToast({
                        icon: "error",
                        title: "获取用户失败"
                    });
                    wx.hideLoading();
                }
            },
            fail: res => {
                wx.showToast({
                    icon: "error",
                    title: "获取用户失败"
                });
                wx.hideLoading();
            }
        })
    },    
    // 登录验证
    authUser: function() {
        const loginUser = Cache.getCache(getApp().globalData.SESSION_KEY_LOGIN_USER);
        if(Tool.isEmpty(loginUser)) {
            Notify({ type: "danger", message: "请先登录!", duration: 2000 });
            return true;
        } else {
            return false;
        }
    },
    // 退出登录
    logout: async function() {
        const loginUser = Cache.getCache(getApp().globalData.SESSION_KEY_LOGIN_USER);
        const res = await myRequest({
            url: api.BASE_URL + "/app/user/logout",
            method: "POST",
            data: {
                token: loginUser
            }
        });
        if(res.data.code === 0) {
            Notify({ type: "success", message: res.data.msg, duration: 1000 });
        }
        Cache.removeCache(getApp().globalData.SESSION_KEY_LOGIN_USER);    
        this.setData({isLogin: false, userInfo: {
            username: "还未登录,请先登录!",
            headPic: api.BASE_URL + "/photo/view?filename=common/mine_normal.jpg"
        }});
    },
  
 
  
})

三、后端Java代码

<!--引入http连接依赖-->
<dependency>
  <groupId>org.apache.httpcomponents</groupId>
  <artifactId>httpclient</artifactId>
  <version>4.5.3</version>
</dependency>
package com.yjq.programmer.service.impl;

import com.alibaba.fastjson.JSON;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.yjq.programmer.bean.CodeMsg;
import com.yjq.programmer.dao.UserMapper;
import com.yjq.programmer.domain.User;
import com.yjq.programmer.domain.UserExample;
import com.yjq.programmer.dto.LoginDTO;
import com.yjq.programmer.dto.PageDTO;
import com.yjq.programmer.dto.ResponseDTO;
import com.yjq.programmer.dto.UserDTO;
import com.yjq.programmer.enums.RoleEnum;
import com.yjq.programmer.service.IUserService;
import com.yjq.programmer.utils.CommonUtil;
import com.yjq.programmer.utils.CopyUtil;
import com.yjq.programmer.utils.UuidUtil;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @author 杨杨吖
 * @QQ 823208782
 * @WX yjqi12345678
 * @create 2023-09-25 17:08
 */
@Service
@Transactional
public class UserServiceImpl implements IUserService {

    @Resource
    private UserMapper userMapper;

    @Resource
    private StringRedisTemplate stringRedisTemplate;

    private static final Logger logger = LoggerFactory.getLogger(UserServiceImpl.class);

    // 填写上你的AppID,如何获取AppID自行百度,这步骤很简单
    private final static String APP_ID = "wxc41c88e07f3f1bd7";
    // 填写上你的AppSecret,如何获取AppSecret自行百度,这步骤很简单
    private final static String APP_SECRET = "99a06dc0d1e21d797a9915baca08c872";
    // 微信小程序登录校验请求地址
    private final static String LOGIN_URL = "https://api.weixin.qq.com/sns/jscode2session";

    /**
     * 小程序授权登录验证
     * @param userDTO
     * @return
     */
    @Override
    public ResponseDTO<UserDTO> appWxLogin(UserDTO userDTO) {
        String url = LOGIN_URL + "?appid=" + APP_ID + "&secret="+ APP_SECRET + "&grant_type=authorization_code&js_code=" + userDTO.getCode();
        HttpClient client = HttpClients.createDefault(); // 创建默认http连接
        HttpGet getRequest = new HttpGet(url);// 创建一个get请求
        LoginDTO loginDTO = new LoginDTO(); // 存储下面http请求返回的结果
        try {
            // 用http连接去执行get请求并且获得http响应
            HttpResponse response = client.execute(getRequest);
            // 从response中取到响实体
            HttpEntity entity = response.getEntity();
            // 把响应实体转成文本
            String html = EntityUtils.toString(entity);
            loginDTO = JSON.parseObject(html, LoginDTO.class);
            if(null == loginDTO.getErrcode()) {
                userDTO.setWxId(loginDTO.getOpenid()); // 拿到openId,存入userDTO实体
            } else {
                return ResponseDTO.errorByMsg(CodeMsg.USER_WX_LOGIN_ERROR);
            }
        } catch (Exception e) {
            e.printStackTrace();
            return ResponseDTO.errorByMsg(CodeMsg.USER_WX_LOGIN_ERROR);
        }
        // 使用微信openId查询是否有此用户
        UserExample userExample = new UserExample();
        userExample.createCriteria().andWxIdEqualTo(userDTO.getWxId());
        List<User> userList = userMapper.selectByExample(userExample);
        if(null != userList && userList.size() > 0) {
            // 已经存在用户信息,读取数据库中用户信息
            User user = userList.get(0);
            userDTO = CopyUtil.copy(user, UserDTO.class);
        } else {
            // 数据库中不存在,注册用户信息
            User user = CopyUtil.copy(userDTO, User.class);
            // 自定义工具类,生成8位uuid
            user.setId(UuidUtil.getShortUuid());
            user.setUsername(user.getWxUsername());
            user.setHeadPic(user.getWxHeadPic());
            user.setRoleId(RoleEnum.USER.getCode());
            if(userMapper.insertSelective(user) == 0) {
                return ResponseDTO.errorByMsg(CodeMsg.USER_REGISTER_ERROR);
            }
            // domain转dto 这步不是必须的,我项目中需要这步
            userDTO = CopyUtil.copy(user, UserDTO.class);
        }
        // 生成8位uuid作为登录的token,标识用户的登录信息
        userDTO.setToken(UuidUtil.getShortUuid());
        // 把用户登录信息存入redis中,定时1小时
        stringRedisTemplate.opsForValue().set("USER_" + userDTO.getToken(), JSON.toJSONString(userMapper.selectByPrimaryKey(userDTO.getId())), 3600, TimeUnit.SECONDS);
        return ResponseDTO.successByMsg(userDTO, "登录成功!");
    }

    
    /**
     * 获取当前登录用户
     * @param token
     * @return
     */
    @Override
    public ResponseDTO<UserDTO> getLoginUser(String token) {
        if(CommonUtil.isEmpty(token)){
            return ResponseDTO.errorByMsg(CodeMsg.USER_SESSION_EXPIRED);
        }
        String value = stringRedisTemplate.opsForValue().get("USER_" + token);
        if(CommonUtil.isEmpty(value)){
            return ResponseDTO.errorByMsg(CodeMsg.USER_SESSION_EXPIRED);
        }
        UserDTO selectedUserDTO = JSON.parseObject(value, UserDTO.class);
        return ResponseDTO.success(CopyUtil.copy(userMapper.selectByPrimaryKey(selectedUserDTO.getId()), UserDTO.class));
    }

    /**
     * 退出登录操作
     * @param userDTO
     * @return
     */
    @Override
    public ResponseDTO<Boolean> logout(UserDTO userDTO) {
        if(!CommonUtil.isEmpty(userDTO.getToken())){
            // token不为空  清除redis中数据
            stringRedisTemplate.delete("USER_" + userDTO.getToken());
        }
        return ResponseDTO.successByMsg(true, "退出登录成功!");
    }

   
}

四、备注

大家要跟着我的教学视频去配套着看代码,了解整个登录流程的实现思路最重要! 以上是我列出的主要实现代码页面样式那些根据自己需求去实现,我这就不贴了。文章来源地址https://www.toymoban.com/news/detail-720783.html

到了这里,关于【2023最新】微信小程序中微信授权登录功能和退出登录功能实现讲解的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 关于uniapp中微信小程序获取最新昵称和头像的方法

    哎,最近项目中遇到一个需求就是直接获取微信头像和昵称,可是去官方查阅后发现原先的接口已经不能获取了,返回的是灰色头像和微信用户,后来只能采用亡羊补牢的方法,就是用内置按钮组件的开放能力,引用了插件市场的代码,地址链接获取昵称、头像的弹窗,适用

    2024年02月08日
    浏览(32)
  • 微信小程序 - 2023年最新版手机号快捷登录详细教程

    最近开发公司手机快捷登录的功能,花费了不少时间,这里附上详细教程。 这里以海底捞小程序的图片为例,如有侵权请联系小编删除。 1、如果在微信开发者工具弹出下边的提示,不要慌张,用真机预览,其实是生效的。

    2024年02月09日
    浏览(46)
  • 【微信授权登录】uniapp开发小程序,实现微信授权登录功能 & 退出登录

    微信授权登录(获取用户信息) 1.先获取用户信息——用户授权允许后,通过调用uni.login 可以获取到code。 2.拿着获取到的code去调用——登录接口,可以获取到token。 3.把token存入缓存。就可以在页面判断是否登录了。 第一种方式: 第二种方式:

    2024年02月03日
    浏览(35)
  • 【微信授权登录】uniapp开发小程序,实现获取微信授权登录功能

    微信授权登录(获取用户信息) 1.先获取用户信息——用户授权允许后,通过调用uni.login 可以获取到code。 2.拿着获取到的code去调用——登录接口,可以获取到token。 3.把token存入缓存。就可以在页面判断是否登录了。 第一种方式: 第二种方式:

    2024年02月11日
    浏览(27)
  • 微信小程序 - 2023 年最新授权获取用户手机号详细教程,完美解决 getPhoneNumber 获取不到 code 的问题(老项目使用手机号快速验证组件,打印授权后没有code字段,拿不到cod)

    由于官方修改了 “获取用户手机号” 规则,导致网上几乎所有教程全部失效,本文来做最新详细教程。 2023年8月往后(官方废弃了原来 “免费” 获取用户手机号的相关方法 API,导致了大量小程序原获取手机号的方式失效报错),本文是最新微信小程序 “收费” 获取用户手

    2024年02月17日
    浏览(48)
  • 微信小程序-微信授权登录

    小程序可以通过微信官方提供的登录能力方便地获取微信提供的用户身份标识,快速建立小程序内的用户体系 触发授权登录 : 用户在小程序中触发登录操作,通常通过点击登录按钮或执行相关操作。 授权弹窗 : 小程序弹出授权登录的弹窗,要求用户授权小程序访问其微信账

    2024年02月08日
    浏览(34)
  • 微信小程序——授权登录

    在微信小程序中,授权登录通常是指用户允许小程序获取其微信用户信息(如昵称、头像等)的过程。以下是微信小程序授权登录的基本步骤以及相关API的使用: 步骤一:获取用户授权 在小程序中,你需要创建一个按钮或其他用户触发的UI元素,以触发授权登录操作。 创建

    2024年02月04日
    浏览(34)
  • 微信小程序授权登录

    登录流程时序 说明: 1.小程序端调用  wx.login()  获取临时登录凭证code ,并回传到开发者服务器。 2.服务器调用  code2Session  接口,换取 用户唯一标识 OpenID 和 会话密钥 session_key。 之后开发者服务器可以根据用户标识来生成自定义登录态,用于后续业务逻辑中前后端交互

    2024年02月07日
    浏览(46)
  • 微信小程序三种授权登录以及授权登录流程讲解

    🎉🎉欢迎来到我的CSDN主页!🎉🎉 🏅我是Java方文山,一个在CSDN分享笔记的博主。📚📚 🌟推荐给大家我的专栏《 微信小程序开发实战 》。🎯🎯 👉点击这里,就可以查看我的主页啦!👇👇 Java方文山的个人主页 🎁如果感觉还不错的话请给我点赞吧!🎁🎁 💖期待你

    2024年02月08日
    浏览(35)
  • 微信小程序授权登录流程

    我是IT果果日记,微信公众号请搜索 IT果果日记 一个普通的技术宅,定期分享技术文章,欢迎点赞、关注和转发,请多关照。 首先, 我们要了解什么是微信小程序登录?它的作用是什么? 微信小程序登录是为了让开发者的服务器获取用户的openId以及session_key的令牌。 请不要

    2024年02月14日
    浏览(36)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包