obsidian/wiki/payloadcms/authentication-overview.md
2026-05-15 15:13:56 +01:00

4.9 KiB

title aliases tags sources created updated
Authentication — Overview
payload-auth-overview
payload-authentication
payloadcms
authentication
jwt
cookies
api-keys
security
raw/authentication__overview.md
2026-05-15 2026-05-15

What It Is

Payload provides built-in, portable authentication on any Collection — no third-party services needed. Enabling auth on a Collection turns each document into a "user" with a complete login/logout/reset workflow.

Enable Auth on a Collection

// Minimal — all defaults
export const Users: CollectionConfig = {
  slug: 'users',
  auth: true,
}

// With options
export const Admins: CollectionConfig = {
  slug: 'admins',
  auth: {
    tokenExpiration: 7200,      // seconds; applies to both JWT and cookie
    verify: true,               // require email verification
    maxLoginAttempts: 5,        // lock after N failures
    lockTime: 600 * 1000,       // lockout window in ms
  },
}

Auto-injected fields on auth-enabled collections: hash, salt, email.

Config Options Reference

Option Description
cookies Cookie overrides: secure, sameSite, domain
depth Populate depth when binding user to req — default 0, raise only if needed
disableLocalStrategy Remove built-in strategy (only if you've replaced it with a custom one)
forgotPassword Customize forgot-password flow
lockTime Lockout duration (ms) after maxLoginAttempts exceeded
loginWithUsername Allow login with username instead of email
maxLoginAttempts Max failed logins before lockout; 0 = disabled
removeTokenFromResponses Strip token from login/refresh API responses
strategies Array of custom auth strategies
tokenExpiration JWT + cookie expiry in seconds
useAPIKey Enable per-user API keys
useSessions true (default) = session cookies; false = stateless JWTs
verify Email verification before login

Login With Username

auth: {
  loginWithUsername: true,
}

// With fine-grained control:
auth: {
  loginWithUsername: {
    allowEmailLogin: true,   // allow both email and username (default: false)
    requireEmail: false,     // require email on registration (default: false)
  },
}

Auto-Login (Dev Only)

Skip the login screen during development:

admin: {
  autoLogin: process.env.NODE_ENV === 'development'
    ? { email: 'test@example.com', password: 'test', prefillOnly: true }
    : false,
}

prefillOnly: true — credentials pre-filled but user must click Login (safer than full bypass).

Auto-Refresh

Keep sessions alive while the Admin Panel is open:

admin: {
  autoRefresh: true,
}

Built-In Strategies

Strategy Details
HTTP-Only Cookies XSS-proof, invisible to JS — see wiki/payloadcms/authentication-cookies
JWT Authorization header tokens — see wiki/payloadcms/authentication-jwt
API Keys Non-expiring keys for third-party services — see wiki/payloadcms/authentication-api-keys
Custom Plug in your own — see wiki/payloadcms/authentication-custom-strategies

Strategies can be combined or used independently.

Overriding Default Auth Field Access

Redefine email, username, or password fields to apply custom access control:

fields: [
  {
    name: 'email',
    type: 'text',
    access: { create: () => true, read: () => false, update: () => false },
  },
  {
    name: 'password',
    type: 'text',
    hidden: true,              // prevents duplicate field in Admin UI
    access: { update: () => false },
  },
]

Gotcha: disabling read on email/username breaks the Unlock action in Admin panel.

Key Takeaways

  • Enable auth with auth: true or auth: { ... } on any Collection
  • Auto-injected fields: hash, salt, email — no manual setup needed
  • Three built-in strategies: cookies (XSS-safe), JWT (stateless), API keys (third-party)
  • loginWithUsername replaces email login for username-based systems
  • autoLogin should always be gated behind NODE_ENV === 'development'
  • Default depth: 0 on user population — raise only with clear justification
  • Access control on default auth fields (email/password) uses field override pattern

Sources