---
title: "How Twenty Is Built"
description: "Repository structure, Nx build system, dependencies, testing, and deployment"
image: "https://tractiongrowth.com/og/open-source/twenty-crm/how-it-is-built/image.png"
---

# How Twenty Is Built

# How Twenty Is Built

Twenty is built as an Nx monorepo with a NestJS backend, a React frontend, shared packages, and deployment tooling for both cloud and self-hosted environments. This page explains the repository layout, build system, dependencies, and deployment path that ship the CRM.

<Callout title="For Product Managers">
  This page answers "how does the engineering team ship Twenty?" — the tools, processes, and infrastructure behind the product. Understanding this helps you estimate customization effort, deployment complexity, and maintenance costs for self-hosting.
</Callout>

## Repository Structure

Twenty is an **Nx monorepo** with **15+ packages** managed by Yarn workspaces. All applications and libraries live in a single repository.

```
twenty/
├── packages/
│   ├── twenty-server/        ← NestJS backend (API, GraphQL, workers)
│   ├── twenty-front/         ← React SPA (Vite, the main CRM UI)
│   ├── twenty-ui/            ← Shared UI component library
│   ├── twenty-shared/        ← Shared types, utils, constants
│   ├── twenty-emails/        ← Email templates (React Email)
│   ├── twenty-sdk/           ← SDK for app development
│   ├── twenty-website/       ← Marketing site (Next.js)
│   ├── twenty-docs/          ← Documentation (Mintlify)
│   ├── twenty-docker/        ← Docker Compose, K8s, Helm configs
│   ├── twenty-e2e-testing/   ← Playwright E2E tests
│   ├── twenty-zapier/        ← Zapier integration
│   ├── twenty-apps/          ← Plugin/app ecosystem
│   │   ├── internal/         ← First-party apps (self-hosting, call recording)
│   │   └── community/        ← Community apps (Stripe sync, Mailchimp, etc.)
│   ├── twenty-companion/     ← Desktop companion app
│   ├── twenty-cli/           ← CLI tool (deprecated → twenty-sdk)
│   ├── twenty-utils/         ← Dev utilities and release scripts
│   ├── twenty-oxlint-rules/  ← Custom linting rules
│   └── create-twenty-app/    ← App scaffolding CLI
├── nx.json                   ← Nx monorepo configuration
├── package.json              ← Root workspace definition
├── tsconfig.base.json        ← Shared TypeScript config
└── .github/workflows/        ← CI/CD (20+ GitHub Actions workflows)
```

### The Core Applications

| Package            | Technology          | Purpose                                        |
| ------------------ | ------------------- | ---------------------------------------------- |
| **twenty-server**  | NestJS 11 + TypeORM | Backend API, GraphQL, REST, background workers |
| **twenty-front**   | React 18 + Vite 7   | Main CRM single-page application               |
| **twenty-website** | Next.js 14          | Marketing site (twenty.com)                    |
| **twenty-docs**    | Mintlify            | Developer documentation (docs.twenty.com)      |

### The Shared Libraries

| Package           | Purpose                                                                       |
| ----------------- | ----------------------------------------------------------------------------- |
| **twenty-ui**     | 100+ React components (buttons, tables, kanban, navigation, rich text editor) |
| **twenty-shared** | TypeScript types, workflow schemas, metadata utils, i18n constants            |
| **twenty-emails** | React Email templates for transactional emails                                |
| **twenty-sdk**    | SDK for building Twenty apps/plugins + CLI                                    |

<Callout type="info" title="Why an Nx Monorepo?">
  Twenty has 15+ interconnected packages that share types, components, and utilities. Nx ensures: (1) only affected packages are rebuilt when code changes, (2) builds are cached locally and in CI, (3) dependency relationships are tracked automatically. Without Nx, a change to `twenty-shared` would require manually rebuilding everything — Nx does it automatically.
</Callout>

## Build System

### Nx as Orchestrator

```
yarn install                     ← installs all dependencies (Yarn workspaces)
    │
    ▼
nx build twenty-shared           ← build shared libs first (Nx dependency graph)
nx build twenty-ui               ← then UI components
    │
    ├──► nx build twenty-front   ← Vite production build
    └──► nx build twenty-server  ← NestJS compilation (TypeScript → JS)
```

**Nx features used:**

* **Task graph** — knows build order from package dependencies
* **Caching** — skips unchanged packages
* **Affected** — `nx affected:build` only rebuilds what changed
* **Parallel** — builds independent packages simultaneously

### Frontend Build (Vite)

```
twenty-front → Vite 7
  ├── SWC (fast TypeScript transpilation)
  ├── Linaria (CSS extraction at build time)
  ├── GraphQL Codegen (type generation)
  └── Output: static HTML/JS/CSS bundle
```

### Backend Build (NestJS)

