passwordpolicy

package
v1.3.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 23, 2026 License: MIT, MIT Imports: 17 Imported by: 0

README

gomodularauth-password-policy

gomodularauth-password-policy provides configurable password-strength, complexity, reuse prevention, and compromised-password detection through Core authentication hooks in GoModularAuth.

Installation

go get github.com/BladiCreator/go-modular-auth/plugins/password-policy

Quick Start


Detailed guide: doc/plugins/password-policy.md.

Documentation

Overview

Package passwordpolicy provides configurable password-strength, complexity, reuse prevention, and compromised-password detection through Core authentication hooks in GoModularAuth.

Index

Constants

View Source
const (
	// EventPolicyValidated is emitted when a candidate password successfully passes all policy checks.
	EventPolicyValidated auth.EventName = "password_policy.validated"

	// EventPolicyViolation is emitted when a password fails policy enforcement.
	EventPolicyViolation auth.EventName = "password_policy.violation"

	// EventHistoryRecorded is emitted when a new password hash is stored in user history.
	EventHistoryRecorded auth.EventName = "password_policy.history_recorded"
)
View Source
const (
	ModelPasswordHistory = "password_history"
)
View Source
const PluginID = "password-policy"

PluginID identifies this plugin in the GoModularAuth runtime.

Variables

View Source
var (
	// ErrPasswordTooShort indicates that the password is shorter than the minimum length requirement.
	ErrPasswordTooShort = errors.New("password-policy: password does not meet minimum length requirement")

	// ErrPasswordTooLong indicates that the password exceeds the maximum allowable length.
	ErrPasswordTooLong = errors.New("password-policy: password exceeds maximum length requirement")

	// ErrPasswordRequiresUppercase indicates that the password must contain at least one uppercase letter.
	ErrPasswordRequiresUppercase = errors.New("password-policy: password requires at least one uppercase letter")

	// ErrPasswordRequiresLowercase indicates that the password must contain at least one lowercase letter.
	ErrPasswordRequiresLowercase = errors.New("password-policy: password requires at least one lowercase letter")

	// ErrPasswordRequiresDigit indicates that the password must contain at least one numeric digit.
	ErrPasswordRequiresDigit = errors.New("password-policy: password requires at least one numeric digit")

	// ErrPasswordRequiresSymbol indicates that the password must contain at least one special symbol.
	ErrPasswordRequiresSymbol = errors.New("password-policy: password requires at least one special symbol")

	// ErrPasswordInHistory indicates that the password matches a recently used password in the user's history.
	ErrPasswordInHistory = errors.New("password-policy: password cannot be a recently used password")

	// ErrPasswordCompromised indicates that the password was found in a list of known compromised or breached passwords.
	ErrPasswordCompromised = errors.New("password-policy: password has been identified as compromised or common")

	// ErrInvalidInput indicates that one or more required input arguments are missing or malformed.
	ErrInvalidInput = errors.New("password-policy: invalid input")

	// ErrUserNotFound indicates that the specified user was not found.
	ErrUserNotFound = errors.New("password-policy: user not found")
)
View Source
var CommonCompromisedPasswords = map[string]struct{}{
	"123456":      {},
	"12345678":    {},
	"123456789":   {},
	"password":    {},
	"password123": {},
	"qwerty":      {},
	"111111":      {},
	"12345":       {},
	"1234567":     {},
	"dragon":      {},
	"welcome":     {},
	"welcome1":    {},
	"welcome123":  {},
	"admin":       {},
	"admin123":    {},
	"letmein":     {},
	"monkey":      {},
	"football":    {},
	"iloveyou":    {},
	"starwars":    {},
	"master":      {},
	"secret":      {},
	"pass1234":    {},
	"changeme":    {},
	"trustno1":    {},
	"sunshine":    {},
	"princess":    {},
	"superman":    {},
	"batman":      {},
	"charlie":     {},
	"donald":      {},
	"jordan":      {},
	"harley":      {},
	"michelle":    {},
	"shadow":      {},
	"hunter2":     {},
}

CommonCompromisedPasswords contains universally known weak, leaked, and default passwords.

