Skip to content

Model: EmailAuthentication

Authenticates a User by email address. Owned by exactly one User; one User may own many.

Fields

Field Type Constraints Notes
Id uuid PK, generated
CreatedAt timestamp with time zone NOT NULL, default now() UTC
Address text NOT NULL, UNIQUE Stored normalized: trimmed, lowercase. The unique constraint applies to the normalized value directly — no citext, no functional index. Application-level normalization at the controller boundary is the contract.
UserId uuid NOT NULL, FK → User.Id ON DELETE RESTRICT, ON UPDATE RESTRICT

Invariants

  • Address is globally unique. One address authenticates one User.
  • Address is stored normalized (lowercase, trimmed, no surrounding whitespace). Inputs are normalized at the controller boundary before any DB lookup or write.
  • The FK to User is RESTRICT on both delete and update — the row must be removed explicitly before deleting the User. (Project policy: no cascade.)

Relationships

  • Many-to-one with User. See User's Relationships section for the FK behavior.

Notes

  • Uniqueness is enforced on the pre-normalized lowercase string — a plain UNIQUE constraint on Address. Per ADR 0004, the database collation is C.UTF-8 (byte-order), so no functional index or citext extension is needed. Normalization (trim + lowercase) happens at the controller boundary; the database is told the truth and indexes the truth.
  • This table holds only the address. Sign-in flows resolve Address → User → PasswordHash; the password lives on User, not here.