当前位置:网站首页>15、用户web层服务(三)
15、用户web层服务(三)
2022-07-28 11:13:00 【无休止符】
一、图形验证码
1 - 生成图片验证码
- 官方地址:https://mojotv.cn/go/refactor-base64-captcha
- user_web\api\chaptcha.go
package api
import (
"net/http"
"github.com/gin-gonic/gin"
"github.com/mojocn/base64Captcha"
"go.uber.org/zap"
)
var store = base64Captcha.DefaultMemStore
func GetCaptcha(ctx *gin.Context) {
driver := base64Captcha.NewDriverDigit(80, 240, 5, 0.7, 80)
cp := base64Captcha.NewCaptcha(driver, store)
id, b64s, err := cp.Generate()
if err != nil {
zap.S().Errorf("生成验证码错误,: ", err.Error())
ctx.JSON(http.StatusInternalServerError, gin.H{
"msg": "生成验证码错误",
})
return
}
ctx.JSON(http.StatusOK, gin.H{
"captchaId": id,
"picPath": b64s,
})
}
- user_web\router\router_base.go
package router
import (
"github.com/gin-gonic/gin"
"web_api/user_web/api"
)
func InitBaseRouter(Router *gin.RouterGroup) {
BaseRouter := Router.Group("base")
{
BaseRouter.GET("captcha", api.GetCaptcha)
}
}
- user_web\initialize\init_router.go
package initialize
import (
"github.com/gin-gonic/gin"
"web_api/user_web/middlewares"
"web_api/user_web/router"
)
func Routers() *gin.Engine {
Router := gin.Default()
//配置跨域
Router.Use(middlewares.Cors())
ApiGroup := Router.Group("/u/v1")
router.InitUserRouter(ApiGroup)
router.InitBaseRouter(ApiGroup)
return Router
}

- 在线转换查看base64图片:https://www.qvdv.net/tools/qvdv-img2base64.html

