Skip to content

Commit

Permalink
fix: otp attempt issue knadh#23
Browse files Browse the repository at this point in the history
  • Loading branch information
abhinavxd committed Jan 27, 2022
1 parent 1031f29 commit e4dbf70
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 14 deletions.
41 changes: 30 additions & 11 deletions cmd/otpgateway/handlers.go
Original file line number Diff line number Diff line change
Expand Up @@ -307,6 +307,15 @@ func handleVerifyOTP(w http.ResponseWriter, r *http.Request) {
return
}

if err == store.ErrTooManyAttempts {
code = http.StatusTooManyRequests
errMsg := fmt.Sprintf("Too many attempts. Please retry after %0.f seconds.",
out.TTL.Seconds())
err := errors.New(errMsg)
sendErrorResponse(w, err.Error(), code, nil)
return
}

if out.Closed {
code = http.StatusTooManyRequests
}
Expand Down Expand Up @@ -349,8 +358,17 @@ func handleOTPView(w http.ResponseWriter, r *http.Request) {
return
}

isOtpLocked := false
// Attempts are maxed out and locked.
if isLocked(out) {
if action == actCheck {
if otpErr == store.ErrTooManyAttempts {
isOtpLocked = true
}
} else if isLocked(out) {
isOtpLocked = true
}

if isOtpLocked {
app.tpl.ExecuteTemplate(w, "message", webviewTpl{App: app.constants,
Title: "Too many attempts",
Description: fmt.Sprintf("Please retry after %d seconds.", int64(out.TTLSeconds)),
Expand Down Expand Up @@ -522,20 +540,21 @@ func verifyOTP(namespace, id, otp string, deleteOnVerify bool, app *App) (models
app.lo.Printf("error checking OTP: %v", err)
return out, err
}
return out, errors.New("error checking OTP.")
return out, errors.New("error checking OTP")
}

errMsg := ""
if isLocked(out) {
errMsg = fmt.Sprintf("Too many attempts. Please retry after %0.f seconds.",
out.TTL.Seconds())
} else if out.OTP != otp {
errMsg = "Incorrect OTP"
// Attempts exceeded for OTP
if out.Attempts > out.MaxAttempts {
return out, store.ErrTooManyAttempts
}

// Final attempt with incorrect OTP
if out.Attempts == out.MaxAttempts && out.OTP != otp {
return out, store.ErrTooManyAttempts
}

// There was an error.
if errMsg != "" {
return out, errors.New(errMsg)
if out.OTP != otp {
return out, errors.New("incorrect OTP")
}

// Delete the OTP?
Expand Down
12 changes: 9 additions & 3 deletions internal/store/store.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,15 @@ import (
"github.com/knadh/otpgateway/v3/internal/models"
)

// ErrNotExist is thrown when an OTP (requested by namespace / ID)
// does not exist.
var ErrNotExist = errors.New("the OTP does not exist")

var (
// ErrNotExist is thrown when an OTP (requested by namespace / ID)
// does not exist.
ErrNotExist = errors.New("the OTP does not exist")
// ErrNotExist is thrown when an OTP (requested by namespace / ID)
// strictly exceeds the maximum number of attempts.
ErrTooManyAttempts = errors.New("too many attempts")
)

// Store represents a storage backend where OTP data is stored.
type Store interface {
Expand Down

0 comments on commit e4dbf70

Please sign in to comment.