mirror of
https://github.com/twentyhq/twenty
synced 2026-04-21 13:37:22 +00:00
Upgrade command internal doc (#19541)
Open to discussion not sure on where to store such documentation
This commit is contained in:
parent
186bc02533
commit
847e7124d7
6 changed files with 178 additions and 37 deletions
|
|
@ -71,10 +71,10 @@ npx nx build twenty-server
|
|||
# Database management
|
||||
npx nx database:reset twenty-server # Reset database
|
||||
npx nx run twenty-server:database:init:prod # Initialize database
|
||||
npx nx run twenty-server:database:migrate:prod # Run migrations
|
||||
npx nx run twenty-server:database:migrate:prod # Run instance commands (fast only)
|
||||
|
||||
# Generate migration
|
||||
npx nx run twenty-server:database:migrate:generate
|
||||
# Generate an instance command (fast or slow)
|
||||
npx nx run twenty-server:database:migrate:generate --name <name> --type <fast|slow>
|
||||
```
|
||||
|
||||
### Database Inspection (Postgres MCP)
|
||||
|
|
@ -158,14 +158,17 @@ packages/
|
|||
- **Redis** for caching and session management
|
||||
- **BullMQ** for background job processing
|
||||
|
||||
### Database & Migrations
|
||||
### Database & Upgrade Commands
|
||||
- **PostgreSQL** as primary database
|
||||
- **Redis** for caching and sessions
|
||||
- **ClickHouse** for analytics (when enabled)
|
||||
- Always generate migrations when changing entity files
|
||||
- Migration names must be kebab-case (e.g. `add-agent-turn-evaluation`)
|
||||
- Include both `up` and `down` logic in migrations
|
||||
- Never delete or rewrite committed migrations
|
||||
- When changing entity files, generate an **instance command** (`database:migrate:generate --name <name> --type <fast|slow>`)
|
||||
- **Fast** instance commands handle schema changes; **slow** ones add a `runDataMigration` step for data backfills
|
||||
- **Workspace commands** iterate over all active/suspended workspaces for per-workspace upgrades
|
||||
- Commands use `@RegisteredInstanceCommand` and `@RegisteredWorkspaceCommand` decorators for automatic discovery
|
||||
- Include both `up` and `down` logic in instance commands
|
||||
- Never delete or rewrite committed instance command `up`/`down` logic
|
||||
- See `packages/twenty-server/docs/UPGRADE_COMMANDS.md` for full documentation
|
||||
|
||||
### Utility Helpers
|
||||
Use existing helpers from `twenty-shared` instead of manual type guards:
|
||||
|
|
@ -178,7 +181,7 @@ IMPORTANT: Use Context7 for code generation, setup or configuration steps, or li
|
|||
### Before Making Changes
|
||||
1. Always run linting (`lint:diff-with-main`) and type checking after code changes
|
||||
2. Test changes with relevant test suites (prefer single-file test runs)
|
||||
3. Ensure database migrations are generated for entity changes
|
||||
3. Ensure instance commands are generated for entity changes (`database:migrate:generate`)
|
||||
4. Check that GraphQL schema changes are backward compatible
|
||||
5. Run `graphql:generate` after any GraphQL schema changes
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ This directory contains Twenty's development guidelines and best practices in th
|
|||
### Core Guidelines
|
||||
- **architecture.mdc** - Project overview, technology stack, and infrastructure setup (Always Applied)
|
||||
- **nx-rules.mdc** - Nx workspace guidelines and best practices (Auto-attached to Nx files)
|
||||
- **server-migrations.mdc** - Backend migration and TypeORM guidelines for `twenty-server` (Auto-attached to server entities and migration files)
|
||||
- **server-migrations.mdc** - Upgrade command guidelines (instance commands and workspace commands) for `twenty-server` (Auto-attached to server entities and upgrade command files)
|
||||
- **creating-syncable-entity.mdc** - Comprehensive guide for creating new syncable entities (with universalIdentifier and applicationId) in the workspace migration system (Agent-requested for metadata-modules and workspace-migration files)
|
||||
|
||||
### Code Quality
|
||||
|
|
@ -81,10 +81,8 @@ npx nx run twenty-server:typecheck # Type checking
|
|||
npx nx run twenty-server:test # Run unit tests
|
||||
npx nx run twenty-server:test:integration:with-db-reset # Run integration tests
|
||||
|
||||
# Migrations
|
||||
npx nx run twenty-server:database:migrate:generate
|
||||
|
||||
# Workspace
|
||||
# Upgrade commands (instance + workspace)
|
||||
npx nx run twenty-server:database:migrate:generate --name <name> --type <fast|slow>
|
||||
```
|
||||
|
||||
## Usage Guidelines
|
||||
|
|
|
|||
|
|
@ -55,7 +55,8 @@ If feature descriptions are not provided or need enhancement, research the codeb
|
|||
- Services: Look for `*.service.ts` files
|
||||
|
||||
**For Database/ORM Changes:**
|
||||
- Migrations: `packages/twenty-server/src/database/typeorm/`
|
||||
- Instance commands (fast/slow): `packages/twenty-server/src/database/commands/upgrade-version-command/`
|
||||
- Legacy TypeORM migrations: `packages/twenty-server/src/database/typeorm/`
|
||||
- Entities: `packages/twenty-server/src/entities/`
|
||||
|
||||
### Research Commands
|
||||
|
|
|
|||
|
|
@ -1,27 +1,46 @@
|
|||
---
|
||||
description: Guidelines for generating and managing TypeORM migrations in twenty-server
|
||||
description: Guidelines for generating and managing upgrade commands (instance commands and workspace commands) in twenty-server
|
||||
globs: [
|
||||
"packages/twenty-server/src/**/*.entity.ts",
|
||||
"packages/twenty-server/src/database/typeorm/**/*.ts"
|
||||
"packages/twenty-server/src/database/commands/upgrade-version-command/**/*.ts"
|
||||
]
|
||||
alwaysApply: false
|
||||
---
|
||||
|
||||
## Server Migrations (twenty-server)
|
||||
## Upgrade Commands (twenty-server)
|
||||
|
||||
- **When changing an entity, always generate a migration**
|
||||
- If you modify a `*.entity.ts` file in `packages/twenty-server/src`, you **must** generate a corresponding TypeORM migration instead of manually editing the database schema.
|
||||
- Use the Nx command from the project root:
|
||||
The upgrade system uses two types of commands instead of raw TypeORM migrations:
|
||||
- **Instance commands** — schema and data migrations that run once at the instance level.
|
||||
- **Workspace commands** — commands that iterate over all active/suspended workspaces.
|
||||
|
||||
See `packages/twenty-server/docs/UPGRADE_COMMANDS.md` for full documentation.
|
||||
|
||||
### Instance Commands
|
||||
|
||||
- **When changing a `*.entity.ts` file**, generate an instance command:
|
||||
|
||||
```bash
|
||||
npx nx run twenty-server:database:migrate:generate
|
||||
npx nx run twenty-server:database:migrate:generate --name <name> --type <fast|slow>
|
||||
```
|
||||
|
||||
- **Prefer generated migrations over manual edits**
|
||||
- Let TypeORM infer schema changes from the updated entities; only adjust the generated migration file manually if absolutely necessary (for example, for data backfills or complex constraints).
|
||||
- Keep schema changes (DDL) in these generated migrations and avoid mixing in heavy data migrations unless there is a strong reason and clear comments.
|
||||
- **Fast commands** (`--type fast`, default) are for schema-only changes that must run immediately. They implement `FastInstanceCommand` with `up`/`down` methods and use the `@RegisteredInstanceCommand` decorator.
|
||||
|
||||
- **Keep migrations consistent and reversible**
|
||||
- Ensure the generated migration includes both `up` and `down` logic that correctly applies and reverts the entity change when possible.
|
||||
- Do not delete or rewrite existing, committed migrations unless you are explicitly working on a pre-release branch where history rewrites are allowed by team conventions.
|
||||
- **Slow commands** (`--type slow`) add a `runDataMigration` method for potentially long-running data backfills that execute before `up`. They only run when `--include-slow` is passed. Use the decorator with `{ type: 'slow' }`.
|
||||
|
||||
- The generator auto-registers the command in `instance-commands.constant.ts` — do not edit that file manually.
|
||||
|
||||
- **Keep commands consistent and reversible**: include both `up` and `down` logic. Do not delete or rewrite existing, committed commands unless on a pre-release branch.
|
||||
|
||||
### Workspace Commands
|
||||
|
||||
- Use the `@RegisteredWorkspaceCommand` decorator alongside nest-commander's `@Command` decorator.
|
||||
- Extend `ActiveOrSuspendedWorkspaceCommandRunner` and implement `runOnWorkspace`.
|
||||
- The base class provides `--dry-run`, `--verbose`, and workspace filter options automatically.
|
||||
|
||||
### Execution Order
|
||||
|
||||
Within a given version, commands run in this order (timestamp-sorted within each group):
|
||||
1. Instance fast commands
|
||||
2. Instance slow commands (only with `--include-slow`)
|
||||
3. Workspace commands
|
||||
|
||||
|
|
|
|||
21
CLAUDE.md
21
CLAUDE.md
|
|
@ -71,10 +71,10 @@ npx nx build twenty-server
|
|||
# Database management
|
||||
npx nx database:reset twenty-server # Reset database
|
||||
npx nx run twenty-server:database:init:prod # Initialize database
|
||||
npx nx run twenty-server:database:migrate:prod # Run migrations
|
||||
npx nx run twenty-server:database:migrate:prod # Run instance commands (fast only)
|
||||
|
||||
# Generate migration
|
||||
npx nx run twenty-server:database:migrate:generate
|
||||
# Generate an instance command (fast or slow)
|
||||
npx nx run twenty-server:database:migrate:generate --name <name> --type <fast|slow>
|
||||
```
|
||||
|
||||
### Database Inspection (Postgres MCP)
|
||||
|
|
@ -158,14 +158,17 @@ packages/
|
|||
- **Redis** for caching and session management
|
||||
- **BullMQ** for background job processing
|
||||
|
||||
### Database & Migrations
|
||||
### Database & Upgrade Commands
|
||||
- **PostgreSQL** as primary database
|
||||
- **Redis** for caching and sessions
|
||||
- **ClickHouse** for analytics (when enabled)
|
||||
- Always generate migrations when changing entity files
|
||||
- Migration names must be kebab-case (e.g. `add-agent-turn-evaluation`)
|
||||
- Include both `up` and `down` logic in migrations
|
||||
- Never delete or rewrite committed migrations
|
||||
- When changing entity files, generate an **instance command** (`database:migrate:generate --name <name> --type <fast|slow>`)
|
||||
- **Fast** instance commands handle schema changes; **slow** ones add a `runDataMigration` step for data backfills
|
||||
- **Workspace commands** iterate over all active/suspended workspaces for per-workspace upgrades
|
||||
- Commands use `@RegisteredInstanceCommand` and `@RegisteredWorkspaceCommand` decorators for automatic discovery
|
||||
- Include both `up` and `down` logic in instance commands
|
||||
- Never delete or rewrite committed instance command `up`/`down` logic
|
||||
- See `packages/twenty-server/docs/UPGRADE_COMMANDS.md` for full documentation
|
||||
|
||||
### Utility Helpers
|
||||
Use existing helpers from `twenty-shared` instead of manual type guards:
|
||||
|
|
@ -178,7 +181,7 @@ IMPORTANT: Use Context7 for code generation, setup or configuration steps, or li
|
|||
### Before Making Changes
|
||||
1. Always run linting (`lint:diff-with-main`) and type checking after code changes
|
||||
2. Test changes with relevant test suites (prefer single-file test runs)
|
||||
3. Ensure database migrations are generated for entity changes
|
||||
3. Ensure instance commands are generated for entity changes (`database:migrate:generate`)
|
||||
4. Check that GraphQL schema changes are backward compatible
|
||||
5. Run `graphql:generate` after any GraphQL schema changes
|
||||
|
||||
|
|
|
|||
117
packages/twenty-server/docs/UPGRADE_COMMANDS.md
Normal file
117
packages/twenty-server/docs/UPGRADE_COMMANDS.md
Normal file
|
|
@ -0,0 +1,117 @@
|
|||
# Upgrade Commands
|
||||
|
||||
The upgrade process relies on two types of commands:
|
||||
|
||||
- **Instance commands** — schema and data migrations that run once at the instance level (replacing raw TypeORM migrations).
|
||||
- **Workspace commands** — commands that iterate over all active or suspended workspaces to apply per-workspace changes.
|
||||
|
||||
Both are registered via decorators and automatically discovered by the upgrade pipeline.
|
||||
|
||||
## Instance Commands
|
||||
|
||||
### Generating an instance command
|
||||
|
||||
```bash
|
||||
npx nx run twenty-server:database:migrate:generate --name <name> --type <fast|slow>
|
||||
```
|
||||
|
||||
This generates a timestamped file and auto-registers it in `instance-commands.constant.ts` — do not edit that file manually.
|
||||
|
||||
### Fast instance commands
|
||||
|
||||
Fast commands run immediately during the upgrade. They are used for schema changes that could introduce breaking inconsistencies between the database and the server if delayed.
|
||||
|
||||
A fast command implements `FastInstanceCommand` and provides `up` / `down` methods:
|
||||
|
||||
```ts
|
||||
@RegisteredInstanceCommand('1.22.0', 1775758621017)
|
||||
export class AddWorkspaceIdToTotoFastInstanceCommand
|
||||
implements FastInstanceCommand
|
||||
{
|
||||
public async up(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(
|
||||
`ALTER TABLE "core"."toto" ADD "workspaceId" uuid`,
|
||||
);
|
||||
}
|
||||
|
||||
public async down(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(
|
||||
`ALTER TABLE "core"."toto" DROP COLUMN "workspaceId"`,
|
||||
);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Slow instance commands
|
||||
|
||||
Slow commands are used when a potentially long-running data migration must happen before the schema change. They only run when the `--include-slow` flag is passed.
|
||||
|
||||
A slow command implements `SlowInstanceCommand`, which extends `FastInstanceCommand` with an additional `runDataMigration` method that executes before `up`:
|
||||
|
||||
```ts
|
||||
@RegisteredInstanceCommand('1.22.0', 1775758621018, { type: 'slow' })
|
||||
export class BackfillWorkspaceIdSlowInstanceCommand
|
||||
implements SlowInstanceCommand
|
||||
{
|
||||
async runDataMigration(dataSource: DataSource): Promise<void> {
|
||||
// Backfill logic (can be slow — e.g. iterating over workspaces, cache recomputation)
|
||||
}
|
||||
|
||||
public async up(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(
|
||||
`ALTER TABLE "core"."toto" ALTER COLUMN "workspaceId" SET NOT NULL`,
|
||||
);
|
||||
}
|
||||
|
||||
public async down(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(
|
||||
`ALTER TABLE "core"."toto" ALTER COLUMN "workspaceId" DROP NOT NULL`,
|
||||
);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
A common pattern is to pair a **fast** command (add a nullable column) with a **slow** command (backfill existing rows, then set `NOT NULL`).
|
||||
|
||||
## Workspace Commands
|
||||
|
||||
Workspace commands run per-workspace logic across all active or suspended workspaces. They are registered with the `@RegisteredWorkspaceCommand` decorator alongside nest-commander's `@Command` decorator:
|
||||
|
||||
```ts
|
||||
@RegisteredWorkspaceCommand('1.22.0', 1780000002000)
|
||||
@Command({
|
||||
name: 'upgrade:1-22:backfill-standard-skills',
|
||||
description:
|
||||
'Backfill standard skills for existing workspaces',
|
||||
})
|
||||
export class BackfillStandardSkillsCommand
|
||||
extends ActiveOrSuspendedWorkspaceCommandRunner
|
||||
{
|
||||
constructor(
|
||||
protected readonly workspaceIteratorService: WorkspaceIteratorService,
|
||||
// inject any services you need
|
||||
) {
|
||||
super(workspaceIteratorService);
|
||||
}
|
||||
|
||||
override async runOnWorkspace({
|
||||
workspaceId,
|
||||
options,
|
||||
}: RunOnWorkspaceArgs): Promise<void> {
|
||||
// Per-workspace logic goes here
|
||||
// options.dryRun, options.verbose are available for free
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
The base class `ActiveOrSuspendedWorkspaceCommandRunner` handles workspace iteration and provides `--dry-run`, `--verbose`, and workspace filter options automatically.
|
||||
|
||||
## Execution Order
|
||||
|
||||
Within a given version of Twenty, the upgrade pipeline runs commands in this order, sorted by timestamp within each group:
|
||||
|
||||
1. **Instance fast** commands
|
||||
2. **Instance slow** commands
|
||||
3. **Workspace commands**
|
||||
|
||||
Workspace commands are executed sequentially across all active/suspended workspaces.
|
||||
Loading…
Reference in a new issue