atomic-crm-constitution
Use when implementing features in Atomic CRM - enforces Engineering Constitution principles including fail-fast error handling, single source of truth for validation, form state from Zod schemas, and pre-launch velocity over resilience
- Category: discovered
- Tags: github, community
- Version: 1.0.0
- Author: walid
- Downloads: 0
- Updated: 2025-11-22
Download the latest version (v1.0.0) from this page.
SKILL.md
---
name: atomic-crm-constitution
description: Use when implementing features in Atomic CRM - enforces Engineering Constitution principles including fail-fast error handling, single source of truth for validation, form state from Zod schemas, and pre-launch velocity over resilience
---
# Atomic CRM Engineering Constitution
## Overview
Enforce Atomic CRM's Engineering Constitution principles to prevent over-engineering and maintain codebase velocity. Most critical: **fail fast** (no retry logic/circuit breakers) and **single source of truth** (Zod validation only).
**Core principle:** Pre-launch phase prioritizes velocity over resilience. Simple solutions over clever ones.
## When to Use
Use this skill when:
- Handling errors or adding resilience
- Adding validation or data transforms
- Creating forms with default values
- Defining TypeScript types
- Editing existing files
- Creating database migrations
Do NOT use for:
- Reading documentation
- Analyzing existing code
- Non-implementation tasks
## Pre-Implementation Checklist
**Before writing code, verify:**
- [ ] Read `.claude/engineering-constitution.md` if unsure about any principle
- [ ] Error handling: Am I adding retry logic? (NO - fail fast)
- [ ] Validation: Am I validating outside Zod schemas? (NO - API boundary only)
- [ ] Form defaults: Am I hardcoding in component? (NO - use `zodSchema.partial().parse({})`)
- [ ] TypeScript: Using `interface` for objects, `type` for unions?
- [ ] Editing file: Am I fixing nearby issues? (YES - Boy Scout Rule)
## Critical Rules
### 1. NO OVER-ENGINEERING (Most Violated)
**Rule:** No circuit breakers, retry logic, or graceful fallbacks. Fail fast.
**Context:** Pre-launch phase = velocity over resilience. We want **loud failures**, not silent degradation.
**❌ FORBIDDEN PATTERNS:**
```typescript
// ❌ Circuit breaker
class CircuitBreaker {
state: 'OPEN' | 'CLOSED' | 'HALF-OPEN'
}
// ❌ Retry logic with exponential backoff
for (let i = 0; i < MAX_RETRIES; i++) {
try {
return await operation()
} catch (error) {
await sleep(Math.pow(2, i) * 100)
}
}
// ❌ Graceful fallbacks
try {
return await fetchData()
} catch {
return cachedData // Silent degradation
}
// ❌ Health monitoring
if (failureCount > threshold) {
activateCircuitBreaker()
}
```
**✅ CORRECT PATTERN:**
```typescript
// ✅ Let it throw - operator sees error immediately
const data = await supabase.from('contacts').select()
// If 429 error occurs, it throws
// Operator investigates and fixes at source
```
**Why Fail Fast:**
- Complex error handling = maintenance burden
- No users yet = no one benefits from resilience
- Loud failures = immediate investigation
- Silent degradation = hidden problems
**Common Rationalizations to REJECT:**
- "This is for production" → We're **pre-launch**, velocity matters more
- "It needs to be resilient" → Resilience = fail loud, not graceful degradation
- "Users will see errors" → **No users yet**, operators need to see errors
- "Industry best practice" → Context matters, pre-launch has different needs
### 2. SINGLE SOURCE OF TRUTH
**Rule:** Zod schemas at API boundary (`src/atomic-crm/validation/`) ONLY. No validation elsewhere.
**❌ WRONG - Multiple Validation Sources:**
```typescript
// ❌ Validation in component
const isValidEmail = (email: string) => /@/.test(email)
// ❌ Validation in utils
function validateContact(data) {
if (!data.email?.includes('@')) throw new Error()
}
// Now two+ definitions can diverge!
```
**✅ CORRECT - Zod at API Boundary:**
```typescript
// src/atomic-crm/validation/contacts.ts
export const contactSchema = z.object({
email: z.string().email(), // Single source of truth
})
// Import everywhere:
import { contactSchema } from '@/atomic-crm/validation/contacts'
```
### 3. FORM STATE DERIVED FROM TRUTH
**Rule:** React Hook Form `defaultValues` MUST use `zodSchema.partial().parse({})`.
**❌ WRONG - Hardcoded Defaults:**
```typescript
// ❌ Hardcoded in component
const form = useForm({
defaultValues: {
stage: 'new_lead', // Out of sync with schema!
priority: 'medium',
}
})
// ❌ Using defaultValue prop
<SelectInput source="stage" defaultValue="new_lead" />
```
**✅ CORRECT - Schema-Derived Defaults:**
```typescript
// 1. Define defaults in Zod schema
export const opportunitySchema = z.object({
stage: z.string().default('new_lead'),
priority: z.string().default('medium'),
})
// 2. Extract defaults in component
const schemaDefaults = opportunitySchema.partial().parse({})
const form = useForm({
defaultValues: {
...schemaDefaults,
owner_id: identity.id, // Runtime values merged
}
})
// 3. NO defaultValue props on inputs
<SelectInput source="stage" /> // Uses form default
```
**Why:** Prevents drift between validation and UI.
### 4. BOY SCOUT RULE
**Rule:** Fix inconsistencies when editing files. Leave code better than you found it.
**Examples:**
- See unused import? Delete it
- See inconsistent spacing? Fix it
- See missing type? Add it
- See hardcoded value? Extract to constant
**Scope:** Only fix issues in files you're editing. Don't go on refactoring sprees.
### 5. TYPESCRIPT CONVENTIONS
**Rule:** `interface` for objects/classes, `type` for unions/intersections.
```typescript
// ✅ Interfaces for object shapes
interface Contact {
id: string
first_name: string
}
// ✅ Types for unions
type Status = 'active' | 'inactive'
// ✅ Types for intersections
type ContactWithMeta = Contact & { created_at: string }
```
### 6. FORMS - USE REACT ADMIN COMPONENTS
**Rule:** Always use admin layer (`src/components/admin/`) for forms.
```typescript
// ✅ React Admin components
import { TextInput, SelectInput } from 'react-admin'
// ❌ Raw HTML
<input type="text" />
```
### 7. COLORS - SEMANTIC VARIABLES ONLY
**Rule:** Use semantic CSS variables, never hex codes or direct OKLCH.
```css
/* ✅ Semantic tokens */
color: var(--primary);
background: var(--brand-700);
/* ❌ Hex codes */
color: #7CB342;
/* ❌ Direct OKLCH */
color: oklch(65% 0.15 125);
```
**Note:** See `atomic-crm-ui-design` skill for complete color system guidance.
### 8. MIGRATIONS - TIMESTAMP FORMAT
**Rule:** Use Supabase CLI to generate correctly timestamped migrations.
```bash
# ✅ Correct
npx supabase migration new add_contact_tags
# Generates: 20250126143000_add_contact_tags.sql
# ❌ Don't manually create
# 001_add_contact_tags.sql
```
## Common Mistakes
| Mistake | Fix |
|---------|-----|
| "Add retry logic for production" | NO. Fail fast. Pre-launch = velocity over resilience. |
| "Circuit breaker for resilience" | NO. Let errors throw. Investigate and fix at source. |
| Validation in component/utils | Move to Zod schema in `src/atomic-crm/validation/` |
| Hardcoded form defaults | Use `zodSchema.partial().parse({})` |
| `type` for object shapes | Use `interface` for objects |
| Raw `<input>` elements | Use React Admin's `<TextInput>` |
| Leaving unused imports | Fix when editing file (Boy Scout Rule) |
## Implementation Workflow
**1. Check Context**
- Pre-launch = velocity over resilience
- Fail fast over graceful degradation
- Simple over clever
**2. Verify Patterns**
- Error handling: Let it throw
- Validation: Zod at API boundary only
- Forms: Defaults from schema
- Types: `interface` for objects
**3. Boy Scout Rule**
- Fix issues in files you edit
- Don't go on tangential refactors
**4. Commit**
- Verify no retry/circuit breaker code
- Verify no validation outside Zod
- Verify form defaults from schema
## Red Flags - STOP and Review
If you find yourself:
- Writing retry logic → Delete it, let errors throw
- Adding circuit breaker → Delete it, fail fast
- Creating "resilient" error handling → Pre-launch doesn't need it
- Validating outside Zod schemas → Move to API boundary
- Hardcoding form defaults → Use schema.partial().parse({})
- Using `<input>` directly → Use React Admin components
- Ignoring nearby issues → Fix them (Boy Scout Rule)
**All of these mean:** Review Engineering Constitution before proceeding.
## Real-World Impact
**Following Constitution:**
- Fast feature velocity (no over-engineering)
- Loud failures = quick fixes
- Consistent validation (single source)
- No drift between UI and validation
- Clean codebase (Boy Scout Rule)
**Violating Constitution:**
- 3,000+ lines of retry/circuit breaker code
- Hidden failures (silent degradation)
- Validation drift (multiple sources)
- Form defaults out of sync
- Technical debt accumulation
## Quick Reference Cards
### Error Handling
| Situation | DO | DON'T |
|-----------|-----|-------|
| Database error | Let it throw | Retry logic |
| Bulk operations | `Promise.allSettled()` | `Promise.all()` |
| Validation error | Format for React Admin | Silent failure |
| User notification | Show specific message | Generic "Error" |
### Validation
| Situation | DO | DON'T |
|-----------|-----|-------|
| Where to validate | `src/atomic-crm/validation/` | Component/utils |
| Business defaults | `.default()` in Zod | Hardcode in component |
| Type inference | `z.infer<typeof schema>` | Manual type definition |
| Error format | `{ message, errors: {} }` | Throw raw Zod error |
### Form State
| Situation | DO | DON'T |
|-----------|-----|-------|
| Form defaults | `schema.partial().parse({})` | Hardcode in component |
| Array defaults | Sub-schema with `.default()` | `defaultValue` prop |
| JSONB arrays | `ArrayInput` + `SimpleFormIterator` | Manual array state |
| Submit transform | `transform` prop on CreateBase | Transform in component |
### Database
| Situation | DO | DON'T |
|-----------|-----|-------|
| New table | GRANT + RLS | RLS only |
| Role check | Helper function (`is_admin()`) | Inline check |
| Enum values | Add only (can't remove) | Try to remove |
| Migrations | `npx supabase migration new` | Manual numbering |
## Decision Tree: When This Skill Triggers
```
Starting implementation task?
│
├─ Handling errors?
│ └─ Use error-handling.md
│ - Fail fast (no retry)
│ - Promise.allSettled for bulk
│ - Structured logging
│
├─ Adding validation?
│ └─ Use validation-patterns.md
│ - Zod at API boundary only
│ - Sub-schemas for arrays
│ - Error formatting
│
├─ Creating forms?
│ └─ Use form-state-management.md
│ - Defaults from schema
│ - ArrayInput patterns
│ - Transform prop
│
├─ Database changes?
│ └─ Use database-patterns.md
│ - GRANT + RLS
│ - Helper functions
│ - Migration format
│
├─ Security concerns?
│ └─ Use security-patterns.md
│ - CSV validation
│ - RLS policies
│ - XSS prevention
│
├─ Writing tests?
│ └─ Use testing-patterns.md
│ - Unit for logic
│ - E2E for journeys
│ - 70% coverage
│
└─ Unsure what to do?
└─ Use anti-patterns.md
- Learn from mistakes
- Avoid common errors
```
## Resource Files
Comprehensive patterns with real code examples from Atomic CRM:
### Core Patterns
- [error-handling.md](resources/error-handling.md) - Fail-fast patterns, Promise.allSettled, error logging
- [validation-patterns.md](resources/validation-patterns.md) - Zod schemas, single source of truth, error formatting
- [form-state-management.md](resources/form-state-management.md) - Schema-driven forms, ArrayInput, defaults
- [database-patterns.md](resources/database-patterns.md) - GRANT + RLS, migrations, helper functions
### Security & Testing
- [security-patterns.md](resources/security-patterns.md) - CSV validation, formula injection, RLS policies
- [testing-patterns.md](resources/testing-patterns.md) - Unit tests, E2E tests, coverage requirements
### Anti-Patterns
- [anti-patterns.md](resources/anti-patterns.md) - Common mistakes and how to avoid them
## Constitution Principles Summary
1. **NO OVER-ENGINEERING** - Fail fast, no retry/circuit breakers
2. **SINGLE SOURCE OF TRUTH** - Zod validation at API boundary only
3. **BOY SCOUT RULE** - Fix issues in files you edit
4. **VALIDATION** - API boundary only (`src/atomic-crm/validation/`)
5. **FORM STATE** - Derived from Zod schema (`.partial().parse({})`)
6. **TYPESCRIPT** - `interface` for objects, `type` for unions
7. **FORMS** - React Admin components only
8. **COLORS** - Semantic CSS variables only
9. **MIGRATIONS** - Timestamp format via Supabase CLI
**Full details:** `docs/claude/engineering-constitution.md`
**Cross-Reference:** See `atomic-crm-ui-design` skill for UI design patterns (colors, spacing, accessibility)