identitystore

package
v0.44.2 Latest Latest
Warning

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

Go to latest
Published: Sep 25, 2026 License: MIT Imports: 5 Imported by: 0

Documentation

Overview

Package identitystore guarantees that every account has a login name.

Why a store wrapper, and not a line in each caller

Accounts are created from eight places: the admin UI, the grants "invite by e-mail" path, the CLI, first-run seeding, and the OIDC, LDAP and proxy-header drivers doing just-in-time provisioning. A username assigned in seven of them is worse than one assigned in none: the eighth account is the one that cannot log in over SFTP, and nothing about it looks different until someone tries.

What all eight share is db.Store.CreateUser — an account cannot come into existence without it. Wrapping that one method is therefore both complete and future-proof: a creation path added next month gets a username on the day it is written, with no line of its own. This is the pattern internal/quotastore and internal/tenantstore already use, and for the same reason.

⚠ Apply the wrapper immediately above dbDrv.NewStore(), and in the test fixtures too. A single consumer holding the raw store creates accounts nobody named — which is exactly the class of bug quotastore was written to fix.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Backfill

func Backfill(ctx context.Context, s db.Store) (int, error)

Backfill names every account that has none. It runs at start-up, after migrations, and is idempotent: an account that already has a username is skipped, and Suggest is deterministic, so an interrupted run resumed later renames nobody.

It returns the number of accounts named. Errors on individual accounts are logged and skipped rather than aborting the run — one unnameable account must not stop the other nine hundred from being named.

Types

type Store

type Store struct {
	db.Store
}

Store decorates db.Store, naming accounts as they are created.

func New

func New(s db.Store) *Store

New wraps s.

func (*Store) CreateUser

func (s *Store) CreateUser(ctx context.Context, email, passwordHash, role, locale, tz string) (*model.User, error)

CreateUser creates the account and claims a username derived from its e-mail.

A failure to claim does NOT fail the creation. The account already exists by then, so returning an error would leave the caller looking at a failure it cannot retry (the e-mail is taken now) for a field that Backfill repairs on the next start. It is logged at error level because an unnamed account is a real defect — it just is not one worth refusing a login over.

Jump to

Keyboard shortcuts

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