用途
db-migration 用于为 Activepieces 服务端 API 创建 TypeORM 数据库迁移,适用于需要新增列、创建表、添加索引或进行其他 schema 变更的场景。
主要能力
该技能覆盖 schema 变更的完整流程,包括实体更新、迁移生成、文件修补、注册与代码同步,并针对 PGlite 数据库给出兼容处理方式。
工作流步骤
第一步:确定变更
在生成前需明确:受影响的表;所需 SQL(ADD COLUMN、CREATE TABLE、CREATE INDEX 等);迁移是否为破坏性(删除列或表、不可逆的数据转换,无法安全回滚);当前发布版本(检查根目录 package.json 的 version)。
第二步:更新实体
更新 packages/server/api/src/app/ 下的 TypeORM 实体文件以反映新 schema,确保 CLI 生成命令能基于当前状态进行 diff。数组列统一使用以下模式:
columnName: {
type: String,
array: true,
nullable: false,
}
第三步:使用 CLI 生成迁移
在 packages/server/api/ 目录下运行:
npm run db-migration -- src/app/database/migration/postgres/MigrationName
该命令会对比当前实体状态与数据库,生成包含正确 SQL 和时间戳的迁移文件。
第四步:修补生成的文件
CLI 生成的文件使用 MigrationInterface,必须修补为项目自定义的 Migration 接口并补齐必填字段:
- 将
import { MigrationInterface, QueryRunner } from "typeorm"替换为import { QueryRunner } from 'typeorm',并添加import { Migration } from '../../migration' - 将
implements MigrationInterface替换为implements Migration - 添加
breaking = false(若为破坏性变更则设为 true) - 添加
release = '<version>',与根目录 package.json 中即将发布的版本一致 - 确认 down() 正确反转 up()
示例结果:
import { QueryRunner } from 'typeorm'
import { Migration } from '../../migration'
export class AddMyColumn1234567890 implements Migration {
name = 'AddMyColumn1234567890'
breaking = false
release = '0.78.0'
public async up(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(`ALTER TABLE "project" ADD COLUMN "description" text`)
}
public async down(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(`ALTER TABLE "project" DROP COLUMN "description"`)
}
}
必填字段:breaking = false(仅当回滚具有破坏性时设为 true);release = '<version>'(根目录 package.json 中即将发布的版本);down() 必须反转 up()。缺少任一字段 CI 都会失败。
第五步:注册迁移
打开 packages/server/api/src/app/database/postgres-connection.ts,将新迁移类添加到 getMigrations() 数组末尾(按时间顺序):
import { AddMyColumn1234567890 } from './migration/postgres/1234567890-AddMyColumn'
// Inside getMigrations():
return [
// ... existing migrations ...
AddMyColumn1234567890,
]
第六步:更新类型与服务代码
迁移生成并注册后,更新所有引用变更列的 TypeScript 类型、服务文件或其他代码,使其与新 schema 保持同步。
注意事项
尽可能创建非破坏性迁移以支持安全回滚;任务完成前要求零错误。
PGlite 兼容性
PGlite 为单连接嵌入式数据库,不支持 CONCURRENTLY。使用 CONCURRENTLY 创建或删除索引时,需添加 PGlite 判断:
import { QueryRunner } from 'typeorm'
import { Migration } from '../../migration'
import { system } from '../../../helper/system/system'
import { AppSystemProp } from '../../../helper/system/system-props'
import { DatabaseType } from '../../database-type'
const isPGlite = system.get(AppSystemProp.DB_TYPE) === DatabaseType.PGLITE
export class AddMyIndex1234567890 implements Migration {
name = 'AddMyIndex1234567890'
breaking = false
release = '0.78.0'
transaction = false // Required when using CONCURRENTLY
public async up(queryRunner: QueryRunner): Promise<void> {
if (isPGlite) {
await queryRunner.query(`CREATE INDEX "idx_name" ON "table" ("column")`)
} else {
await queryRunner.query(`CREATE INDEX CONCURRENTLY "idx_name" ON "table" ("column")`)
}
}
public async down(queryRunner: QueryRunner): Promise<void> {
if (isPGlite) {
await queryRunner.query(`DROP INDEX "idx_name"`)
} else {
await queryRunner.query(`DROP INDEX CONCURRENTLY "idx_name"`)
}
}
}
只要使用 CONCURRENTLY 就必须设置 transaction = false,这是 PostgreSQL 的要求。
快速参考
| 项目 | 值 |
|---|---|
| 迁移文件位置 | packages/server/api/src/app/database/migration/postgres/ |
| 注册位置 | packages/server/api/src/app/database/postgres-connection.ts |
| 迁移导入 | import { Migration } from '../../migration' |
| 生成命令 | npm run db-migration -- src/app/database/migration/postgres/MigrationName(在 packages/server/api/ 下运行) |
关键提醒
- 始终通过 CLI 生成,切勿手写迁移 SQL;使用 npm run db-migration 从实体 diff 生成
- 切勿使用 MigrationInterface;务必将生成文件修补为使用 ../../migration 的 Migration
- breaking、release 和 down() 为必填项;缺少则 CI 拒绝该迁移
- 必须在 postgres-connection.ts 中注册;否则迁移不会运行
- PGlite + CONCURRENTLY:始终使用 isPGlite 判断并设置 transaction = false
适用场景与限制
适用于 Activepieces 服务端 API 的数据库 schema 变更,涵盖添加列、创建表、创建索引等操作。使用前提是具备 Activepieces 仓库的 packages/server/api/ 目录结构,并按上述流程操作。目前提供的资料未涉及该技能的收费、价格、平台等其它信息。