```
twenty-server → TypeScript compiler
  ├── NestJS modules compiled
  ├── TypeORM entities and migrations
  ├── GraphQL schema generation (runtime)
  └── Output: Node.js application (dist/)
```

## Dependency Map

### Backend Dependencies (Key Libraries)

| Package                           | Purpose                    | Why Chosen                                                   |
| --------------------------------- | -------------------------- | ------------------------------------------------------------ |
| NestJS 11                         | Application framework      | Dependency injection, modular architecture, enterprise-grade |
| TypeORM 0.3                       | Database ORM               | Mature, decorator-based, migration support                   |
| GraphQL Yoga                      | GraphQL server             | Lightweight, spec-compliant, subscription support            |
| @nestjs/graphql                   | NestJS GraphQL integration | Schema-first with code generation                            |
| BullMQ                            | Job queue                  | Reliable, Redis-backed, supports delays and cron             |
| ioredis                           | Redis client               | High-performance, cluster support                            |
| Passport                          | Authentication             | Modular strategies (JWT, OAuth, SAML)                        |
| class-validator                   | Input validation           | Decorator-based validation for DTOs                          |
| googleapis                        | Google API client          | Gmail and Calendar sync                                      |
| @microsoft/microsoft-graph-client | Microsoft Graph            | Outlook and Calendar sync                                    |
| stripe                            | Billing                    | Payment processing for hosted version                        |
| ai + @ai-sdk/\*                   | AI integration             | Multi-provider AI (OpenAI, Anthropic, Google)                |
| imapflow + nodemailer             | Email                      | IMAP sync and SMTP sending                                   |

### Frontend Dependencies (Key Libraries)

| Package              | Purpose          | Why Chosen                                         |
| -------------------- | ---------------- | -------------------------------------------------- |
| React 18             | UI framework     | Industry standard, large ecosystem                 |
| Vite 7               | Build tool       | Fast dev server, optimized production builds       |
| Apollo Client        | GraphQL client   | Mature caching, real-time subscriptions            |
| Jotai                | State management | Atomic — minimal boilerplate, fine-grained updates |
| Linaria (@wyw-in-js) | CSS-in-JS        | Zero-runtime — CSS extracted at build time         |
| React Router 6       | Routing          | Nested layouts, lazy loading                       |
| React Hook Form      | Forms            | Performant, minimal re-renders                     |
| @blocknote/mantine   | Rich text editor | Block-based editor (like Notion)                   |
| @nivo/\*             | Charts           | Data visualization for analytics                   |
| @xyflow/react        | Flow diagrams    | Workflow visual editor                             |
| Lingui               | i18n             | Compile-time message extraction                    |
| Mantine              | UI primitives    | Accessible component foundation                    |
| Framer Motion        | Animations       | Declarative animations                             |

### Infrastructure Dependencies

| Service               | Purpose                                               |
| --------------------- | ----------------------------------------------------- |
| PostgreSQL 16         | Primary database (multi-tenant with schema isolation) |
| Redis                 | Cache + BullMQ broker + SSE pub/sub                   |
| ClickHouse            | Analytics and usage data                              |
| S3 (or local storage) | File attachments and uploads                          |

<Callout type="info" title="Key Design Choice: Zero-Runtime CSS">
  Twenty uses Linaria (via @wyw-in-js), which extracts CSS at build time. Unlike runtime CSS-in-JS libraries (styled-components, Emotion), Linaria adds zero JavaScript overhead — the styles are plain CSS files. This matters for a CRM where users have large tables with hundreds of rows; runtime CSS-in-JS would add measurable overhead per row.
</Callout>

## Deployment

### Docker Compose (Primary Method)

The simplest deployment uses 4 Docker services:

```
docker-compose.yml
  ├── server   → Twenty app (NestJS + bundled React frontend)
  │               Port 3000
  ├── worker   → BullMQ background workers
  │               (same image, different entrypoint)
  ├── db       → PostgreSQL 16
  │               Port 5432
  └── redis    → Redis
                  Port 6379
```

**Quick install:**

```bash
bash <(curl -sL https://raw.githubusercontent.com/twentyhq/twenty/main/packages/twenty-docker/scripts/install.sh)
```

**Manual:**

```bash
curl -O https://raw.githubusercontent.com/twentyhq/twenty/main/packages/twenty-docker/.env.example
curl -O https://raw.githubusercontent.com/twentyhq/twenty/main/packages/twenty-docker/docker-compose.yml
# Edit .env with your settings
docker compose up -d
```

### Required Environment Variables

| Variable               | Purpose                                                  |
| ---------------------- | -------------------------------------------------------- |
| `APP_SECRET`           | Encryption key (generate with `openssl rand -base64 32`) |
| `SERVER_URL`           | Public URL of the application                            |
| `PG_DATABASE_PASSWORD` | PostgreSQL password                                      |
| `STORAGE_TYPE`         | `local` or `s3`                                          |

