Skip to content

Why Sentinel Password? ​

The Problem ​

Password validation is a critical part of user authentication, but implementing it properly is surprisingly complex:

  • Inconsistent Standards: Every app has different password requirements
  • Poor User Experience: Cryptic error messages frustrate users
  • Accessibility Issues: Many password validators fail WCAG compliance
  • Bundle Size: Heavy libraries slow down your app
  • Rigid Implementations: Hard to customize for your specific needs

Our Solution ​

Sentinel Password provides a flexible, accessible, and lightweight solution for password validation:

🎯 Flexible & Configurable ​

Unlike rigid password validators, Sentinel Password lets you define exactly what makes a valid password for your application:

typescript
// Enterprise app with strict requirements
const strictConfig = {
  minLength: 16,
  maxLength: 128,
  requireUppercase: true,
  requireLowercase: true,
  requireDigit: true,
  requireSymbol: true,
  // checkCommonPasswords and checkKeyboardPatterns default to true
}

// Consumer app with balanced requirements
const balancedConfig = {
  minLength: 8,
  requireDigit: true,
}

β™Ώ Accessibility First ​

PasswordInput is designed to meet WCAG 2.1 AAA. The component provides:

  • βœ… Semantic HTML with a useId()-linked <label>
  • βœ… ARIA attributes managed for you (aria-invalid, aria-describedby, aria-pressed on the toggle)
  • βœ… Live region (role="alert" aria-live="polite") for validation announcements
  • βœ… Keyboard support (Tab, Escape to clear, Space/Enter on toggle)
  • βœ… Focus management for the component's own elements

Page-level conformance is the consumer's responsibility β€” contrast (AAA wants 7:1), surrounding markup, reduced-motion/forced-colors/focus-visible CSS, and localization of the bundled English toggle text. See the Accessibility guide for the full split and the known gaps.

πŸ“¦ Tiny Bundle Size ​

Core package is ~5.5 KB gzipped with zero dependencies (CI fails if it exceeds 10 KB):

PackageSize (gzipped)Dependencies
@sentinel-password/core~5.5 KBZero
@sentinel-password/react~0.7 KB@sentinel-password/core (runtime, installed transitively); React 18/19 (peer)
@sentinel-password/react-components~1.7 KB@sentinel-password/core (runtime, installed transitively); React 18/19 and React DOM 18/19 (peers)
@sentinel-password/entropy (optional)~28 KBZero

Compare this to popular alternatives that can be 50KB+ with dozens of dependencies. The optional entropy package is intentionally separate so consumers only pay for it when they want crack-time estimation β€” zxcvbn ships ~400 KB unconditionally.

🎨 Headless Architecture ​

React components are completely unstyled, giving you full design control:

tsx
<PasswordInput
  label="Password"
  containerClassName="my-input-wrapper"
  className="my-custom-input"
  labelClassName="my-custom-label"
  validationClassName="my-custom-error"
/>

Style it with CSS, Tailwind, CSS-in-JS, or any styling solution you prefer.

🌍 Pluggable i18n ​

Pass messages (template map keyed by stable MessageCode) or formatMessage (callback) to localize validator output β€” no manual lookup-table needed:

typescript
import { validatePassword, type MessageCode } from '@sentinel-password/core'

// Pattern 1 β€” template overrides
const result = validatePassword('weak', {
  messages: {
    'length.tooShort': 'La contraseΓ±a debe tener al menos {minLength} caracteres',
  } satisfies Partial<Record<MessageCode, string>>,
})

// Pattern 2 β€” plug into react-intl / i18next / FormatJS
validatePassword('weak', {
  formatMessage: (code, params, defaultMessage) =>
    intl.formatMessage({ id: `sentinelPassword.${code}`, defaultMessage }, params),
})

The legacy lookup-table workaround still works (default English strings are stable), but new code should prefer the explicit options above. See the i18n guide for full coverage.

πŸ”’ Security Focused ​

Helps users create stronger passwords by checking for:

  • βœ… Common passwords (top 1,000 most common passwords, O(1) Bloom-filter lookup)
  • βœ… Keyboard patterns (qwerty, asdfgh)
  • βœ… Sequential characters (abc123, 987654)
  • βœ… Repetitive patterns (aaaaaa, 111111)
  • βœ… Personal information (name, email)

⚑ Framework Agnostic ​

Use the core package with any framework:

typescript
// Vue
import { ref, computed } from 'vue'
import { validatePassword } from '@sentinel-password/core'

const password = ref('')
const validation = computed(() => 
  validatePassword(password.value, config)
)

// Angular
import { validatePassword } from '@sentinel-password/core'

validatePassword(this.passwordControl.value, config)

// Svelte
import { validatePassword } from '@sentinel-password/core'

$: validation = validatePassword(password, config)

✨ TypeScript First ​

Written in TypeScript with comprehensive type definitions:

typescript
import type {
  ValidationResult,
  ValidatorOptions,
  StrengthScore,
  StrengthLabel,
} from '@sentinel-password/core'

// Full IntelliSense and type checking
const options: ValidatorOptions = {
  minLength: 8, // TypeScript knows all available options
  requireUppercase: true,
}

Comparison ​

FeatureSentinel PasswordTraditional RegexOther Libraries
Bundle Size~5.5 KBN/A20-100KB+
Dependencies005-50+
AccessibilityDesigned for AAA❌Varies
Customizableβœ… Full control⚠️ Limited⚠️ Partial
React Supportβœ… Native hooks❌⚠️ Varies
TypeScriptβœ… Full typesN/A⚠️ Varies
Common Password Checkβœ…βŒβš οΈ Sometimes
Pattern Detectionβœ…βŒβš οΈ Sometimes

Real-World Benefits ​

Better User Experience ​

Clear, actionable error messages help users succeed:

typescript
// ❌ Bad: "Password invalid"
// βœ… Good: "Password must be at least 8 characters long"

Reduced Support Burden ​

Users understand password requirements upfront, reducing support tickets.

Improved Security ​

Pattern detection and common password checks help users create stronger passwords.

Faster Development ​

Pre-built components and hooks save development time:

tsx
// Instead of building from scratch...
import { PasswordInput } from '@sentinel-password/react-components'

// Just use it!
<PasswordInput label="Password" />

Get Started ​

Ready to try Sentinel Password?

Released under the MIT License.