Broken Authentication Explained: When Login Security Fails

Share

TL;DR

Broken authentication covers any weakness in login and session management. Common issues include weak password policies, missing rate limiting, insecure password storage, and predictable session tokens. For most apps, use established auth providers (Clerk, Auth0, Supabase Auth) instead of building your own. If you must build auth, hash passwords with bcrypt, implement rate limiting, and use secure session management.

What Is Broken Authentication?

Broken authentication is a category of vulnerabilities that affect how users log in and stay logged in. When authentication is broken, attackers can:

  • Guess or brute-force passwords without rate limiting
  • Steal or hijack session tokens
  • Bypass authentication entirely
  • Take over accounts through password reset flaws
  • Access accounts through credential stuffing (using leaked passwords)

Common Authentication Vulnerabilities

1. Weak Password Storage

DANGEROUS: Storing passwords wrong
// CRITICAL VULNERABILITY: Plain text passwords
const user = await db.user.create({
  data: { email, password }  // Password stored as-is!
});

// WRONG: Using weak hashing
const hash = crypto.createHash('md5').update(password).digest('hex');

// WRONG: Missing salt
const hash = crypto.createHash('sha256').update(password).digest('hex');
SECURE: Proper password hashing
import bcrypt from 'bcrypt';

// Hashing a password (on signup)
const saltRounds = 12;
const hashedPassword = await bcrypt.hash(password, saltRounds);

// Verifying a password (on login)
const isValid = await bcrypt.compare(password, user.hashedPassword);

2. No Rate Limiting

Without rate limiting, attackers can try thousands of passwords:

Vulnerable endpoint
// Attacker can send unlimited login attempts
app.post('/api/login', async (req, res) => {
  const { email, password } = req.body;
  const user = await authenticate(email, password);
  // No rate limiting = brute force attacks work
});
Protected with rate limiting
import rateLimit from 'express-rate-limit';

const loginLimiter = rateLimit({
  windowMs: 15 * 60 * 1000, // 15 minutes
  max: 5, // 5 attempts per window
  message: 'Too many login attempts, please try again later',
  standardHeaders: true,
  legacyHeaders: false,
});

app.post('/api/login', loginLimiter, async (req, res) => {
  // Now protected against brute force
});

3. Insecure Session Management

VulnerabilityProblemFix
Predictable session IDsAttackers can guess valid sessionsUse cryptographically random IDs
Session in URLToken leaked in browser history, referrerUse HttpOnly cookies
No session expirationStolen sessions work foreverSet reasonable expiration times
Session not invalidated on logoutOld sessions still workDestroy session server-side on logout

4. Insecure Password Reset

Vulnerable password reset
// VULNERABLE: Predictable reset tokens
const resetToken = Date.now().toString();
const resetUrl = `/reset?token=${resetToken}`;

// VULNERABLE: No expiration
await db.passwordReset.create({
  data: { userId: user.id, token: resetToken }
  // Missing: expiresAt field
});

// VULNERABLE: Token not invalidated after use
// User could reuse the same reset link
Secure password reset
import crypto from 'crypto';

// Generate secure random token
const resetToken = crypto.randomBytes(32).toString('hex');
const tokenHash = crypto.createHash('sha256').update(resetToken).digest('hex');

// Store hashed token with expiration
await db.passwordReset.create({
  data: {
    userId: user.id,
    tokenHash,
    expiresAt: new Date(Date.now() + 3600000) // 1 hour
  }
});

// After password reset, delete the token
await db.passwordReset.delete({ where: { tokenHash } });

Authentication in AI-Generated Code

AI assistants frequently generate authentication code with critical vulnerabilities:

Common AI auth mistakes: Plain text passwords, hardcoded secrets, missing rate limiting, JWT tokens without expiration, predictable session IDs, and no CSRF protection on login forms.

What AI might generate
// AI often generates vulnerable auth patterns
app.post('/login', async (req, res) => {
  const user = await db.user.findFirst({
    where: {
      email: req.body.email,
      password: req.body.password  // Plain text comparison!
    }
  });

  if (user) {
    res.cookie('userId', user.id);  // Insecure cookie!
    res.json({ success: true });
  }
});

Better Approach: Use Auth Providers

For most applications, using established authentication services is safer:

ProviderBest ForFeatures
ClerkNext.js apps, fast setupPre-built components, MFA, social login
Auth0Enterprise, complex requirementsSSO, compliance features, custom rules
Supabase AuthFull-stack with SupabaseRow-level security integration, social login
NextAuth.jsSelf-hosted, flexibleMany providers, database sessions

Auth providers handle: Password hashing, secure sessions, rate limiting, MFA, password reset flows, social login, and security updates. This lets you focus on your app instead of security implementation.

What is broken authentication?

Broken authentication refers to weaknesses in login and session management that let attackers compromise passwords, keys, or session tokens. This can lead to account takeover, unauthorized access, or identity impersonation.

Should I build my own authentication system?

For most applications, using established authentication providers like Clerk, Auth0, or NextAuth is safer than building your own. These services handle security complexities like password hashing, session management, and brute force protection.

Is storing passwords in plain text really that bad?

Yes, it's critical. If your database is breached, attackers get everyone's passwords immediately. Since users reuse passwords, this often leads to account compromises on other sites. Always hash passwords with bcrypt, argon2, or scrypt.

What's the difference between authentication and authorization?

Authentication verifies who you are (login). Authorization determines what you can do (permissions). Both are important: broken authentication lets attackers log in; broken authorization lets logged-in users access things they shouldn't.

Check Your Authentication Security

Our scanner tests your login system for common vulnerabilities.

Start Free Scan
Vulnerability Guides

Broken Authentication Explained: When Login Security Fails