Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
164 changes: 141 additions & 23 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,14 @@ Twenty is an open-source CRM (Customer Relationship Management) platform built a

### Technology Stack

| Layer | Technology |
|-------|-----------|
| Layer | Technology |
| -------- | ------------------------------------------- |
| Frontend | React 18, TypeScript, Recoil, Emotion, Vite |
| Backend | NestJS, TypeORM, GraphQL (Yoga), PostgreSQL |
| Caching | Redis |
| Queue | BullMQ |
| Testing | Jest, Playwright, Storybook |
| Monorepo | Nx workspace with Yarn 4 |
| Backend | NestJS, TypeORM, GraphQL (Yoga), PostgreSQL |
| Caching | Redis |
| Queue | BullMQ |
| Testing | Jest, Playwright, Storybook |
| Monorepo | Nx workspace with Yarn 4 |

### Package Structure

Expand Down Expand Up @@ -70,13 +70,13 @@ export default UserCard; // Use named export

### Naming Conventions

| Element | Convention | Example |
|---------|-----------|---------|
| Variables/Functions | camelCase | `userAccountBalance`, `calculateTotal` |
| Constants | SCREAMING_SNAKE_CASE | `API_ENDPOINTS`, `MAX_RETRY_COUNT` |
| Types/Classes | PascalCase | `UserService`, `ButtonProps` |
| Files/Directories | kebab-case | `user-profile.component.tsx` |
| Component Props | PascalCase + Props suffix | `UserCardProps` |
| Element | Convention | Example |
| ------------------- | ------------------------- | -------------------------------------- |
| Variables/Functions | camelCase | `userAccountBalance`, `calculateTotal` |
| Constants | SCREAMING_SNAKE_CASE | `API_ENDPOINTS`, `MAX_RETRY_COUNT` |
| Types/Classes | PascalCase | `UserService`, `ButtonProps` |
| Files/Directories | kebab-case | `user-profile.component.tsx` |
| Component Props | PascalCase + Props suffix | `UserCardProps` |

### React Guidelines

