forked from ebhomengo/niki
55 lines
1.8 KiB
Go
55 lines
1.8 KiB
Go
package benefactorservice
|
|
|
|
import (
|
|
"context"
|
|
"math/rand"
|
|
"time"
|
|
|
|
benefactoreparam "git.gocasts.ir/ebhomengo/niki/param/benefactor/benefactore"
|
|
errmsg "git.gocasts.ir/ebhomengo/niki/pkg/err_msg"
|
|
richerror "git.gocasts.ir/ebhomengo/niki/pkg/rich_error"
|
|
)
|
|
|
|
func (s Service) SendOtp(ctx context.Context, req benefactoreparam.SendOtpRequest) (benefactoreparam.SendOtpResponse, error) {
|
|
const op = "benefactorservice.SendOtp"
|
|
|
|
isExist, iErr := s.redisOtp.IsExistPhoneNumber(ctx, req.PhoneNumber)
|
|
if iErr != nil {
|
|
return benefactoreparam.SendOtpResponse{}, richerror.New(op).WithErr(iErr).WithKind(richerror.KindUnexpected)
|
|
}
|
|
if isExist {
|
|
return benefactoreparam.SendOtpResponse{}, richerror.New(op).WithMessage(errmsg.ErrorMsgOtpCodeExist).WithKind(richerror.KindForbidden)
|
|
}
|
|
|
|
newCode := s.generateVerificationCode()
|
|
spErr := s.redisOtp.SaveCodeWithPhoneNumber(ctx, req.PhoneNumber, newCode, s.config.OtpExpireTime)
|
|
if spErr != nil {
|
|
return benefactoreparam.SendOtpResponse{}, richerror.New(op).WithErr(spErr).WithKind(richerror.KindUnexpected)
|
|
}
|
|
|
|
if isExist {
|
|
// Log error in sms provider
|
|
go s.smsProviderClient.SendForRegisteredUser(req.PhoneNumber, newCode)
|
|
} else {
|
|
// Log error in sms provider
|
|
go s.smsProviderClient.SendForNewUser(req.PhoneNumber, newCode)
|
|
}
|
|
|
|
// we use code in sendOtpResponse until sms provider will implement
|
|
return benefactoreparam.SendOtpResponse{
|
|
PhoneNumber: req.PhoneNumber,
|
|
Code: newCode, // TODO - have to remove it in production
|
|
}, nil
|
|
}
|
|
|
|
func (s Service) generateVerificationCode() string {
|
|
rand.NewSource(time.Now().UnixNano())
|
|
result := make([]byte, s.config.LengthOfOtpCode)
|
|
for i := 0; i < s.config.LengthOfOtpCode; i++ {
|
|
//nolint
|
|
result[i] = s.config.OtpChars[rand.Intn(len(s.config.OtpChars))]
|
|
}
|
|
|
|
return string(result)
|
|
}
|