package authlogic import ( "context" "errors" "fmt" "github.com/zeromicro/go-zero/core/stores/redis" "github.com/zeromicro/go-zero/core/stores/sqlc" "tianyuan-api/apps/user/internal/model" "regexp" "strings" "tianyuan-api/apps/user/internal/svc" "tianyuan-api/apps/user/user" "github.com/zeromicro/go-zero/core/logx" ) type RegisterUserLogic struct { ctx context.Context svcCtx *svc.ServiceContext logx.Logger } func NewRegisterUserLogic(ctx context.Context, svcCtx *svc.ServiceContext) *RegisterUserLogic { return &RegisterUserLogic{ ctx: ctx, svcCtx: svcCtx, Logger: logx.WithContext(ctx), } } // 注册接口 func (l *RegisterUserLogic) RegisterUser(in *user.RegisterReq) (*user.EmptyResponse, error) { // 检查密码是否一致 if in.Password != in.ConfirmPassword { return nil, errors.New("密码不一致") } // 检查密码强度 if err := checkPasswordStrength(in.Password); err != nil { return nil, err } // 校验手机号码 err := validatePhoneNumber(in.Phone) if err != nil { return nil, err } // 从 Redis 获取验证码 savedCode, err := l.svcCtx.Redis.Get(fmt.Sprintf("register:%s", in.Phone)) if err != nil { if errors.Is(err, redis.Nil) { return nil, errors.New("验证码已过期") } return nil, err } // 验证码不匹配 if savedCode != in.Code { return nil, errors.New("验证码不正确") } // 检查用户名是否已经存在 existingUser, err := l.svcCtx.UserModel.FindOneByUsername(l.ctx, in.Username) if err != nil && err != sqlc.ErrNotFound { // 如果发生其他错误,返回错误 return nil, err } if existingUser != nil { // 用户名已经存在,返回错误 return nil, errors.New("用户名已存在,请选择其他用户名") } // 检查手机号是否已经存在 existingPhone, err := l.svcCtx.UserModel.FindOneByPhone(l.ctx, in.Phone) if err != nil && err != sqlc.ErrNotFound { // 如果发生其他错误,返回错误 return nil, err } if existingPhone != nil { // 用户名已经存在,返回错误 return nil, errors.New("手机号码已存在,请选择其他用户名") } // 加密密码 hashedPassword := hashPassword(in.Password) // 构建 Users 结构体 users := &model.Users{ Username: in.Username, Password: hashedPassword, Phone: in.Phone, AuthStatus: "unverified", } // 调用 Insert 方法插入用户数据 _, err = l.svcCtx.UserModel.Insert(l.ctx, users) if err != nil { return nil, err } return &user.EmptyResponse{}, nil } // 密码强度检查 func checkPasswordStrength(password string) error { // 检查密码长度是否不少于8位 if len(password) < 8 { return errors.New("密码长度不能少于8位") } // 检查密码是否为简单重复的字符(如"11111111" 或 "aaaaaaaa"等) firstChar := password[0] if strings.Count(password, string(firstChar)) == len(password) { return errors.New("密码不能是重复的字符") } // 正则表达式:密码必须包含数字或字母,不能是全符号 var passwordRegex = `^[A-Za-z0-9]+$` match, _ := regexp.MatchString(passwordRegex, password) if !match { return errors.New("密码只能包含字母和数字") } return nil } // 校验手机号码的函数 func validatePhoneNumber(phone string) error { // 定义正则表达式,匹配中国大陆的手机号格式 var phoneRegex = `^1[3-9]\d{9}$` // 检查手机号是否匹配正则表达式 match, _ := regexp.MatchString(phoneRegex, phone) if !match { return errors.New("手机号码格式不正确") } return nil }