Expand Down Expand Up @@ -285,6 +285,105 @@ scope:shared -> can use: scope:shared only
scope:sdk -> can use: scope:sdk, scope:shared
```

## CI/CD Pipeline

### Overview

The repository has 24 GitHub Actions workflows covering CI, deployment, security, and automation. All CI workflows run on PRs and merge groups with concurrency controls.

### CI Workflow Matrix

| Workflow | File | Checks | Runner |
| ----------- | ----------------- | ------------------------------------------------------------------------------------------------------ | -------------------- |
| Frontend CI | `ci-front.yaml` | lint, typecheck, test, build, Storybook build/test (4 shards), coverage, E2E | depot-ubuntu-24.04-8 |
| Server CI | `ci-server.yaml` | lint, typecheck, build, unit tests, integration tests (8 shards), migration checks, GraphQL generation | depot-ubuntu-24.04-8 |
| Shared CI | `ci-shared.yaml` | lint, typecheck, test | ubuntu-latest |
| SDK CI | `ci-sdk.yaml` | SDK package checks | ubuntu-latest |
| Emails CI | `ci-emails.yaml` | Email template checks | ubuntu-latest |
| Docs CI | `ci-docs.yaml` | Documentation checks | ubuntu-latest |
| Website CI | `ci-website.yaml` | Website checks | ubuntu-latest |
| Utils CI | `ci-utils.yaml` | Danger.js PR analysis | ubuntu-latest |
| Security | `security.yaml` | CodeQL + dependency review | ubuntu-latest |

### CI Services (Backend)

Backend CI jobs spin up these services:

- **PostgreSQL** (`twentycrm/twenty-postgres-spilo`) - Primary database
- **Redis** - Caching and sessions
- **ClickHouse** (`clickhouse/clickhouse-server:25.8.8`) - Analytics (integration tests only)

### What CI Validates

1. **Lint** - ESLint with flat config (ESLint 9), including 15+ custom rules
2. **Type Check** - TypeScript via `tsgo` (native TypeScript compiler)
3. **Unit Tests** - Jest for both frontend and backend
4. **Integration Tests** - Backend tests with real PostgreSQL/Redis/ClickHouse (8 shards)
5. **Storybook Tests** - Visual regression with coverage (4 shards × 3 scopes)
6. **Build Verification** - Full production builds for frontend and backend
7. **Migration Check** - Detects uncommitted TypeORM migration changes
8. **GraphQL Schema Check** - Detects uncommitted GraphQL codegen changes
9. **E2E Tests** - Playwright tests (requires `run-e2e` label on PRs)

### Security Scanning

- **CodeQL Analysis** - Runs on PRs, main branch pushes, and weekly (Sunday midnight)
- Scans `javascript-typescript` language
- Results appear in GitHub Security tab
- **Dependency Review** - Runs on PRs, fails on `high` severity vulnerabilities
- Uses `actions/dependency-review-action@v4`
- `continue-on-error: true` (non-blocking until Dependency graph is enabled)

### Custom GitHub Actions

| Action | Location | Purpose |
| --------------- | -------------------------------- | ---------------------------------------- |
| `yarn-install` | `.github/actions/yarn-install/` | Cached Yarn 4 dependency installation |
| `nx-affected` | `.github/actions/nx-affected/` | Run Nx tasks on affected projects by tag |
| `save-cache` | `.github/actions/save-cache/` | Save build artifacts to cache |
| `restore-cache` | `.github/actions/restore-cache/` | Restore cached build artifacts |

### Pre-commit Hooks

The repository uses **Husky** + **lint-staged**:

- **`.ts`, `.tsx`, `.js`, `.jsx`** files: `eslint --fix` then `prettier --write`
- **`.json`, `.md`, `.mdx`, `.yml`, `.yaml`** files: `prettier --write`

## Custom ESLint Rules

The project maintains custom ESLint rules in `packages/twenty-eslint-rules/`:

### Frontend Rules

| Rule | Purpose |
| ---------------------------------------- | ------------------------------------------ |
| `component-props-naming` | Enforce component prop naming conventions |
| `effect-components` | Rules for effect components |
| `matching-state-variable` | State variable naming consistency |
| `no-hardcoded-colors` | Prevent hardcoded color values (use theme) |
| `styled-components-prefixed-with-styled` | Styled component naming |
| `sort-css-properties-alphabetically` | CSS property ordering |
| `no-navigate-prefer-link` | Prefer Link over navigate() |
| `no-state-useref` | Prevent state in useRef |
| `useRecoilCallback-has-dependency-array` | Recoil callback deps |
| `max-consts-per-file` | Limit constants per file |

### Backend Rules

| Rule | Purpose |
| ------------------------------------- | ----------------------------------------- |
| `inject-workspace-repository` | Workspace repository injection pattern |
| `rest-api-methods-should-be-guarded` | Ensure REST endpoints have auth guards |
| `graphql-resolvers-should-be-guarded` | Ensure GraphQL resolvers have auth guards |

### Documentation Rules

| Rule | Purpose |
| ------------------------------- | ----------------------------------------- |
| `mdx-component-newlines` | JSX tags on separate lines (i18n/Crowdin) |
| `no-angle-bracket-placeholders` | No angle bracket placeholders in MDX |

## PR Guidelines

### Before Submitting
Expand All @@ -294,6 +393,7 @@ scope:sdk -> can use: scope:sdk, scope:shared
3. Run relevant tests
4. Ensure no console errors in browser
5. Update documentation if API changes
6. Regenerate GraphQL types if schema changed: `npx nx run twenty-front:graphql:generate`

### Commit Messages

Expand All @@ -312,9 +412,23 @@ docs: update API authentication guide
- [ ] Code follows project style guidelines (ESLint, Prettier)
- [ ] Self-review completed
- [ ] Tests added/updated for new functionality
- [ ] No TypeScript errors
- [ ] No TypeScript errors (`npx nx typecheck <package>`)
- [ ] No ESLint errors (`npx nx lint:diff-with-main <package>`)
- [ ] GraphQL schema changes are backward compatible
- [ ] GraphQL types regenerated if schema changed
- [ ] Database migrations are properly structured
- [ ] No pending migration drift (CI checks automatically)
- [ ] Security: no hardcoded secrets, inputs sanitized

### Code Review Automation

The following checks run automatically on every PR:

- **Danger.js** (`ci-utils.yaml`) - PR analysis and automated comments
- **ESLint** - Via `nx-affected` with `scope:frontend` and `scope:backend` tags
- **TypeScript** - Type checking via `tsgo`
- **Tests** - Unit and integration tests for affected packages
- **Security** - CodeQL analysis and dependency vulnerability scanning

## Common Patterns

Expand Down Expand Up @@ -358,14 +472,18 @@ const result = processData(sanitizedInput);

## Important Files

| File | Purpose |
|------|---------|
| `nx.json` | Nx workspace configuration and task definitions |
| `tsconfig.base.json` | Base TypeScript configuration |
| `eslint.config.mjs` | ESLint configuration (flat config) |
| `package.json` | Root package with workspace definitions |
| `.cursor/rules/` | Development guidelines and rules |
| `CLAUDE.md` | Claude Code specific instructions |
| File | Purpose |
| ------------------------------- | ----------------------------------------------- |
| `nx.json` | Nx workspace configuration and task definitions |
| `tsconfig.base.json` | Base TypeScript configuration |
| `eslint.config.mjs` | Root ESLint flat config (ESLint 9) |
| `package.json` | Root package with workspace definitions |
| `.husky/pre-commit` | Pre-commit hook (runs lint-staged) |
| `.github/workflows/` | CI/CD pipeline (24 workflows) |
| `.github/actions/` | Custom reusable GitHub Actions |
| `packages/twenty-eslint-rules/` | Custom ESLint rules (15+ rules) |
| `.cursor/rules/` | Development guidelines and rules |
| `CLAUDE.md` | Claude Code specific instructions |

## Getting Help

Expand Down
82 changes: 80 additions & 2 deletions CLAUDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ Twenty is an open-source CRM built with modern technologies in a monorepo struct
## Key Commands

### Development

```bash
# Start development environment (frontend + backend + worker)
yarn start
Expand All @@ -20,6 +21,7 @@ npx nx run twenty-server:worker # Start background worker
```

### Testing

```bash
# Run tests
npx nx test twenty-front # Frontend unit tests
Expand All @@ -35,6 +37,7 @@ When testing the UI end to end, click on "Continue with Email" and use the prefi
```

### Code Quality

```bash
# Linting (diff with main - fastest)
npx nx lint:diff-with-main twenty-front # Lint only files changed vs main
Expand All @@ -56,13 +59,15 @@ npx nx fmt twenty-server
```

### Build

```bash
# Build packages
npx nx build twenty-front
npx nx build twenty-server
```

### Database Operations

```bash
# Database management
npx nx database:reset twenty-server # Reset database
Expand All @@ -77,6 +82,7 @@ npx nx run twenty-server:command workspace:sync-metadata
```

### GraphQL

```bash
# Generate GraphQL types
npx nx run twenty-front:graphql:generate
Expand All @@ -85,11 +91,13 @@ npx nx run twenty-front:graphql:generate
## Architecture Overview

