Merge branch 'main' of http://1.117.67.95:3000/team/qnc-server-v3
This commit is contained in:
@@ -10,6 +10,7 @@ import (
|
||||
"qnc-server/app/main/model"
|
||||
"qnc-server/common/ctxdata"
|
||||
"qnc-server/common/globalkey"
|
||||
"qnc-server/common/reviewphone"
|
||||
"qnc-server/common/xerr"
|
||||
"qnc-server/pkg/lzkit/crypto"
|
||||
|
||||
@@ -53,8 +54,12 @@ func (l *ApplyForAgentLogic) ApplyForAgent(req *types.AgentApplyReq) (resp *type
|
||||
if req.Referrer == "" {
|
||||
return nil, errors.Wrapf(xerr.NewErrMsg("请填写邀请信息"), "")
|
||||
}
|
||||
// 2. 校验验证码(开发环境下跳过验证码校验)
|
||||
if os.Getenv("ENV") != "development" {
|
||||
// 2. 校验验证码:开发环境跳过;审核预留号段 + 固定码;其余 Redis
|
||||
if os.Getenv("ENV") == "development" {
|
||||
// skip
|
||||
} else if reviewphone.IsAppReviewDemoMobile(req.Mobile) && req.Code == reviewphone.DemoVerifyCode {
|
||||
l.Infof("[ApplyForAgent] 审核体验号段固定验证码通过, mobile: %s", req.Mobile)
|
||||
} else {
|
||||
redisKey := fmt.Sprintf("%s:%s", "agentApply", encryptedMobile)
|
||||
cacheCode, err := l.svcCtx.Redis.Get(redisKey)
|
||||
if err != nil {
|
||||
|
||||
@@ -8,11 +8,13 @@ import (
|
||||
"qnc-server/app/main/model"
|
||||
"qnc-server/common/ctxdata"
|
||||
"qnc-server/common/globalkey"
|
||||
"qnc-server/common/reviewphone"
|
||||
"qnc-server/common/xerr"
|
||||
"qnc-server/pkg/lzkit/crypto"
|
||||
"strconv"
|
||||
"time"
|
||||
|
||||
"github.com/go-sql-driver/mysql"
|
||||
"github.com/google/uuid"
|
||||
"github.com/pkg/errors"
|
||||
"github.com/zeromicro/go-zero/core/stores/redis"
|
||||
@@ -24,6 +26,36 @@ import (
|
||||
"github.com/zeromicro/go-zero/core/logx"
|
||||
)
|
||||
|
||||
func isMySQLDuplicateEntry(err error) bool {
|
||||
var me *mysql.MySQLError
|
||||
return errors.As(err, &me) && me.Number == 1062
|
||||
}
|
||||
|
||||
// insertMobileUserAuthOrSkip 写入 mobile 认证;若并发重复插入触发唯一键冲突,且该手机号已绑定同一用户则视为成功(幂等)。
|
||||
func (l *RegisterByInviteCodeLogic) insertMobileUserAuthOrSkip(ctx context.Context, session sqlx.Session, userID string, encryptedMobile string) error {
|
||||
_, err := l.svcCtx.UserAuthModel.Insert(ctx, session, &model.UserAuth{
|
||||
Id: uuid.NewString(),
|
||||
UserId: userID,
|
||||
AuthType: model.UserAuthTypeMobile,
|
||||
AuthKey: encryptedMobile,
|
||||
})
|
||||
if err == nil {
|
||||
return nil
|
||||
}
|
||||
if !isMySQLDuplicateEntry(err) {
|
||||
return err
|
||||
}
|
||||
exist, findErr := l.svcCtx.UserAuthModel.FindOneByAuthTypeAuthKey(ctx, model.UserAuthTypeMobile, encryptedMobile)
|
||||
if findErr != nil {
|
||||
return findErr
|
||||
}
|
||||
if exist != nil && exist.UserId == userID {
|
||||
l.Infof("[insertMobileUserAuthOrSkip] mobile 认证已由并发请求创建,跳过: userId=%s", userID)
|
||||
return nil
|
||||
}
|
||||
return errors.Wrapf(xerr.NewErrMsg("该手机号已被占用"), "")
|
||||
}
|
||||
|
||||
type RegisterByInviteCodeLogic struct {
|
||||
logx.Logger
|
||||
ctx context.Context
|
||||
@@ -48,8 +80,12 @@ func (l *RegisterByInviteCodeLogic) RegisterByInviteCode(req *types.RegisterByIn
|
||||
}
|
||||
l.Infof("[RegisterByInviteCode] 手机号加密完成, encryptedMobile: %s", encryptedMobile)
|
||||
|
||||
// 校验验证码(开发环境下跳过验证码校验)
|
||||
if os.Getenv("ENV") != "development" && req.Code != "143838" {
|
||||
// 校验验证码:开发环境跳过;审核预留号段 + 固定码走专用通道;其余走 Redis
|
||||
if os.Getenv("ENV") == "development" {
|
||||
l.Infof("[RegisterByInviteCode] 开发环境跳过验证码校验")
|
||||
} else if reviewphone.IsAppReviewDemoMobile(req.Mobile) && req.Code == reviewphone.DemoVerifyCode {
|
||||
l.Infof("[RegisterByInviteCode] 审核体验号段固定验证码通过, mobile: %s", req.Mobile)
|
||||
} else {
|
||||
redisKey := fmt.Sprintf("%s:%s", "agentApply", encryptedMobile)
|
||||
cacheCode, err := l.svcCtx.Redis.Get(redisKey)
|
||||
if err != nil {
|
||||
@@ -64,8 +100,6 @@ func (l *RegisterByInviteCodeLogic) RegisterByInviteCode(req *types.RegisterByIn
|
||||
return nil, errors.Wrapf(xerr.NewErrMsg("验证码不正确"), "")
|
||||
}
|
||||
l.Infof("[RegisterByInviteCode] 验证码校验通过, mobile: %s", req.Mobile)
|
||||
} else {
|
||||
l.Infof("[RegisterByInviteCode] 开发环境跳过验证码校验")
|
||||
}
|
||||
|
||||
// 获取当前登录态(可能为空)
|
||||
@@ -471,14 +505,8 @@ func (l *RegisterByInviteCodeLogic) handleMobileNotExists(ctx context.Context, s
|
||||
return "", errors.Wrapf(xerr.NewErrCode(xerr.DB_ERROR), "创建用户失败: %v", err)
|
||||
}
|
||||
l.Infof("[handleMobileNotExists] 用户创建成功, userId: %s", newUser.Id)
|
||||
// 创建 mobile 认证
|
||||
if _, err := l.svcCtx.UserAuthModel.Insert(ctx, session, &model.UserAuth{
|
||||
Id: uuid.NewString(),
|
||||
UserId: newUser.Id,
|
||||
AuthType: model.UserAuthTypeMobile,
|
||||
AuthKey: encryptedMobile,
|
||||
}); err != nil {
|
||||
return "", errors.Wrapf(xerr.NewErrCode(xerr.DB_ERROR), "创建手机号认证失败: %v", err)
|
||||
if err := l.insertMobileUserAuthOrSkip(ctx, session, newUser.Id, encryptedMobile); err != nil {
|
||||
return "", errors.Wrap(err, "创建手机号认证失败")
|
||||
}
|
||||
l.Infof("[handleMobileNotExists] 手机号认证创建成功, userId: %s", newUser.Id)
|
||||
return newUser.Id, nil
|
||||
@@ -496,14 +524,8 @@ func (l *RegisterByInviteCodeLogic) handleMobileNotExists(ctx context.Context, s
|
||||
return "", errors.Wrapf(xerr.NewErrCode(xerr.DB_ERROR), "更新手机号失败: %v", err)
|
||||
}
|
||||
l.Infof("[handleMobileNotExists] 用户升级为正式用户成功, userId: %s", currentUserID)
|
||||
// 创建 mobile 认证
|
||||
if _, err := l.svcCtx.UserAuthModel.Insert(ctx, session, &model.UserAuth{
|
||||
Id: uuid.NewString(),
|
||||
UserId: currentUserID,
|
||||
AuthType: model.UserAuthTypeMobile,
|
||||
AuthKey: encryptedMobile,
|
||||
}); err != nil {
|
||||
return "", errors.Wrapf(xerr.NewErrCode(xerr.DB_ERROR), "创建手机号认证失败: %v", err)
|
||||
if err := l.insertMobileUserAuthOrSkip(ctx, session, currentUserID, encryptedMobile); err != nil {
|
||||
return "", errors.Wrap(err, "创建手机号认证失败")
|
||||
}
|
||||
l.Infof("[handleMobileNotExists] 手机号认证创建成功, userId: %s", currentUserID)
|
||||
return currentUserID, nil
|
||||
|
||||
Reference in New Issue
Block a user