Zum Inhalt springen

Auth Feature Implementation Plan

For agentic workers: REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (- [ ]) syntax for tracking.

Goal: Implement login, 2FA via email, session management, and auth middleware so the CMS has a working authentication system.

Architecture: Feature-based packages under internal/feature/auth/. Raw SQL via database/sql (Jet code-gen comes later). Session stored in traffino.sessions, session ID in HTTP-only cookie. 2FA codes stored in traffino.login_attempts. Auth middleware extracts session from cookie and injects user info into request context.

Tech Stack: Go, Chi v5, bcrypt, crypto/rand, database/sql, pgx


cms/backend/
├── internal/
│ ├── feature/
│ │ └── auth/
│ │ ├── errors.go # Sentinel errors
│ │ ├── password.go # bcrypt hash/verify
│ │ ├── repository.go # AccountRepository + SessionRepository interfaces
│ │ ├── sql_repository.go # SQL implementations
│ │ ├── login.go # Login use case
│ │ ├── verify2fa.go # Verify 2FA use case
│ │ ├── logout.go # Logout use case
│ │ ├── session_check.go # Session check use case
│ │ └── handler.go # Chi HTTP handler (routes + handlers)
│ └── shared/
│ └── middleware/
│ └── auth.go # Auth middleware (cookie → context)
├── cmd/api/
│ └── main.go # Wire auth feature + middleware

Files:

  • Create: internal/feature/auth/errors.go
  • Create: internal/feature/auth/password.go
  • Test: internal/feature/auth/password_test.go

Sentinel errors for the auth feature. Password hashing with bcrypt.


Task 2: Repository interfaces + SQL implementation

Abschnitt betitelt „Task 2: Repository interfaces + SQL implementation“

Files:

  • Create: internal/feature/auth/repository.go
  • Create: internal/feature/auth/sql_repository.go

AccountRepository: FindByEmail, FindByID. SessionRepository: Create, FindByID, Terminate. LoginAttemptRepository: Create, FindByID, MarkVerified, CountRecent.

All using raw SQL with database/sql.


Files:

  • Create: internal/feature/auth/login.go

Login flow:

  1. Find account by email
  2. Verify password
  3. If 2FA enabled: create login_attempt with random 6-digit code, return 2fa_required + attempt_id
  4. If 2FA disabled: create session, return session_id
  5. Rate limiting: max 5 failed attempts per email in 15 minutes

Files:

  • Create: internal/feature/auth/verify2fa.go
  1. Find login_attempt by ID
  2. Verify code matches and not expired (5 min)
  3. Create session
  4. Mark attempt as verified

Files:

  • Create: internal/feature/auth/logout.go
  • Create: internal/feature/auth/session_check.go

Logout: terminate session by ID. Session check: find session, return account info if valid.


Files:

  • Create: internal/shared/middleware/auth.go

Extract session ID from session cookie → find session → inject account info into context. Public routes skip this. Protected routes return 401 if no valid session.


Files:

  • Create: internal/feature/auth/handler.go

Routes:

  • POST /api/public/auth/login → Login
  • POST /api/public/auth/verify-2fa → Verify2FA
  • GET /api/public/auth/session → SessionCheck
  • POST /api/protected/auth/logout → Logout

Files:

  • Modify: cmd/api/main.go

Wire repositories, use cases, handler, middleware into the Chi router.


Test login flow end-to-end with httptest (no DB — mock repositories).


Compile, run tests, commit, push.