2 - 登录添加图片验证码
- user_web\forms\form_user.go
package forms
type PassWordLoginForm struct {
Mobile string `form:"mobile" json:"mobile" binding:"required,mobile"` //手机号码格式有规范可寻, 自定义validator
PassWord string `form:"password" json:"password" binding:"required,min=3,max=20"`
Captcha string `form:"captcha" json:"captcha" binding:"required,min=5,max=5"`
CaptchaId string `form:"captcha_id" json:"captcha_id" binding:"required"`
}
- user_web\api\api_user.go
func PassWordLogin(c *gin.Context) {
//表单验证
passwordLoginForm := forms.PassWordLoginForm{
}
if err := c.ShouldBind(&passwordLoginForm); err != nil {
HandleValidatorError(c, err)
return
}
if store.Verify(passwordLoginForm.CaptchaId, passwordLoginForm.Captcha, false) {
c.JSON(http.StatusBadRequest, gin.H{
"captcha": "验证码错误",
})
return
}
//...省略

二、用户注册
1 - docker安装redis
- 参考地址:https://blog.csdn.net/qq23001186/article/details/126023939
- redis的go驱动:https://github.com/go-redis/redis
2 - 阿里云短信验证码
- user_web\forms\form_sms.go
package forms
type SendSmsForm struct {
Mobile string `form:"mobile" json:"mobile" binding:"required,mobile"` // 手机号码格式有规范可寻, 自定义validator
Type uint `form:"type" json:"type" binding:"required,oneof=1 2"` // 注册发送短信验证码和动态验证码登录发送验证码
}
- user_web\router\router_base.go
package router
import (
"github.com/gin-gonic/gin"
"web_api/user_web/api"
)
func InitBaseRouter(Router *gin.RouterGroup) {
BaseRouter := Router.Group("base")
{
BaseRouter.GET("captcha", api.GetCaptcha)
BaseRouter.POST("send_sms", api.SendSms)
}
}
- user_web\api\sms.go
package api
import (
"context"
"fmt"
"math/rand"
"net/http"
"strings"
"time"
"web_api/user_web/forms"
"github.com/aliyun/alibaba-cloud-sdk-go/sdk/requests"
"github.com/aliyun/alibaba-cloud-sdk-go/services/dysmsapi"
"github.com/gin-gonic/gin"
"github.com/go-redis/redis/v8"
"web_api/user_web/global"
)
func GenerateSmsCode(witdh int) string {
//生成width长度的短信验证码
numeric := [10]byte{
0, 1, 2, 3, 4, 5, 6, 7, 8, 9}
r := len(numeric)
rand.Seed(time.Now().UnixNano())
var sb strings.Builder
for i := 0; i < witdh; i++ {
fmt.Fprintf(&sb, "%d", numeric[rand.Intn(r)])
}
return sb.String()
}
func SendSms(ctx *gin.Context) {
sendSmsForm := forms.SendSmsForm{
}
if err := ctx.ShouldBind(&sendSmsForm); err != nil {
HandleValidatorError(ctx, err)
return
}
client, err := dysmsapi.NewClientWithAccessKey("cn-beijing", global.ServerConfig.AliSmsInfo.ApiKey, global.ServerConfig.AliSmsInfo.ApiSecrect)
if err != nil {
panic(err)
}
smsCode := GenerateSmsCode(6)
request := requests.NewCommonRequest()
request.Method = "POST"
request.Scheme = "https" // https | http
request.Domain = "dysmsapi.aliyuncs.com"
request.Version = "2017-05-25"
request.ApiName = "SendSms"
request.QueryParams["RegionId"] = "cn-beijing"
request.QueryParams["PhoneNumbers"] = sendSmsForm.Mobile //手机号
request.QueryParams["SignName"] = "慕学在线" //阿里云验证过的项目名 自己设置
request.QueryParams["TemplateCode"] = "SMS_181850725" //阿里云的短信模板号 自己设置
request.QueryParams["TemplateParam"] = "{\"code\":" + smsCode + "}" //短信模板中的验证码内容 自己生成 之前试过直接返回,但是失败,加上code成功。
response, err := client.ProcessCommonRequest(request)
fmt.Print(client.DoAction(request, response))
if err != nil {
fmt.Print(err.Error())
}
//将验证码保存起来 - redis
rdb := redis.NewClient(&redis.Options{
Addr: fmt.Sprintf("%s:%d", global.ServerConfig.RedisInfo.Host, global.ServerConfig.RedisInfo.Port),
})
rdb.Set(context.Background(), sendSmsForm.Mobile, smsCode, time.Duration(global.ServerConfig.RedisInfo.Expire)*time.Second)
ctx.JSON(http.StatusOK, gin.H{
"msg": "发送成功",
})
}
- yaml:隐私原因key和secret未配置
//user_web\config_debug.yaml
//user_web\config_pro.yaml
name: 'user-web'
port: '8081'
user_srv:
host: '127.0.0.1'
port: '50051'
jwt:
key: 'VYLDYq3&hGWjWqF$K1ih'
sms:
key: ''
secrect: ''
expire: 300
redis:
host: '192.168.124.51'
port: '6379'
三、用户注册接口
- user_web\forms\form_user.go
package forms
type PassWordLoginForm struct {
Mobile string `form:"mobile" json:"mobile" binding:"required,mobile"` //手机号码格式有规范可寻, 自定义validator
PassWord string `form:"password" json:"password" binding:"required,min=3,max=20"`
Captcha string `form:"captcha" json:"captcha" binding:"required,min=5,max=5"`
CaptchaId string `form:"captcha_id" json:"captcha_id" binding:"required"`
}
type RegisterForm struct {
Mobile string `form:"mobile" json:"mobile" binding:"required,mobile"` //手机号码格式有规范可寻, 自定义validator
PassWord string `form:"password" json:"password" binding:"required,min=3,max=20"`
Code string `form:"code" json:"code" binding:"required,min=6,max=6"`
}
- user_web\api\api_user.go
func Register(c *gin.Context) {
//用户注册
registerForm := forms.RegisterForm{
}
if err := c.ShouldBind(®isterForm); err != nil {
HandleValidatorError(c, err)
return
}
//验证码
rdb := redis.NewClient(&redis.Options{
Addr: fmt.Sprintf("%s:%d", global.ServerConfig.RedisInfo.Host, global.ServerConfig.RedisInfo.Port),
})
value, err := rdb.Get(registerForm.Mobile).Result()
if err == redis.Nil {
c.JSON(http.StatusBadRequest, gin.H{
"code": "验证码错误",
})
return
} else {
if value != registerForm.Code {
c.JSON(http.StatusBadRequest, gin.H{
"code": "验证码错误",
})
return
}
}
user, err := global.UserSrvClient.CreateUser(context.Background(), &proto.CreateUserInfo{
NickName: registerForm.Mobile,
PassWord: registerForm.PassWord,
Mobile: registerForm.Mobile,
})
if err != nil {
zap.S().Errorf("[Register] 查询 【新建用户失败】失败: %s", err.Error())
HandleGrpcErrorToHttp(err, c)
return
}
j := middlewares.NewJWT()
claims := models.CustomClaims{
ID: uint(user.Id),
NickName: user.NickName,
AuthorityId: uint(user.Role),
StandardClaims: jwt.StandardClaims{
NotBefore: time.Now().Unix(), //签名的生效时间
ExpiresAt: time.Now().Unix() + 60*60*24*30, //30天过期
Issuer: "imooc",
},
}
token, err := j.CreateToken(claims)
if err != nil {
c.JSON(http.StatusInternalServerError, gin.H{
"msg": "生成token失败",
})
return
}
c.JSON(http.StatusOK, gin.H{
"id": user.Id,
"nick_name": user.NickName,
"token": token,
"expired_at": (time.Now().Unix() + 60*60*24*30) * 1000,
})
}
- user_web\router\router_user.go
package router
import (
"web_api/user_web/api"
"web_api/user_web/middlewares"
"github.com/gin-gonic/gin"
"go.uber.org/zap"
)
func InitUserRouter(Router *gin.RouterGroup) {
UserRouter := Router.Group("user")
//UserRouter := Router.Group("user").Use(middlewares.JWTAuth()) //给整个user都添加登录验证
zap.S().Info("配置用户相关的url")
{
UserRouter.GET("list", middlewares.JWTAuth(), middlewares.IsAdminAuth(), api.GetUserList)
UserRouter.POST("pwd_login", api.PassWordLogin)
UserRouter.POST("register", api.Register)
}
}
- YApi配置注册接口

四、完整源码
边栏推荐
- Flash point list of cross platform efficiency software
- Introduction to web security RADIUS protocol application
- 目标检测领域必看的6篇论文
- Server online speed measurement system source code
- A new mode of one-stop fixed asset management
- Introduction to the usage of SAP ui5 image display control avatar trial version
- OsCache缓存监控刷新工具
- R language uses LM function to build regression model with interactive items, and uses: sign (colon) to represent the interaction of variables (colon is pure multiplication, excluding the constituent
- ES6知识点补充
- 从零开始Blazor Server(2)--整合数据库
猜你喜欢

Leecode8 string conversion integer (ATOI)
![[half understood] zero value copy](/img/4b/c8140bf7ee4baa094ca3011108d686.gif)
[half understood] zero value copy

AlexNet—论文分析及复现

Quickly deploy mqtt clusters on AWS using terraform

Outlook suddenly becomes very slow and too laggy. How to solve it

Design a system that supports millions of users

Cvpr2021 pedestrian re identification /person re identification paper + summary of open source code

B2 sub theme / blog b2child sub theme / open source code

Ten thousand words detailed Google play online application standard package format AAB

Three methods of using unity mouse to drive objects
随机推荐
Embrace open source guidelines
R语言-用于非平衡数据集的一些度量指标
CVPR2021 行人重识别/Person Re-identification 论文+开源代码汇总
How to use JWT for authentication and authorization
R language uses LM function to build regression model, uses the augmented function of bloom package to store the model results in dataframe, and uses ggplot2 to visualize the regression residual diagr
In order to ensure the normal operation of fire-fighting equipment in large buildings, the power supply monitoring system of fire-fighting equipment plays a key role
Object stream of i/o operation (serialization and deserialization)
Learning notes tree array
一文看懂设备指纹如何防篡改、防劫持
Tiktok programmer confession special code tutorial (how to play Tiktok)
echo -ne(echo line)
Outlook suddenly becomes very slow and too laggy. How to solve it
Solutions to the disappearance of Jupiter, spyder, Anaconda prompt and navigator shortcut keys
Left connection and right connection of MySQL (the difference between inner connection and natural connection)
数字孪生轨道交通:“智慧化”监控疏通城市运行痛点
Understand how to prevent tampering and hijacking of device fingerprints
什么是WordPress
mysql(8.0.16版)命令及说明
OsCache缓存监控刷新工具
[极客大挑战 2019]BabySQL-1|SQL注入