Installation
Get CleanStack up and running in less than 5 minutes
Prerequisites
Before you begin, ensure you have the following installed:
- Node.js ā„ 24.12.0
- PNPM 10.26.2
- Docker and Docker Compose
Quick Start
Step 1: Clone & Install
git clone https://github.com/axelhamil/nextjs-clean-architecture-starter cleanstack
cd cleanstack
pnpm install
Step 2: Setup Database
# Copy environment variables
cp .env.example .env
# Start PostgreSQL container
pnpm db
# Push database schema
pnpm db:push
The .env file should contain at minimum:
DATABASE_URL="postgresql://postgres:postgres@localhost:5432/cleanstack"
Step 3: Start Development
pnpm dev
Visit http://localhost:3000 to see your app running!
Available Commands
Development Commands
| Command | Description |
|---------|-------------|
| pnpm dev | Start development server (runs db:generate first) |
| pnpm build | Build all packages and apps for production |
| pnpm start | Start production server |
| pnpm clean | Clean all build artifacts and node_modules |
Code Quality Commands
| Command | Description |
|---------|-------------|
| pnpm validate | Full validation (type-check + lint + test) |
| pnpm quick-check | Fast check (type-check + lint only) |
| pnpm type-check | TypeScript type checking (requires db:generate) |
| pnpm check | Biome lint & format check (without fixing) |
| pnpm format | Format code with Biome |
| pnpm fix | Auto-fix Biome issues |
| pnpm lint | Lint with Biome |
| pnpm ci:check | CI-friendly check |
Database Commands
| Command | Description |
|---------|-------------|
| pnpm db | Start PostgreSQL container (Docker Compose) |
| pnpm db:generate | Generate migrations from schema changes |
| pnpm db:push | Push schema to database (dev only - no migrations) |
| pnpm db:migrate | Run migrations (production) |
| pnpm db:studio | Open Drizzle Studio UI |
Important: Always run pnpm db:generate before pnpm type-check or pnpm dev when you modify database schemas. TypeScript needs the generated types.
Testing Commands
| Command | Description |
|---------|-------------|
| pnpm test | Run all tests with Vitest |
| pnpm test:watch | Run tests in watch mode |
| pnpm test:coverage | Generate coverage report |
To run tests in a specific package:
cd apps/nextjs && pnpm test
cd packages/ddd-kit && pnpm test
Package Management
| Command | Description |
|---------|-------------|
| pnpm ui:add | Add shadcn/ui component |
| pnpm install <package> | Install dependency |
Project Structure Overview
cleanstack/
āāā apps/
ā āāā nextjs/ # Main Next.js application
ā āāā app/ # Next.js App Router (pages, layouts, routes)
ā āāā common/ # DI container, env config, i18n
ā āāā src/ # Clean Architecture layers
ā āāā domain/ # Entities, Value Objects, Aggregates
ā āāā application/ # Use Cases, DTOs, Port interfaces
ā āāā adapters/ # Controllers, Repositories (in/out)
ā āāā shared/ # Shared utilities
āāā packages/
ā āāā ddd-kit/ # DDD primitives (Entity, Result, Option, etc.)
ā āāā drizzle/ # Database schema & ORM setup
ā āāā ui/ # shadcn/ui components
ā āāā test/ # Shared Vitest configuration
ā āāā typescript-config/ # Shared TypeScript configs
āāā turbo.json # Turborepo configuration
Initial Setup Workflow
After installation, follow this recommended workflow:
1. Read Documentation
- CLAUDE.md - Complete architecture guide and codebase context
- .cursorrules - AI coding guidelines and architectural patterns
- @packages/ddd-kit - Explore DDD primitives
2. Explore the Codebase
Start with these files:
# DDD primitives
packages/ddd-kit/src/entity.ts
packages/ddd-kit/src/value-object.ts
packages/ddd-kit/src/result.ts
packages/ddd-kit/src/option.ts
# Example domain implementations
apps/nextjs/src/domain/examples/
# Dependency injection setup
apps/nextjs/common/di/container.ts
apps/nextjs/common/di/types.ts
3. Try Helper Scripts
Generate boilerplate code:
# Create a new Use Case
./scripts/create-use-case.sh CreateUser
# Create a new Value Object
./scripts/create-value-object.sh Email
4. Run Validation
Ensure everything works:
pnpm validate
This runs:
- Type checking
- Linting
- Tests
Database Setup Details
Docker Compose
The project includes a docker-compose.yml with PostgreSQL:
services:
postgres:
image: postgres:16
ports:
- "5432:5432"
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
POSTGRES_DB: cleanstack
Start it with:
pnpm db
# or
docker compose up -d postgres
Schema Changes Workflow
When you modify database schemas:
# 1. Edit schema files in packages/drizzle/src/schema/
# 2. Generate migration
pnpm db:generate
# 3. Apply changes
pnpm db:push # Dev: direct push (fast, no migrations)
# OR
pnpm db:migrate # Prod: run migrations (versioned, safe)
# 4. TypeScript types are auto-generated
pnpm type-check # Should pass now
Drizzle Studio
Explore your database with a visual interface:
pnpm db:studio
Opens https://local.drizzle.studio
Environment Variables
Required variables in .env:
# Database (required by Turborepo globally)
DATABASE_URL="postgresql://postgres:postgres@localhost:5432/cleanstack"
# Optional: Add your own as needed
# NEXT_PUBLIC_API_URL="http://localhost:3000/api"
# EMAIL_SERVICE_KEY="your-key"
Validation is handled by apps/nextjs/common/env.ts using Zod:
import { z } from 'zod';
const envSchema = z.object({
DATABASE_URL: z.string().url(),
// Add more as needed
});
export const env = envSchema.parse(process.env);
Troubleshooting
TypeScript Errors After Schema Changes
Problem: pnpm type-check fails with database-related errors
Solution:
pnpm db:generate # Regenerate types
pnpm type-check # Should pass now
Turborepo Cache Issues
Problem: Changes not reflected, stale builds
Solution:
pnpm clean # Clean all artifacts
pnpm install # Reinstall dependencies
pnpm build # Rebuild everything
Database Connection Errors
Problem: Cannot connect to database
Solution:
# Check if PostgreSQL is running
docker ps | grep postgres
# Restart container
docker compose down
docker compose up -d postgres
# Verify connection
psql postgresql://postgres:postgres@localhost:5432/cleanstack
Port Already in Use
Problem: Port 3000 or 5432 already in use
Solution:
# Find process using port
lsof -i :3000
lsof -i :5432
# Kill process or change port in .env
Next Steps
Now that you're set up:
- ā
Read Architecture Docs - Visit
/docs/architectureto understand Clean Architecture - ā
Explore Examples - Check
apps/nextjs/src/domain/examples/ - ā Try Creating a Feature - Follow the Use Case pattern
- ā
Run Tests -
pnpm testto see examples - ā
Use AI Assistance - Read
/docs/claude-codefor AI development tips
Happy coding with CleanStack! š