### Tech Stack

- **Frontend**: React 18, TypeScript, Recoil (state management), Emotion (styling), Vite
- **Backend**: NestJS, TypeORM, PostgreSQL, Redis, GraphQL (with GraphQL Yoga)
- **Monorepo**: Nx workspace managed with Yarn 4

### Package Structure

```
packages/
├── twenty-front/ # React frontend application
Expand All @@ -103,6 +111,7 @@ packages/
```

### Key Development Principles

- **Functional components only** (no class components)
- **Named exports only** (no default exports)
- **Types over interfaces** (except when extending third-party interfaces)
Expand All @@ -111,47 +120,116 @@ packages/
- **Event handlers preferred over useEffect** for state updates

### State Management

- **Recoil** for global state management
- Component-specific state with React hooks
- GraphQL cache managed by Apollo Client

### Backend Architecture

- **NestJS modules** for feature organization
- **TypeORM** for database ORM with PostgreSQL
- **GraphQL** API with code-first approach
- **Redis** for caching and session management
- **BullMQ** for background job processing

### Database

- **PostgreSQL** as primary database
- **Redis** for caching and sessions
- **TypeORM migrations** for schema management
- **ClickHouse** for analytics (when enabled)

## Pre-commit Hooks

The repository uses **Husky** + **lint-staged** for pre-commit checks:

- **TypeScript/JavaScript files** (`.ts`, `.tsx`, `.js`, `.jsx`): ESLint `--fix` + Prettier `--write`
- **Config/doc files** (`.json`, `.md`, `.mdx`, `.yml`, `.yaml`): Prettier `--write`

These run automatically on `git commit`. To skip temporarily: `git commit --no-verify` (not recommended).

## CI/CD Pipeline

### Continuous Integration Workflows

