feat: 增强短信服务功能,添加验证码相关错误处理和国际化文本支持,更新错误码以改善用户体验

This commit is contained in:
wood911010 committed 2026-01-12 19:54:00 +08:00
1 parent d2423f3705
commit 7062b9f1e8
5 files changed
+94 -13

No files matched your search

+4
View File
@@ -69,6 +69,10 @@ errors:
"500011": "Invalid authentication token"
"500012": "Authentication token expired"
"500013": "Failed to generate token"
"500014": "Verification code incorrect or expired"
"500015": "Verification code does not exist"
"500016": "SMS sending too frequent, please try again later"
"500017": "SMS sending failed"
# Package order module (60xxxx)
cu_package:
+4
View File
@@ -69,6 +69,10 @@ errors:
"500011": "認証トークンが無効です"
"500012": "認証トークンが期限切れです"
"500013": "トークン生成に失敗しました"
"500014": "認証コードが正しくないか期限切れです"
"500015": "認証コードが存在しません"
"500016": "SMS送信が頻繁すぎます。しばらくしてからお試しください"
"500017": "SMS送信に失敗しました"
# セット料金モジュール (60xxxx)
cu_package:
+4
View File
@@ -69,6 +69,10 @@ errors:
"500011": "认证令牌无效"
"500012": "认证令牌已过期"
"500013": "令牌生成失败"
"500014": "验证码错误或已过期"
"500015": "验证码不存在"
"500016": "短信发送过于频繁,请稍后再试"
"500017": "短信发送失败"
# 套餐订单模块 (60xxxx)
cu_package:
+68 -9
View File
@@ -169,10 +169,17 @@ func (s *cuUserService) Login(ctx context.Context, req *models.CuUserLoginReques
// 验证短信验证码
valid, err := s.smsService.VerifyCode(ctx, req.Phone, phoneCountryCode, req.SmsCode)
if err != nil {
return nil, "", i18n.NewI18nError("900004", lang, err.Error())
switch err {
case utils.ErrSMSCodeNotExist:
return nil, "", i18n.NewI18nError("500015", lang) // 验证码不存在
case utils.ErrSMSCodeIncorrect:
return nil, "", i18n.NewI18nError("500014", lang) // 验证码错误或已过期
default:
return nil, "", i18n.NewI18nError("900004", lang, err.Error())
}
}
if !valid {
return nil, "", i18n.NewI18nError("500003", lang) // 验证码错误
return nil, "", i18n.NewI18nError("500014", lang) // 验证码错误或已过期
}
} else {
// 密码登录(默认行为)
@@ -432,7 +439,14 @@ func (s *cuUserService) sendSmsCode(ctx context.Context, phone, phoneCountryCode
}
if sendErr != nil {
return i18n.NewI18nError("200004", lang) // 短信发送失败
switch sendErr {
case utils.ErrSMSRateLimited:
return i18n.NewI18nError("500016", lang) // 短信发送过于频繁,请稍后再试
case utils.ErrSMSSendFailed:
return i18n.NewI18nError("500017", lang) // 短信发送失败
default:
return i18n.NewI18nError("200004", lang) // 短信发送失败
}
}
return nil
@@ -479,7 +493,14 @@ func (s *cuUserService) SendCurrentPhoneSms(ctx context.Context, userID string)
// 发送当前手机号验证码
err = s.smsService.SendCurrentPhoneCode(ctx, user.Phone, user.PhoneCountryCode)
if err != nil {
return i18n.NewI18nError("200004", lang) // 短信发送失败
switch err {
case utils.ErrSMSRateLimited:
return i18n.NewI18nError("500016", lang) // 短信发送过于频繁,请稍后再试
case utils.ErrSMSSendFailed:
return i18n.NewI18nError("500017", lang) // 短信发送失败
default:
return i18n.NewI18nError("200004", lang) // 短信发送失败
}
}
return nil
@@ -511,18 +532,49 @@ func (s *cuUserService) SendNewPhoneSms(ctx context.Context, req *models.CuUserS
// 发送新手机号验证码
err = s.smsService.SendNewPhoneCode(ctx, req.NewPhone, phoneCountryCode)
if err != nil {
return i18n.NewI18nError("200004", lang) // 短信发送失败
switch err {
case utils.ErrSMSRateLimited:
return i18n.NewI18nError("500016", lang) // 短信发送过于频繁,请稍后再试
case utils.ErrSMSSendFailed:
return i18n.NewI18nError("500017", lang) // 短信发送失败
default:
return i18n.NewI18nError("200004", lang) // 短信发送失败
}
}
return nil
}
func (s *cuUserService) VerifyRegisterSmsCode(ctx context.Context, phone, phoneCountryCode, code string) (bool, error) {
return s.smsService.VerifyCode(ctx, phone, phoneCountryCode, code)
valid, err := s.smsService.VerifyCode(ctx, phone, phoneCountryCode, code)
if err != nil {
lang := pkgcontext.GetLanguageFromContext(ctx)
switch err {
case utils.ErrSMSCodeNotExist:
return false, i18n.NewI18nError("500015", lang) // 验证码不存在
case utils.ErrSMSCodeIncorrect:
return false, i18n.NewI18nError("500014", lang) // 验证码错误或已过期
default:
return false, i18n.NewI18nError("900004", lang, err.Error())
}
}
return valid, nil
}
func (s *cuUserService) VerifyPhoneCode(ctx context.Context, phone, phoneCountryCode, code, templateType string) (bool, error) {
return s.smsService.VerifyCode(ctx, phone, phoneCountryCode, code)
valid, err := s.smsService.VerifyCode(ctx, phone, phoneCountryCode, code)
if err != nil {
lang := pkgcontext.GetLanguageFromContext(ctx)
switch err {
case utils.ErrSMSCodeNotExist:
return false, i18n.NewI18nError("500015", lang) // 验证码不存在
case utils.ErrSMSCodeIncorrect:
return false, i18n.NewI18nError("500014", lang) // 验证码错误或已过期
default:
return false, i18n.NewI18nError("900004", lang, err.Error())
}
}
return valid, nil
}
func (s *cuUserService) ForgotPassword(ctx context.Context, req *models.CuUserForgotPasswordRequest) error {
@@ -567,10 +619,17 @@ func (s *cuUserService) ResetPassword(ctx context.Context, req *models.CuUserRes
// 验证短信验证码
valid, err := s.smsService.VerifyCode(ctx, req.Phone, phoneCountryCode, req.SmsCode)
if err != nil {
return i18n.NewI18nError("900004", lang, err.Error())
switch err {
case utils.ErrSMSCodeNotExist:
return i18n.NewI18nError("500015", lang) // 验证码不存在
case utils.ErrSMSCodeIncorrect:
return i18n.NewI18nError("500014", lang) // 验证码错误或已过期
default:
return i18n.NewI18nError("900004", lang, err.Error())
}
}
if !valid {
return i18n.NewI18nError("500012", lang) // 验证码错误或已过期
return i18n.NewI18nError("500014", lang) // 验证码错误或已过期
}
// 生成新密码哈希
+14 -4
View File
@@ -2,6 +2,7 @@ package utils
import (
"context"
"errors"
"fmt"
"math/rand"
"time"
@@ -15,6 +16,15 @@ import (
"github.com/alibabacloud-go/tea/tea"
)
// 短信相关错误定义
var (
ErrSMSCodeNotExist = errors.New("sms_code_not_exist")
ErrSMSCodeExpired = errors.New("sms_code_expired")
ErrSMSRateLimited = errors.New("sms_rate_limited")
ErrSMSSendFailed = errors.New("sms_send_failed")
ErrSMSCodeIncorrect = errors.New("sms_code_incorrect")
)
// 默认短信模板常量
const (
DefaultTemplateRegister = "SMS_330275014"
@@ -126,7 +136,7 @@ func createSMSClient(accessKeyID, accessKeySecret, regionID, endpoint string) (i
func (s *smsService) SendVerificationCode(ctx context.Context, phone, phoneCountryCode, templateCode string) error {
// 检查频率限制
if s.IsRateLimited(ctx, phone, phoneCountryCode) {
return fmt.Errorf("request too frequent")
return ErrSMSRateLimited
}
// 生成6位随机验证码
@@ -142,7 +152,7 @@ func (s *smsService) SendVerificationCode(ctx context.Context, phone, phoneCount
err := s.sendSMS(fullPhone, templateCode, code)
if err != nil {
fmt.Printf("Failed to send SMS to %s: %v", fullPhone, err)
return fmt.Errorf("failed to send SMS: %w", err)
return ErrSMSSendFailed
}
// 缓存验证码
@@ -238,7 +248,7 @@ func (s *smsService) VerifyCode(ctx context.Context, phone, phoneCountryCode, co
storedCode, err := s.cache.Get(ctx, cacheKey)
if err != nil {
if err == cache.ErrCacheMiss {
return false, fmt.Errorf("验证码不存在或已过期")
return false, ErrSMSCodeNotExist
}
return false, err
}
@@ -249,7 +259,7 @@ func (s *smsService) VerifyCode(ctx context.Context, phone, phoneCountryCode, co
return true, nil
}
return false, nil
return false, ErrSMSCodeIncorrect
}
// IsRateLimited 检查是否被频率限制