(三)登录和注册(handle_auto.go)

登录和注册(handle_auto.go)

在这里插入图片描述

文章目录

  • 登录和注册(handle_auto.go)
    • 一、所需要的结构体信息
    • 二、注册
    • 三、登录
    • 四、退出

一、所需要的结构体信息

type UserAuth struct{}type LoginReq struct {Username string `json:"username" binding:"required"`Password string `json:"password" binding:"required"`
}type RegisterReq struct {Username string `json:"username" binding:"required"`Password string `json:"password" binding:"required,min=4,max=20"`Code     string `json:"code" binding:"required"`
}type LoginVO struct {model.UserInfo// 点赞 Set: 用于记录用户点赞过的文章, 评论ArticleLikeSet []string `json:"article_like_set"`CommentLikeSet []string `json:"comment_like_set"`Token          string   `json:"token"`
}

二、注册

因为原本的作者没有写注册的功能,我就自己写了一个简单的注册功能。

1.注册的路由

base.POST("/register", userAuthAPI.Register)    // 注册

2.验证码的功能函数

handler层的函数

  • 使用qq邮箱发送验证
  • 限制发送时间
  • 使用redis存储验证码,时间1分钟
func (*UserAuth) SendCode(c *gin.Context) {// 发送验证码限制于1分钟发一次elapsedTime := time.Since(lastEmailSent)remaingTime := time.Minute - elapsedTimeif elapsedTime < time.Minute {c.JSON(http.StatusOK, gin.H{"message": fmt.Sprintf("发送验证码过于频繁,请稍后再试,剩余时间:%d秒", int(remaingTime.Seconds()))})return}// 从请求参数中获取邮箱地址email := c.Query("email")if email == "" {c.JSON(http.StatusBadRequest, gin.H{"error": "未提供邮箱地址"})return}// 发送邮件验证码err := SendEmail(email, c)if err != nil {c.JSON(http.StatusInternalServerError, gin.H{"error": "发送邮件失败"})return}// 发送邮件成功,返回成功响应给前端lastEmailSent = time.Now()ReturnSuccess(c, "验证码发送成功")
}// 发送邮件到指定邮箱
func SendEmail(email string, c *gin.Context) error {// 邮箱配置信息config := gomail.NewDialer("smtp.qq.com", 465, "xxx@qq.com", "自己的授权码")//config.TLSConfig.ServerName = "smtp.qq.com"//config.TLSConfig.InsecureSkipVerify = false// 创建邮件内容message := gomail.NewMessage()message.SetHeader("From", "xxx@qq.com")message.SetHeader("To", email)message.SetHeader("Subject", "验证码")// 获取随机验证码computing := utils2.GetRandNums(6)message.SetBody("text/html", fmt.Sprintf("欢迎使用席万里的博客系统,这是您的注册验证码:%s", computing))// 连接并发送邮件dialer, err := config.Dial()if err != nil {return err}defer dialer.Close()if err = gomail.Send(dialer, message); err != nil {return err}// 将验证码存到redis中,确保输入的是正确的rdb := GetRDB(c)// 以email为key,mima为val存入redis,只存在1分钟rdb.Set(rctx, email, computing, time.Minute)return nil
}

3.注册的主功能函数

  • 用到了密码加密
  • 随机验证码的生成
  • 数据的写入
func (*UserAuth) Register(c *gin.Context) {var req RegisterReqif err := c.ShouldBindJSON(&req); err != nil {ReturnError(c, g2.ErrRequest, err)return}db := GetDB(c)rdb := GetRDB(c)// 检查邮箱是否已经被注册_, err := model.GetUserAuthInfoByName(db, req.Username)if err != nil {if !errors.Is(err, gorm.ErrRecordNotFound) {ReturnError(c, g2.ErrDbOp, err)return}} else {ReturnError(c, g2.ErrMailAleradyUsed, "邮箱已经被使用")return}// 取出来验证码码做判断 看是否正确computing, err := rdb.Get(rctx, req.Username).Result()if err != nil {// 处理获取验证码失败的情况ReturnError(c, g2.FailResult, err)return}// 如果验证码不正确,则返回错误信息if computing != req.Code {ReturnError(c, g2.ErrVerificationCode, "验证码错误")return}// 将密码加密hashpassword, _ := utils2.BcryptHash(req.Password)err = model.RegisterDB(db, req.Username, hashpassword)if err != nil {ReturnError(c, g2.ErrDbOp, "注册失败")}ReturnSuccess(c, "注册成功")
}

4.数据库层的邮箱查重函数

