feat: add Terms & Conditions checkbox to signup (refs #4)
All checks were successful
Deploy to Staging / Build Images (pull_request) Successful in 4m38s
Deploy to Staging / Deploy to Staging (pull_request) Successful in 28s
Deploy to Staging / Verify Staging (pull_request) Successful in 6s
Deploy to Staging / Notify Staging Ready (pull_request) Successful in 6s
Deploy to Staging / Notify Staging Failure (pull_request) Has been skipped

- Add terms_agreements table for legal audit trail
- Create terms-agreement feature capsule with repository
- Modify signup to create terms agreement atomically
- Add checkbox with PDF link to SignupForm
- Capture IP, User-Agent, terms version, content hash
- Update CLAUDE.md documentation index

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Eric Gullickson
2026-01-03 12:27:45 -06:00
parent 0391a23bb6
commit dec91ccfc2
14 changed files with 390 additions and 15 deletions

View File

@@ -0,0 +1,46 @@
# Terms Agreement Feature
Stores legal audit trail for Terms & Conditions acceptance at user signup.
## Purpose
Provides comprehensive legal compliance by capturing:
- **User consent**: Proof that user agreed to T&C before account creation
- **Audit fields**: IP address, user agent, timestamp, terms version, content hash
## Data Flow
1. User checks T&C checkbox on signup form
2. Frontend sends `termsAccepted: true` with signup request
3. Controller extracts IP (from X-Forwarded-For header), User-Agent
4. Service creates user profile and terms agreement atomically in transaction
5. Terms agreement record stores audit fields for legal compliance
## Database Schema
| Column | Type | Description |
|--------|------|-------------|
| id | UUID | Primary key |
| user_id | VARCHAR | Auth0 user ID |
| agreed_at | TIMESTAMPTZ | UTC timestamp of agreement |
| ip_address | VARCHAR(45) | Client IP (supports IPv6) |
| user_agent | TEXT | Browser/client user agent |
| terms_version | VARCHAR | Version string (e.g., v2026-01-03) |
| terms_url | VARCHAR | URL path to PDF |
| terms_content_hash | VARCHAR(64) | SHA-256 hash of PDF content |
## Files
| Path | Purpose |
|------|---------|
| `migrations/001_create_terms_agreements.sql` | Database table creation |
| `data/terms-agreement.repository.ts` | Data access layer |
| `domain/terms-agreement.types.ts` | TypeScript interfaces |
| `domain/terms-config.ts` | Static terms version and hash |
| `index.ts` | Feature exports |
## Invariants
- Every user in `user_profiles` has exactly one record in `terms_agreements`
- `agreed_at` is always stored in UTC
- `terms_content_hash` matches SHA-256 of PDF at signup time