Wires up a periodic cleanup goroutine that drives DeleteExpiredMagicLinkTokens (Phase A.3 method that was never called). Mirrors ADR-0021 JWT cleanup pattern.
Claude trainer takeover : Mistral hit --max-price 1.50 right before commit. Code itself is Mistral's ; Claude only ran the commit/push/PR/merge sequence.
Test plan
go test ./pkg/user/... -count=1 → green (4 new tests)
go vet ./... clean
go build ./... clean
## Summary
Wires up a periodic cleanup goroutine that drives DeleteExpiredMagicLinkTokens (Phase A.3 method that was never called). Mirrors ADR-0021 JWT cleanup pattern.
**Mistral Vibe authored** (batch1 N=2 parallel with PR #64 OIDC config):
- pkg/user/magic_link_cleanup.go (new) — MagicLinkCleanupRunner + StartCleanupLoop(ctx, interval) + runOnce(ctx)
- pkg/user/magic_link_cleanup_test.go (new) — 4 unit tests (happy / error / cancel / zero-interval)
- pkg/server/server.go — start the loop next to JWT cleanup
- pkg/config/config.go — auth.magic_link.cleanup_interval (1h default) + env bind + getter
**Claude trainer takeover** : Mistral hit --max-price 1.50 right before commit. Code itself is Mistral's ; Claude only ran the commit/push/PR/merge sequence.
## Test plan
- go test ./pkg/user/... -count=1 → green (4 new tests)
- go vet ./... clean
- go build ./... clean
Periodically delete magic-link tokens past their expires_at — the rows
accumulate without cleanup since the consume endpoint only marks them
consumed but never removes them, and DeleteExpiredMagicLinkTokens (added
in Phase A.3, PR #61) was never wired up.
Mirrors the JWT secret cleanup pattern (ADR-0021).
- pkg/user/magic_link_cleanup.go: MagicLinkCleanupRunner with
StartCleanupLoop(ctx, interval) and an inner runOnce(ctx) for testability
- pkg/user/magic_link_cleanup_test.go: unit tests cover happy path,
error propagation, ctx-cancel termination, zero-interval no-op
- pkg/server/server.go: start the loop right after the JWT cleanup loop
- pkg/config/config.go: auth.magic_link.cleanup_interval (default 1h),
env DLC_AUTH_MAGIC_LINK_CLEANUP_INTERVAL, getter GetMagicLinkCleanupInterval
Mostly authored by Mistral Vibe in batch1-task-b worktree (parallel with
batch1-task-a OIDC config). Mistral hit --max-price 1.50 right before the
final commit step, Claude finished the ship via trainer takeover (Q-045
pattern, 2nd recurrence in two batches — to be addressed in Phase 1bis).
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Summary
Wires up a periodic cleanup goroutine that drives DeleteExpiredMagicLinkTokens (Phase A.3 method that was never called). Mirrors ADR-0021 JWT cleanup pattern.
Mistral Vibe authored (batch1 N=2 parallel with PR #64 OIDC config):
Claude trainer takeover : Mistral hit --max-price 1.50 right before commit. Code itself is Mistral's ; Claude only ran the commit/push/PR/merge sequence.
Test plan
5bc97545f4to8041a8c04f