### Optional Configuration

| Category       | Variables                                               |
| -------------- | ------------------------------------------------------- |
| **Auth**       | `AUTH_GOOGLE_*`, `AUTH_MICROSOFT_*`, SAML/OIDC settings |
| **Email**      | `EMAIL_DRIVER`, SMTP settings                           |
| **Messaging**  | Gmail/Microsoft API credentials for email sync          |
| **Storage**    | S3 bucket, region, credentials                          |
| **Monitoring** | `SENTRY_DSN`, OpenTelemetry config                      |
| **Analytics**  | ClickHouse connection                                   |
| **AI**         | `OPENAI_API_KEY` or other AI provider keys              |

### Other Deployment Options

| Platform           | Type                              | Maintained By      |
| ------------------ | --------------------------------- | ------------------ |
| **Docker Compose** | Self-hosted                       | Core team          |
| **Kubernetes**     | Self-hosted (Terraform/Manifests) | Community          |
| **Railway**        | Cloud platform                    | Community template |
| **Coolify**        | Self-hosted PaaS                  | Community          |
| **EasyPanel**      | Self-hosted PaaS                  | Community          |
| **Elest.io**       | Managed hosting                   | Partner            |
| **Sealos**         | Cloud platform                    | Community          |

## Quality & Testing

### Testing Stack

| Layer                        | Tool                  | Scope                                      |
| ---------------------------- | --------------------- | ------------------------------------------ |
| **Backend unit/integration** | Jest                  | NestJS modules, services, resolvers        |
| **Frontend components**      | Vitest + Storybook 10 | Component rendering and interaction        |
| **Visual regression**        | Chromatic             | UI screenshot comparison                   |
| **E2E**                      | Playwright            | Full user flows (auth, records, workflows) |
| **SDK**                      | Vitest                | SDK unit + integration tests               |

### Code Quality Tools

| Tool                       | Purpose                                                       |
| -------------------------- | ------------------------------------------------------------- |
| **Oxlint**                 | Fast Rust-based linting (custom rules in twenty-oxlint-rules) |
| **Prettier**               | Code formatting                                               |
| **TypeScript strict mode** | Type safety across all packages                               |
| **GraphQL Codegen**        | Auto-generated types from GraphQL schemas                     |
| **tsgo**                   | Fast TypeScript type checking (Go-based)                      |

### CI/CD Pipeline

Twenty has **20+ GitHub Actions workflows** covering:

* Server, frontend, shared, SDK, docs, website, Zapier — each tested independently
* Docker Compose deployment test
* Breaking changes detection
* Release creation and deployment
* i18n synchronization (Crowdin)
* Preview environments for PRs
* Automated deployment to production on merge to `main`

## Developer Experience

### Getting Started

```bash
# Clone the repo
git clone https://github.com/twentyhq/twenty.git && cd twenty

# Use correct Node version
nvm use

# Install dependencies
yarn install

# Start infrastructure (PostgreSQL + Redis)
cd packages/twenty-docker && docker compose -f docker-compose.dev.yml up -d && cd ../..

# Set up environment
cp packages/twenty-server/.env.example packages/twenty-server/.env

# Run database migrations
npx nx database:migrate twenty-server

# Seed the database
npx nx database:seed twenty-server

# Start the app (frontend + backend + worker)
yarn start
```

### Key Developer Commands

| Task                   | Command                                 |
| ---------------------- | --------------------------------------- |
| Start everything       | `yarn start`                            |
| Start frontend only    | `npx nx start twenty-front`             |
| Start server only      | `npx nx start twenty-server`            |
| Run server tests       | `npx nx test twenty-server`             |
| Run frontend Storybook | `npx nx storybook:dev twenty-front`     |
| Run E2E tests          | `npx nx test twenty-e2e-testing`        |
| Generate GraphQL types | `npx nx graphql:codegen twenty-front`   |
| Database migration     | `npx nx database:migrate twenty-server` |
| Lint all               | `npx nx run-many -t lint`               |
| Build all              | `npx nx run-many -t build`              |

### App / Plugin Development

Twenty has an **app ecosystem** for extensions:

```bash
# Scaffold a new Twenty app
npx create-twenty-app my-app

# Build with the SDK
import { TwentySDK } from 'twenty-sdk';
```

Community apps include: Stripe sync, Mailchimp sync, meeting transcripts, LinkedIn browser extension, AI meeting summaries, and more.

## What's Next

<Cards>
  <Card title="What Is Twenty?" description="What Twenty does, who it's for, and why it exists." href="/open-source/twenty-crm" />

  <Card title="Twenty Architecture Overview" description="Server design, metadata engine, and the systems behind custom objects." href="/open-source/twenty-crm/architecture" />

  <Card title="Twenty Workflows and Data Flows" description="Key user journeys traced through all layers." href="/open-source/twenty-crm/workflows" />
</Cards>

