otp validation is added

This commit is contained in:
kemvl 2024-03-28 00:28:21 +05:00
parent 6054f8bf0f
commit ecba78e8cc
8 changed files with 74 additions and 9 deletions

View File

@ -39,3 +39,24 @@ func (h *OTPHandler) GenerateAndSaveOTPHandler(w http.ResponseWriter, r *http.Re
w.WriteHeader(http.StatusOK) w.WriteHeader(http.StatusOK)
} }
func (h *OTPHandler) ValidateOTPHandler(w http.ResponseWriter, r *http.Request) {
decoder := json.NewDecoder(r.Body)
var request struct {
PhoneNumber string `json:"phone_number"`
OTP string `json:"otp"`
}
err := decoder.Decode(&request)
if err != nil {
utils.RespondWithErrorJSON(w, http.StatusBadRequest, "Invalid request payload")
return
}
err = h.Service.ValidateOTP(request.PhoneNumber, request.OTP)
if err != nil {
utils.RespondWithErrorJSON(w, http.StatusBadRequest, err.Error())
return
}
utils.RespondWithJSON(w, http.StatusOK, "OTP validated successfully")
}

View File

@ -14,6 +14,7 @@ func SetupOTPRoutes(otpService service.OTPService, logger *logger.Loggers) http.
otpHandler := handlers.NewOTPHandler(otpService) otpHandler := handlers.NewOTPHandler(otpService)
otpRouter.Post("/sendOTP", otpHandler.GenerateAndSaveOTPHandler) otpRouter.Post("/sendOTP", otpHandler.GenerateAndSaveOTPHandler)
otpRouter.Post("/validateOTP", otpHandler.ValidateOTPHandler)
return otpRouter return otpRouter
} }

View File

@ -1,5 +1,9 @@
package repository package repository
import "time"
type OTPRepository interface { type OTPRepository interface {
SaveOTP(phoneNumber string, otp string) error SaveOTP(phoneNumber string, otp string) error
GetOTP(phoneNumber string) (string, error)
GetOTPTimestamp(phoneNumber string) (time.Time, error)
} }

View File

@ -28,17 +28,30 @@ func GenerateOTP() string {
} }
func (r *OTPRepository) SaveOTP(phoneNumber string, otp string) error { func (r *OTPRepository) SaveOTP(phoneNumber string, otp string) error {
err := r.Client.Watch(func(tx *redis.Tx) error { err := r.Client.Set(phoneNumber, otp, 5*time.Minute).Err()
err := tx.Set(phoneNumber, otp, 0).Err()
if err != nil { if err != nil {
r.logger.ErrorLogger.Error("Error setting up values into redis: %v", err) r.logger.ErrorLogger.Error("Error setting up values into redis: %v", err)
return err return err
} }
return nil return nil
}, phoneNumber) }
func (r *OTPRepository) GetOTP(phoneNumber string) (string, error) {
otp, err := r.Client.Get(phoneNumber).Result()
if err != nil { if err != nil {
return err return "", err
} }
return nil return otp, nil
}
func (r *OTPRepository) GetOTPTimestamp(phoneNumber string) (time.Time, error) {
timestamp, err := r.Client.Get(phoneNumber + ":timestamp").Result()
if err != nil {
return time.Time{}, err
}
t, err := time.Parse(time.RFC3339, timestamp)
if err != nil {
return time.Time{}, err
}
return t, nil
} }

View File

@ -6,4 +6,5 @@ import (
type OTPService interface { type OTPService interface {
GenerateAndSendOTP(cfg config.Config, phoneNumber string) error GenerateAndSendOTP(cfg config.Config, phoneNumber string) error
ValidateOTP(phoneNumber string, otp string) error
} }

View File

@ -32,3 +32,20 @@ func (s *OTPService) GenerateAndSaveOTP(phoneNumber string) error {
} }
return nil return nil
} }
func (s *OTPService) ValidateOTP(phoneNumber string, otp string) error {
storedOTP, err := s.repository.GetOTP(phoneNumber)
if err != nil {
if err.Error() == "redis: nil" {
return fmt.Errorf("OTP not found or expired")
}
s.logger.ErrorLogger.Error("Error retrieving OTP from repository: %v", err)
return err
}
if storedOTP != otp {
return fmt.Errorf("OTP does not match")
}
return nil
}

View File

@ -0,0 +1,3 @@
time=2024-03-28T00:07:01.216+05:00 level=ERROR msg="Error retrieving OTP timestamp from repository: %v" !BADKEY="redis: nil"
time=2024-03-28T00:09:57.336+05:00 level=ERROR msg="Error retrieving OTP timestamp from repository: %v" !BADKEY="redis: nil"
time=2024-03-28T00:19:15.421+05:00 level=ERROR msg="Error retrieving OTP timestamp from repository: %v" !BADKEY="redis: nil"

View File

@ -2,3 +2,8 @@ time=2024-03-27T23:24:15.715+05:00 level=INFO msg="Shutting down the server grac
time=2024-03-27T23:31:35.765+05:00 level=INFO msg="Shutting down the server gracefully..." time=2024-03-27T23:31:35.765+05:00 level=INFO msg="Shutting down the server gracefully..."
time=2024-03-27T23:39:10.332+05:00 level=INFO msg="Server is up and running" time=2024-03-27T23:39:10.332+05:00 level=INFO msg="Server is up and running"
time=2024-03-27T23:39:22.414+05:00 level=INFO msg="Shutting down the server gracefully..." time=2024-03-27T23:39:22.414+05:00 level=INFO msg="Shutting down the server gracefully..."
time=2024-03-28T00:06:29.253+05:00 level=INFO msg="Server is up and running"
time=2024-03-28T00:18:28.728+05:00 level=INFO msg="Shutting down the server gracefully..."
time=2024-03-28T00:18:31.350+05:00 level=INFO msg="Server is up and running"
time=2024-03-28T00:20:32.122+05:00 level=INFO msg="Shutting down the server gracefully..."
time=2024-03-28T00:20:34.708+05:00 level=INFO msg="Server is up and running"