Functions

func DefaultCompromisedChecker

func DefaultCompromisedChecker(_ context.Context, password string) (bool, error)

DefaultCompromisedChecker checks if the candidate password exists in CommonCompromisedPasswords.

func RegisterSchema

func RegisterSchema(s *schema.Schema) error

RegisterSchema registers the password history model in the compiled schema.

Types

type ChangePasswordInput

type ChangePasswordInput struct {
	UserID            string `json:"user_id"`
	CurrentPassword   string `json:"current_password"`
	NewPassword       string `json:"new_password"`
	CurrentSessionID  string `json:"current_session_id,omitempty"`
	KeepOtherSessions bool   `json:"keep_other_sessions,omitempty"`
}

ChangePasswordInput specifies parameters for policy-enforced password change.

type CompromisedChecker

type CompromisedChecker func(ctx context.Context, password string) (bool, error)

CompromisedChecker defines a function that checks whether a password is known to be breached or common.

type Config

type Config struct {
	// Policy defines the active password strength, complexity, history, and compromised rules.
	Policy Policy

	// CompromisedChecker overrides the default compromised passwords checker if non-nil.
	CompromisedChecker CompromisedChecker

	// Hasher provides password hashing verification for history comparison.
	// Reuses Core's Argon2id hasher by default.
	Hasher password.Hasher

	// EnforceOnSignUp controls whether the BeforeSignUp hook validates passwords. Defaults to true.
	EnforceOnSignUp bool

	// Clock provides time abstraction for deterministic testing. Defaults to time.Now().UTC.
	Clock func() time.Time
}

Config holds configuration parameters for the Password Policy plugin.

type HistoryRecordedPayload

type HistoryRecordedPayload struct {
	UserID    string    `json:"user_id"`
	HistoryID string    `json:"history_id"`
	Timestamp time.Time `json:"timestamp"`
}

HistoryRecordedPayload carries audit details when a password hash is preserved in history.

type Module

type Module struct {
	// contains filtered or unexported fields
}

Module implements auth.PluginModule using plugin-sdk and wires hooks.

func New

func New(opts ...Option) *Module

New creates an installable Password Policy PluginModule with optional configurations.

func (*Module) ID

func (m *Module) ID() string

ID returns the module's unique identifier.

func (*Module) Init

func (m *Module) Init(h *auth.Host) error

Init configures infrastructure, attaches Core authentication hooks, and registers the capability.

func (*Module) RegisterSchema

func (m *Module) RegisterSchema(s *schema.Schema) error

RegisterSchema registers the password history model in the compiled schema.

type Option

type Option func(*Config)

Option configures Config.

func WithClock

func WithClock(clock func() time.Time) Option

WithClock sets a custom clock function.

func WithComplexity

func WithComplexity(upper, lower, digit, symbol bool) Option

WithComplexity sets complexity requirements.

func WithCompromisedChecker

func WithCompromisedChecker(checker CompromisedChecker) Option

WithCompromisedChecker configures a custom checker for compromised passwords.

func WithEnforceOnSignUp

func WithEnforceOnSignUp(enforce bool) Option

WithEnforceOnSignUp configures whether the BeforeSignUp hook validates passwords.

func WithHasher

func WithHasher(hasher password.Hasher) Option

WithHasher configures the password hasher to reuse from Core.

func WithHistoryCount

func WithHistoryCount(count int) Option

WithHistoryCount sets the number of past passwords to remember and prevent reuse.

func WithMaxLength

func WithMaxLength(max int) Option

WithMaxLength sets the maximum password length.

func WithMinLength

func WithMinLength(min int) Option

WithMinLength sets the minimum password length.

func WithPolicy

func WithPolicy(p Policy) Option

WithPolicy sets the complete password policy.

func WithRejectCompromised

func WithRejectCompromised(reject bool) Option

WithRejectCompromised sets whether compromised passwords should be rejected.

type PasswordHistory

type PasswordHistory struct {
	ID           string    `json:"id"`
	UserID       string    `json:"user_id"`
	PasswordHash string    `json:"password_hash"`
	CreatedAt    time.Time `json:"created_at"`
}