func GetUserAuthInfoByName(db *gorm.DB, name string) (*UserAuth, error) {var userAuth UserAuthresult := db.Where(&UserAuth{Username: name}).First(&userAuth)return &userAuth, result.Error
}

5.数据查入、生成随机验证码、mimajiammi

// 数据查入
// 用户注册 用户名,密码
func RegisterDB(db *gorm.DB, username, hashpassword string) error {// 创建新用户认证信息newUserAuth := &UserAuth{Model: Model{CreatedAt: time.Now(),UpdatedAt: time.Now(),},Username: username,Password: hashpassword,}// 保存新用户认证信息到数据库if err := db.Create(newUserAuth).Error; err != nil {return err}return nil
}
// 生成随机验证码
func GetRandNums(digits int) string {rand.Seed(time.Now().UnixNano())numeric := [10]byte{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}var sb strings.Builderfor i := 0; i < digits; i++ {fmt.Fprintf(&sb, "%d", numeric[rand.Intn(len(numeric))])}return sb.String()
}// 密码加密
func BcryptHash(str string) (string, error) {bytes, err := bcrypt.GenerateFromPassword([]byte(str), bcrypt.DefaultCost)return string(bytes), err
}

三、登录

登录功能也用到了查重,校验密码hash等功能,这里不在讲述。

  • 生成jwt token
  • 使用MD5加密
  • 使用Session存储认证ID
  • 使用Redis存储在线信息
func (*UserAuth) Login(c *gin.Context) {var req LoginReqif err := c.ShouldBindJSON(&req); err != nil {ReturnError(c, g2.ErrRequest, err)return}db := GetDB(c)rdb := GetRDB(c)userAuth, err := model.GetUserAuthInfoByName(db, req.Username)if err != nil {if errors.Is(err, gorm.ErrRecordNotFound) {ReturnError(c, g2.ErrUserNotExist, nil)return}ReturnError(c, g2.ErrDbOp, err)return}// 检查密码是否正确if !utils2.BcryptCheck(req.Password, userAuth.Password) {ReturnError(c, g2.ErrPassword, nil)return// 获取 IP 相关信息 FIXME: 好像无法读取到 ip 信息ipAddress := utils2.IP.GetIpAddress(c)ipSource := utils2.IP.GetIpSourceSimpleIdle(ipAddress)userInfo, err := model.GetUserInfoById(db, userAuth.UserInfoId)if err != nil {if errors.Is(err, gorm.ErrRecordNotFound) {ReturnError(c, g2.ErrUserNotExist, nil)return}ReturnError(c, g2.ErrDbOp, err)return}roleIds, err := model.GetRoleIdsByUserId(db, userAuth.ID)if err != nil {ReturnError(c, g2.ErrDbOp, err)return}articleLikeSet, err := rdb.SMembers(rctx, g2.ARTICLE_USER_LIKE_SET+strconv.Itoa(userAuth.ID)).Result()if err != nil {ReturnError(c, g2.ErrDbOp, err)return}commentLikeSet, err := rdb.SMembers(rctx, g2.COMMENT_USER_LIKE_SET+strconv.Itoa(userAuth.ID)).Result()if err != nil {ReturnError(c, g2.ErrDbOp, err)return}// 登录信息正确, 生成 Token// UUID 生成方法: ip + 浏览器信息 + 操作系统信息// uuid := utils.MD5(ipAddress + browser + os)conf := g.Conf.JWTtoken, err := jwt.GenToken(conf.Secret, conf.Issuer, int(conf.Expire), userAuth.ID, roleIds)if err != nil {ReturnError(c, g2.ErrTokenCreate, err)return}// 更新用户验证信息: ip 信息 + 上次登录时间err = model.UpdateUserLoginInfo(db, userAuth.ID, ipAddress, ipSource)if err != nil {ReturnError(c, g2.ErrDbOp, err)return}slog.Info("用户登录成功: " + userAuth.Username)session := sessions.Default(c)session.Set(g2.CTX_USER_AUTH, userAuth.ID)session.Save()// 删除 Redis 中的离线状态offlineKey := g2.OFFLINE_USER + strconv.Itoa(userAuth.ID)rdb.Del(rctx, offlineKey).Result()ReturnSuccess(c, LoginVO{UserInfo: *userInfo,ArticleLikeSet: articleLikeSet,CommentLikeSet: commentLikeSet,Token:          token,})
}

1.use Redis 缓存用户收藏和喜欢的文章

	articleLikeSet, err := rdb.SMembers(rctx, g2.ARTICLE_USER_LIKE_SET+strconv.Itoa(userAuth.ID)).Result()if err != nil {ReturnError(c, g2.ErrDbOp, err)return}commentLikeSet, err := rdb.SMembers(rctx, g2.COMMENT_USER_LIKE_SET+strconv.Itoa(userAuth.ID)).Result()if err != nil {ReturnError(c, g2.ErrDbOp, err)return}

四、退出

func (*UserAuth) Logout(c *gin.Context) {c.Set(g2.CTX_USER_AUTH, nil)// 已经退出登录auth, _ := CurrentUserAuth(c)if auth == nil {ReturnSuccess(c, nil)return}session := sessions.Default(c)session.Delete(g2.CTX_USER_AUTH)session.Save()// 删除 Redis 中的在线状态rdb := GetRDB(c)onlineKey := g2.ONLINE_USER + strconv.Itoa(auth.ID)rdb.Del(rctx, onlineKey)ReturnSuccess(c, nil)
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/830266.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

错误代码126:加载xinput1_3.dll失败如何解决?8个解决方法分享

xinput1_3.dll是Windows操作系统中一个非常关键的动态链接库&#xff08;Dynamic Link Library, DLL&#xff09;文件&#xff0c;它是微软DirectX软件开发包的组成部分&#xff0c;专门用于支持游戏控制器和其它输入设备在游戏及多媒体应用程序中的交互。下面是对xinput1_3.dl…

封装 H.264 视频为 FLV 格式然后推流

封装 H.264 视频为 FLV 格式并通过 RTMP 推流 flyfish 协议 RTMP (Real-Time Messaging Protocol) RTSP (Real Time Streaming Protocol) SRT (Secure Reliable Transport) WebRTC RTMP&#xff08;Real Time Messaging Protocol&#xff09;是一种用于实时音视频流传输的协…

qt安装历史版本5.15.2

0 背景 因为需要&#xff0c;所以需要安装qt5的最后一个版本qt5.15.2&#xff0c;但是下载qt安装器后&#xff0c;发现没有想要的版本。后面才发现&#xff0c;可以筛选历史版本进行安装。 1 解决 1&#xff0c;打开qt安装程序&#xff0c;勾选Archive后&#xff0c;点击筛选…

Python实现自动化的服务器部署和配置管理库之pyinfra使用详解

概要 在现代软件开发中,自动化部署和配置管理变得越来越重要。Python pyinfra库是一个强大的工具,可以帮助开发者实现自动化的服务器部署和配置管理。本文将介绍pyinfra库的安装、特性、基本功能、高级功能、实际应用场景以及总结。 安装 首先,来看一下如何安装pyinfra库。…

服务器被CC攻击怎么办

遇到CC攻击时&#xff0c;可采取以下措施&#xff1a;限制IP访问频率、启用防DDoS服务、配置Web应用防火墙、增加服务器带宽、使用负载均衡分散请求压力。 处理服务器遭遇CC攻击的方法如下&#xff1a; 1. 确认攻击 你需要确认服务器是否真的遭受了CC攻击&#xff0c;这可以…

书生浦语训练营第三节笔记和作业-茴香豆 搭建你的Rag智能助理

书生 浦语 茴香豆项目是一个基于大型语言模型&#xff08;LLM&#xff09;的群聊知识助手&#xff0c;由上海人工智能实验室的书生浦语团队开发。这个项目利用了RAG&#xff08;Retrieval-Augmented Generation&#xff09;技术&#xff0c;通过检索与用户输入相关的信息&#…

P6技巧-关于汇总项目Summarize的使用

前言 不知你在使用P6项目时是否察觉到这么一个有趣的现象&#xff0c;但打开一个项目&#xff08;展开详细任务&#xff09;时&#xff0c;在项目页签下可以看到该项目能反馈此时项目的总体进展&#xff0c;完成时间等内容&#xff1b;而当项目关闭时&#xff0c;其前1s所展示…

Linux快速部署大语言模型LLaMa3,Web可视化j交互(Ollama+Open Web UI)

本文在个人博客同步发布&#xff0c;前往阅读 1 介绍 本文将介绍使用开源工具Ollama(60.6k⭐)部署LLaMa大模型&#xff0c;以及使用Open WebUI搭建前端Web交互界面的方法。 我们先来过一遍几个相关的概念&#xff0c;对这块比较熟悉的朋友可跳过。 1.1 大规模语言模型 大规…

Eclipse内存分析器 Java内存分析工具MAT(Memory Analyzer Tool)的介绍与使用

1.visualvm实时监测 2.Memory Analyzer Tool打开 3.工具的使用可以参考 Java内存分析工具MAT(Memory Analyzer Tool)的介绍与使用 ------------------------ 1.我远程发现是其中一个客户端A请求服务器页面响应&#xff0c;一直得不到响应&#xff0c;然后客户端A一直请求&am…

Ansible 自动化运维

一、介绍 1、定义&#xff1a; ansible是自动化运维工具&#xff0c;基于Python开发&#xff0c;具有批量系统配置、批量程序部署、批量运行命令等功能。 ansible是基于 paramiko&#xff08;框架&#xff09; 开发的&#xff0c;并且基于模块化工作&#xff0c;本身没有批量…

报表控件Stimulsoft在JavaScript报告工具中的事件:查看器事件(上)

Stimulsoft Ultimate &#xff08;原Stimulsoft Reports.Ultimate&#xff09;是用于创建报表和仪表板的通用工具集。该产品包括用于WinForms、ASP.NET、.NET Core、JavaScript、WPF、PHP、Java和其他环境的完整工具集。无需比较产品功能&#xff0c;Stimulsoft Ultimate包含了…

[华为OD]给定一个 N*M 矩阵,请先找出 M 个该矩阵中每列元素的最大值 100

题目&#xff1a; 给定一个 N*M 矩阵&#xff0c;请先找出 M 个该矩阵中每列元素的最大值&#xff0c;然后输出这 M 个值中的 最小值 补充说明&#xff1a; N 和 M 的取值范围均为&#xff1a;[0, 100] 示例 1 输入&#xff1a; [[1,2],[3,4]] 输出&#xff1a; 3 说…

力扣-有效的数独

请你判断一个 9 x 9 的数独是否有效。只需要 根据以下规则 &#xff0c;验证已经填入的数字是否有效即可。 数字 1-9 在每一行只能出现一次。数字 1-9 在每一列只能出现一次。数字 1-9 在每一个以粗实线分隔的 3x3 宫内只能出现一次。&#xff08;请参考示例图&#xff09; 注…

(三十一)第 5 章 数组和广义表(稀疏矩阵的三元组行逻辑链接的顺序存储表示实现)

1. 背景说明 2. 示例代码 1)errorRecord.h // 记录错误宏定义头文件#ifndef ERROR_RECORD_H #define ERROR_RECORD_H#include <stdio.h> #include <string.h> #include <stdint.h>// 从文件路径中提取文件名 #define FILE_NAME(X) strrchr(X, \\) ? strrch…

AI 工具合集

以下工具来源于互联网&#xff0c;可能会失效&#xff0c;请参考使用 网红工具 名称链接说明GPT-4https://chat.openai.com/ 需要梯子&#xff0c;需要付费。功能最强大的聊天机 器人。 文心一言https://yiyan.baidu.com/welcome 国内版 GPT&#xff0c;需要申请账号。回答问…

最好用的电脑监控软件,电脑监控软件怎么监控员工

电脑监控软件是一种专为跟踪和记录计算机使用情况而设计的应用程序&#xff0c;主要用于提升企业内部的信息安全、提高工作效率及监管员工行为。这些软件通常通过以下几种方式实现监控功能&#xff1a; 实时屏幕监控&#xff1a; 软件能够实时显示被监控电脑的屏幕画面&#x…

数据分析:扩增子分析(qiime2平台全流程分析)

Amplicon sequencing analysis pipeline through qiime2 platform qiime2是扩增子数据分析的最佳平台之一&#xff0c;其提供了大量从原始data到统计分析的插件&#xff0c;尤其是它的可重复分析且可扩展插件的理念使得其成为扩增子分析首选的平台。 Platform qiime2是扩增子…

Airmail 5 for Mac:高效电子邮件管理软件

Airmail 5 for Mac作为一款功能强大的电子邮件客户端软件&#xff0c;为Mac用户带来了全新的邮件管理体验。其高效、直观的操作界面&#xff0c;使得用户可以轻松管理各类邮件&#xff0c;提升工作效率。 Airmail 5 for Mac v5.7.4中文激活版 首先&#xff0c;Airmail 5支持多个…

若依前后端部署系统--详细附图

一、后端部署 1、在ruoyi项目的Maven中的生命周期下双击package.bat打包Web工程&#xff0c;生成jar包文件。 提示打包成功 2、多模块版本会生成在ruoyi/ruoyi-admin模块下target文件夹,我们打开目录ruoyi-admin/taget&#xff0c;打开cmd&#xff0c;运行java -jar jar包名称…

Windows Server 评估版转换(升级)为完整版

临时方法 获取 Windows Server 的剩余宽限期 Slmgr /dliWindows Server免费试用期可以使用以下命令合法延长5次&#xff0c;共180天&#xff1a; slmgr /rearm这意味着所评估的 Windows Server 的最长可用时间为 3 年 ( 180 days * 6)。 试用期到期后&#xff0c;Windows S…