A login form is meant to let the right person in and keep everyone else out. That second half depends on more than just requiring the correct password, it depends on what happens when the wrong password gets tried, over and over, thousands of times in a row.
Why an unlimited number of attempts is a real problem
If a login form has no limit on failed attempts, an automated script can try common passwords, or a leaked password from an unrelated breach, against an account thousands of times a minute, with nothing stopping it. Given enough attempts, a weak or reused password eventually gets found. The password itself might be fine; the form's willingness to let it be guessed indefinitely is the actual gap.
How to check your own app
- Try logging into a test account with the wrong password, deliberately, five or six times in a row in quick succession.
- See whether anything changes: a delay, a temporary lockout, a CAPTCHA, or any kind of slowdown at all.
- If nothing changes and the form keeps accepting attempts at the same speed indefinitely, that's the gap.
- Check whether the same limit applies to any other place a password or code gets entered: a password-reset flow, a two-factor code, an invite-code field, since these are just as guessable if left unprotected.
Why this gets missed
A login form built and tested by one person, typing their own correct password in each time, never surfaces this gap, because nobody testing it that way ever tries the wrong password enough times to notice nothing is stopping them. The absence only shows up when someone deliberately tries to abuse it, which is exactly what a real attacker eventually does and a normal test pass usually doesn't.
The fix
A reasonable limit, a handful of failed attempts before a short delay or a temporary lockout kicks in, closes most of this off without meaningfully inconveniencing a real user who just mistyped their password once or twice. This applies to every field where guessing a secret value repeatedly could pay off, not just the main login form. It's a small addition, and one of the more common gaps I still find in apps that otherwise look carefully built.