| Workflow | Trigger | What it checks |
| ----------------- | ------------------------ | --------------------------------------------------------------------------------------------------------------------- |
| `ci-front.yaml` | PR, merge_group | Frontend lint, typecheck, test, build, Storybook build/test, coverage, E2E |
| `ci-server.yaml` | PR, merge_group | Backend lint, typecheck, build, unit tests, integration tests (8 shards), migration checks, GraphQL generation checks |
| `ci-shared.yaml` | PR, merge_group | Shared package lint, typecheck, test |
| `ci-sdk.yaml` | PR, merge_group | SDK checks |
| `ci-emails.yaml` | PR, merge_group | Email template checks |
| `ci-docs.yaml` | PR, merge_group | Documentation checks |
| `ci-website.yaml` | PR, merge_group | Website checks |
| `ci-utils.yaml` | PR | Danger.js PR checks |
| `security.yaml` | PR, push to main, weekly | CodeQL analysis + dependency review |

### Key CI Checks for PRs

- **Frontend**: ESLint, TypeScript type checking, Jest unit tests, Storybook build + visual tests (4 shards), build verification
- **Backend**: ESLint, TypeScript type checking, Jest unit tests, integration tests (8 shards with PostgreSQL + Redis + ClickHouse), pending migration detection, GraphQL schema drift detection
- **Security**: CodeQL static analysis, dependency vulnerability scanning (fails on `high` severity)

### Custom GitHub Actions

- `.github/actions/yarn-install/` - Cached Yarn dependency installation
- `.github/actions/nx-affected/` - Run Nx tasks on affected projects
- `.github/actions/save-cache/` and `.github/actions/restore-cache/` - Build artifact caching

## Development Workflow

IMPORTANT: Use Context7 for code generation, setup or configuration steps, or library/API documentation. Automatically use the Context7 MCP tools to resolve library IDs and get library docs without waiting for explicit requests.

### Before Making Changes

1. Always run linting and type checking after code changes
2. Test changes with relevant test suites
3. Ensure database migrations are properly structured
4. Check that GraphQL schema changes are backward compatible

### Code Style Notes

- Use **Emotion** for styling with styled-components pattern
- Follow **Nx** workspace conventions for imports
- Use **Lingui** for internationalization
- Components should be in their own directories with tests and stories

### Custom ESLint Rules

The project has its own ESLint rules in `packages/twenty-eslint-rules/`:

- `component-props-naming` - Enforce component prop naming conventions
- `effect-components` - Rules for effect components
- `matching-state-variable` - State variable naming consistency
- `no-hardcoded-colors` - Prevent hardcoded color values (use theme)
- `styled-components-prefixed-with-styled` - Styled component naming convention
- `sort-css-properties-alphabetically` - CSS property ordering
- `no-navigate-prefer-link` - Prefer Link over navigate()
- `no-state-useref` - Prevent state in useRef
- `useRecoilCallback-has-dependency-array` - Ensure Recoil callbacks have deps
- `inject-workspace-repository` - Backend workspace repository injection
- `rest-api-methods-should-be-guarded` - Ensure REST endpoints have guards
- `graphql-resolvers-should-be-guarded` - Ensure GraphQL resolvers have guards
- `max-consts-per-file` - Limit constants per file
- `mdx-component-newlines` - MDX formatting for i18n
- `no-angle-bracket-placeholders` - Prevent angle bracket placeholders in MDX

### Testing Strategy

- **Unit tests** with Jest for both frontend and backend
- **Integration tests** for critical backend workflows
- **Storybook** for component development and testing
- **Integration tests** for critical backend workflows (8 parallel shards in CI)
- **Storybook** for component development and testing (4 parallel shards in CI)
- **E2E tests** with Playwright for critical user flows
- **Coverage** enforced via Storybook coverage reports per scope (modules, pages, performance)

## Important Files

- `nx.json` - Nx workspace configuration with task definitions
- `tsconfig.base.json` - Base TypeScript configuration
- `package.json` - Root package with workspace definitions
- `eslint.config.mjs` - Root ESLint flat config (ESLint 9)
- `.husky/pre-commit` - Pre-commit hook (runs lint-staged)
- `.github/workflows/` - CI/CD pipeline definitions (24 workflows)
- `packages/twenty-eslint-rules/` - Custom ESLint rules
- `.cursor/rules/` - Development guidelines and best practices
Loading