PasswordHistory records a historical password hash for reuse prevention.

type PasswordPolicy

type PasswordPolicy interface {
	// ValidatePassword evaluates a candidate password against the configured policy.
	// If userID is provided (non-empty), it also evaluates password reuse against history.
	ValidatePassword(ctx context.Context, password string, userID string) error

	// ValidatePasswordDetailed evaluates a candidate password and returns a structured
	// list of specific violation codes (e.g. "min_length", "complexity_uppercase", "compromised").
	ValidatePasswordDetailed(ctx context.Context, password string, userID string) (*ValidationResult, error)

	// ChangePassword enforces policy and history reuse prevention, executes Core ChangePassword,
	// and records the new password hash into history.
	ChangePassword(ctx context.Context, in ChangePasswordInput) error

	// ResetPassword enforces policy and history reuse prevention, executes Core ResetPassword,
	// and records the new password hash into history.
	ResetPassword(ctx context.Context, in ResetPasswordInput) error

	// RecordHistory adds a password hash into the user's password history and prunes old records.
	RecordHistory(ctx context.Context, userID, hash string) error

	// GetHistory retrieves historical password records for a user up to limit.
	GetHistory(ctx context.Context, userID string, limit int) ([]*PasswordHistory, error)

	// ClearHistory removes all historical password records for a user.
	ClearHistory(ctx context.Context, userID string) error

	// GetPolicy returns the currently active policy configuration.
	GetPolicy() Policy
}

PasswordPolicy defines the capability exposed by the password policy plugin. Applications retrieve this capability via:

policyPlugin, err := auth.Get[plugins.PasswordPolicy](engine)
// or
policyPlugin, err := auth.Get[passwordpolicy.PasswordPolicy](engine)

type Policy

type Policy struct {
	// MinLength specifies the minimum number of characters required. Defaults to 8.
	MinLength int `json:"min_length"`

	// MaxLength specifies the maximum number of characters permitted. Defaults to 128.
	MaxLength int `json:"max_length"`

	// RequireUppercase requires at least one uppercase letter (A-Z).
	RequireUppercase bool `json:"require_uppercase"`

	// RequireLowercase requires at least one lowercase letter (a-z).
	RequireLowercase bool `json:"require_lowercase"`

	// RequireDigit requires at least one numeric digit (0-9).
	RequireDigit bool `json:"require_digit"`

	// RequireSymbol requires at least one special punctuation/symbol character.
	RequireSymbol bool `json:"require_symbol"`

	// HistoryCount specifies how many past passwords to check against reuse. If 0, history check is disabled.
	HistoryCount int `json:"history_count"`

	// RejectCompromised enables checking against known breached or weak passwords.
	RejectCompromised bool `json:"reject_compromised"`
}

Policy specifies password strength, complexity, history, and compromised checks.

func DefaultPolicy

func DefaultPolicy() Policy

DefaultPolicy returns a recommended baseline security policy.

type PolicyValidatedPayload

type PolicyValidatedPayload struct {
	UserID    string    `json:"user_id,omitempty"`
	Timestamp time.Time `json:"timestamp"`
}

PolicyValidatedPayload carries audit details for successful validations.

type PolicyViolationPayload

type PolicyViolationPayload struct {
	UserID     string    `json:"user_id,omitempty"`
	Violations []string  `json:"violations"`
	Timestamp  time.Time `json:"timestamp"`
}

PolicyViolationPayload carries audit details for policy violations.

type ResetPasswordInput

type ResetPasswordInput struct {
	Token       string `json:"token"`
	NewPassword string `json:"new_password"`
}

ResetPasswordInput specifies parameters for policy-enforced password reset.

type ValidationResult

type ValidationResult struct {
	Valid      bool     `json:"valid"`
	Violations []string `json:"violations,omitempty"`
	Error      error    `json:"-"`
}

ValidationResult carries detailed status of a password policy evaluation.

Directories

Path Synopsis
Package migrations embeds SQL migrations for the Password Policy plugin.
Package migrations embeds SQL migrations for the Password Policy plugin.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL