首页
/ TypeORM 开发环境搭建与构建测试实战:从克隆仓库到发布 npm 包

TypeORM 开发环境搭建与构建测试实战:从克隆仓库到发布 npm 包

2026-09-05 10:19:24作者:温艾琴Wonderful

本文基于 TypeORM 仓库根目录的开发者指南 DEVELOPER.md,系统讲解如何搭建 TypeORM 的本地开发环境:安装依赖、配置多数据库测试连接(ormconfig.json)、用 Docker 一键拉起 13 种数据库、构建可分发的 build/package 产物、编写并快速迭代 Mocha 测试,以及 master/v0 双分支的发布流程。读完本文,你可以独立完成从克隆代码到跑通全量测试、乃至走通一次稳定版/预发布/nightly 发布的完整闭环。

一、环境前置与工具链版本

在构建和测试 TypeORM 之前,开发机上需要以下工具:

  • Git:用于克隆仓库与维护 fork/upstream 远程;
  • Node.js:建议使用 fnm 或 nvm 等版本管理器安装。注意 package.json 对运行环境有硬性约束:"node": "^20.19.0 || ^22.13.0 || >=24.11.0",同时 package.json 通过 "packageManager": "pnpm@10.34.4"devEngines 字段锁定了 pnpm 10.34.4,版本不符会直接报错;
  • 数据库(本地安装或 Docker 均可):MySQL、MariaDB、PostgreSQL 为必需测试平台;Oracle、Microsoft SQL Server 同理。

各数据库连接所需的驱动(mysql2pgmssqloracledbmongodbbetter-sqlite3sql.js@sap/hana-client@google-cloud/spanner 等)都声明在 package.jsonpeerDependencies(均为可选)或 devDependencies 中,pnpm install 会一并安装,无需手动处理。

官方提供了 docker-compose.yml,可以只拉起某个数据库,例如:

docker compose up postgres-17

二、获取源码

贡献者需要 Fork 并克隆仓库(可参考 CONTRIBUTING.md 的贡献规范):

  1. 登录你的 GitHub 账号(或注册一个);
  2. Fork TypeORM 主仓库到你的账号下;
  3. 克隆自己的 fork,并添加指向上游主仓库的 upstream 远程:
# 克隆仓库(以下为镜像地址,Fork 后请替换为你自己的 fork 地址)
git clone https://gitcode.com/GitHub_Trending/ty/typeorm.git

# 进入 TypeORM 目录
cd typeorm

# 添加上游主仓库作为 upstream 远程
git remote add upstream <上游主仓库地址>

三、安装依赖与配置 ormconfig.json

3.1 安装依赖

pnpm install

3.2 创建测试配置文件

cp ormconfig.sample.json ormconfig.json

ormconfig.sample.json 是一个 JSON 数组,每个元素描述一种数据库驱动的测试连接,示例文件共包含 13 条配置,覆盖:aurora-mysqlaurora-postgres(默认 "skip": true,因为需要 AWS RDS Data API 凭据)、better-sqlite3cockroachdbmariadbmongodbmssqlmysqloraclepostgressap(HANA Express)、spannersqljs

其中两个控制字段决定了测试会连接哪些数据库,语义定义在 test/utils/test-utils.ts

字段 作用 源码行为
skip true 时该连接永远不参与测试 setupTestingConnectionsif (connectionOptions.skip === true) return false
disabledIfNotEnabledImplicitly true 时,除非测试代码显式声明 enabledDrivers 包含该驱动,否则不启用 同文件 L243-L244 的过滤分支(如示例中的 mongodb 条目)

示例中的账号口令与 docker-compose.yml 中各容器注入的环境变量一一对应(如 Postgres 的 username/password、MariaDB 的 root/admin、MSSQL 的 sa/Admin12345trustServerCertificate: true),因此只要按 compose 文件启动容器,即可直接复用示例配置,只需把不想跑的数据库标记 "skip": true 即可。

配置文件位置的解析逻辑见 getOrmFilepath:优先找 build/compiled/ormconfig.json(便于在 Docker CI 中注入自定义配置),找不到再回退到仓库根目录;两者都不存在时会抛出明确报错提示你从 ormconfig.sample.json 复制。

四、用 Docker 一键启动全部数据库

除了单个数据库,可以在项目根目录直接运行 docker compose up 拉起 docker-compose.yml 中的全部 13 个服务,再执行测试。各服务的镜像与端口映射如下:

服务 镜像 宿主机端口 备注
mysql-5 mysql:5.7.44 3306 mysql-9 共用 3306,二者不要同时跑
mysql-9 mysql:9.5.0 3306 同上
mariadb-10 mariadb:10.11.16 3307 mariadb-12 共用 3307
mariadb-12 mariadb:12.2.2 3307 同上
postgres-14 ghcr.io/typeorm/docker:postgres-14.22-postgis-3.6.2-pgvector-0.8.2 5432 内置 PostGIS + pgvector
postgres-17 ghcr.io/typeorm/docker:postgres-17.9-postgis-3.6.2-pgvector-0.8.2 5432 同上
mssql mcr.microsoft.com/mssql/server:2025-latest 1433 Express 版
cockroachdb cockroachdb/cockroach:v24.3.8 26257 单节点 insecure 模式
oracle container-registry.oracle.com/database/free:23.7.0.0-lite 1521 启动脚本挂载自 docker/oracle/startup
spanner roryq/spanner-emulator:latest 9010/9020 Spanner 模拟器
hanaexpress saplabs/hanaexpress:2.00.088... 39041 仅 Linux,Docker 至少 10GB 内存
mongodb mongo:8.2.5 27017

两个资源提示(来自 DEVELOPER.md):

  • MSSQL Server 镜像至少需要 3.25GB 内存
  • 在 Docker for Mac / Windows 上请为 Docker 虚拟机分配足够的内存。

注意同一端口冲突的服务(两个 MySQL、两个 MariaDB、两个 Postgres)不能同时运行,按你要测的驱动挑一个即可。

五、构建可分发包(pnpm run package

构建 TypeORM 的分发产物:

pnpm run package

该命令在 package.json 中映射为 gulp package,其任务编排见 gulpfile.ts:先清空 ./build,然后并行执行「拷贝浏览器端源码(排除 src/commands/src/cli.ts 等 Node 专属模块)+ 拷贝 src/platform/*.template 平台模板」与「tsc -p tsconfig.node.json / tsc -p tsconfig.browser.json 双端编译」,最后生成 ESM 入口、整理 package.json、拷贝 README 与 shim 文件。完成后:

  • build/package 目录:一个可以直接使用(npm link 或整体拷贝)的 TypeORM 发行目录。你可以把它链接或拷贝到项目里测试(注意保留 TypeORM 所需的 node_modules);
  • 其中的 copyPackageFile 步骤会剥离开发脚本,但特意保留 @types/nodets-nodetypescript 三个 devDependency——因为 typeorm init 命令生成脚手架项目时要把它们写进目标项目的 package.json
  • 生成的 index.mjsnodeCreateEsmIndex 动态扫描 CJS 导出生成,保证 importrequire 的具名导出一致(对应 package.jsonexports 双入口设计)。

打成 npm tar 包:

cd build/package && pnpm pack

会在 build 目录生成 build/typeorm-x.x.x.tgz(版本号取自 package.json,当前仓库版本为 1.1.0,即 v1.x 稳定线)。你可以把 tar 包拷入任意项目,然后:

npm install ./typeorm-x.x.x.tgz

即可把你本地构建的 TypeORM 打进依赖。

六、本地编写与运行测试

6.1 测试基建与标准模板

仓库鼓励「改代码的 PR 附带相应测试」。新测试应参考 test/functional/ 下已有的功能测试,视情况新建 .test.ts 文件或修改现有文件;如果是针对某个 GitHub issue 的回归测试,请在测试中用注释注明 issue 编号(仓库 test/github-issues/ 目录即按 issue 编号组织)。

测试统一使用 test/utils/test-utils.ts 提供的工具函数,标准模板如下(与 DEVELOPER.md 一致,可原样复制):

import { expect } from "chai"
import {
    closeTestingConnections,
    createTestingConnections,
    reloadTestingDatabases,
} from "../../../utils/test-utils"
import { DataSource } from "../../../../src/data-source/DataSource"

describe("description of the functionality you're testing", () => {
    let dataSources: DataSource[]

    before(
        async () =>
            (dataSources = await createTestingConnections({
                entities: [__dirname + "/entity/*{.js,.ts}"],
                schemaCreate: true,
                dropSchema: true,
            })),
    )
    beforeEach(() => reloadTestingDatabases(dataSources))
    after(() => closeTestingConnections(dataSources))

    // optional: test fix for issue https://github.com/typeorm/typeorm/issues/<issue-number>
    it("should <put a detailed description of what it should do here>", () =>
        Promise.all(
            dataSources.map(async (dataSource) => {
                // tests go here:
                expect(result).to.equal(expected)
            }),
        ))

    // you can add additional tests if needed
})

模板要点,结合源码进一步说明:

  • 同一用例在多个数据库上重复执行createTestingConnections 会遍历 ormconfig.json 中所有启用的连接,为每个驱动 new DataSource(options).initialize()(见 createTestingConnections),因此 it 内部用 Promise.all(dataSources.map(...)) 对每个连接断言,一份用例天然覆盖多种 DBMS;
  • 实体自动加载:把实体放在测试文件同级的 ./entity/<entity-name>.ts 中即会被加载——setupTestingConnections 会把 __dirname 选项转写为 entities: [__dirname + "/entity/*{.js,.ts}"]migrations: [__dirname + "/migration/*{.js,.ts}"] 两个 glob;
  • schemaCreate / dropSchema:前者映射为连接的 synchronize: true(建表),后者在连接建立时先清库;beforeEach 中的 reloadTestingDatabases 负责在每个用例前重置数据,保证用例间隔离;
  • 驱动级裁剪createTestingConnectionsTestingOptionstest/utils/test-utils.ts)还支持 enabledDrivers / disabledDrivers(按 L230-L247 的过滤链:先 skip,再 disabledDrivers,再 enabledDrivers,最后 disabledIfNotEnabledImplicitly)、cache(database/redis 缓存策略)、namingStrategymetadataTableNamerelationLoadStrategy"join""query")等参数,用于针对特定驱动行为编写用例。个别数据库还有额外初始化,例如 createTestingConnections 会为 CockroachDB 调低副本数、为 MySQL 打开 performance_schema 的事务事件,支撑其性能相关测试。

6.2 运行测试

先确保已复制 ormconfig.sample.jsonormconfig.json 并替换为你本地的连接参数。测试会对文件中每个定义的数据库各跑一遍;如果你改动的功能与特定数据库无关,可以删掉部分连接对象(或置 "skip": true)来加快反馈速度。

pnpm run test

package.json 可见其实际为 pnpm run compile && pnpm run test:fast --:先删除旧产物、重新编译整个 TypeScript 代码库,再用 Mocha 执行。Mocha 的运行细节由 .mocharc.json 决定:只运行 ./build/compiled/test/**/*.test.{js,ts} 下的编译产物(这就是必须先 compile 的原因)、单测超时 90 秒、加载 test/utils/test-setup.js 全局初始化文件、开启泄漏检查(mongodb@7.2+allowedDriverRequire 已被列入白名单)。另有 pnpm run test:cimocha --bail,供 CI 首个失败即中止。

提交 PR 前应确认测试套件通过:PR 会在 GitHub Actions 上跑测试(需审批后触发),你的 fork 仓库自身也应能跑 CI;所有测试通过是 PR 合并的前提

6.3 只运行部分测试

方式一:给目标 describe / it 临时加上 Mocha 的 .only(对应 describe.onlyit.only):

describe.only('your describe test', ....)

方式二:用 --grep 传正则给 Mocha,只有匹配的 describe/it 会执行:

pnpm run test -- --grep "your test name"

test 脚本末尾的 -- 会把参数原样透传给 Mocha。)

6.4 更快的开发循环

pnpm run test 每次都会删除已构建的 TypeScript 代码并全量重编,耗时较长。更快的节奏是:

pnpm run compile -- --watch

这会先做一次全新构建,随后让 TypeScript 进入 watch 模式、只增量编译你改动的代码(compile 脚本为 gulp clean && tsc--watch 最终附加在 tsc 上)。编译完成后改用:

pnpm run test:fast

test:fast 直接执行 mochapackage.json),不再触发重编译,从而显著加快「改代码 → 看结果」的循环。

七、发布流程:双分支与 npm 发布

TypeORM 维护两条活跃分支(与 DEVELOPER.md 的表格一致):

分支 npm dist-tag(稳定版) npm dist-tag(nightly) 定位
master latest dev v1.x(稳定线,当前仓库版本 1.1.0)
v0 legacy nightly v0.3.x(遗留线)

发布由 publish-package.yml 工作流承担,采用 npm Trusted Publishing(OIDC),全程无需 npm token。该工作流有单文件约束(Trusted Publishing 每个包只支持一个工作流文件),因此稳定版、预发布、nightly 的逻辑全部收敛在这一个文件里,由三个触发器驱动:release: published 事件、Cron 定时任务 0 2 * * *(即每天 02:00 UTC)、以及 workflow_dispatch 手动触发(可选目标 release / master / v0)。

7.1 稳定版(Stable release)

  1. 从目标分支拉出发布分支(例如从 v0release-0.3.32,或从 masterrelease-1.1.1);
  2. 更新 package.json 中的版本号;
  3. 运行 pnpm run changelog(即 package.json 中映射的 standard-changelog)生成变更日志;
  4. 提交变更并创建指向发布分支的 Pull Request;
  5. 合并后,创建与版本号一致的 GitHub Release(如 0.3.321.1.1)并打同名 tag;
  6. 工作流被 release: published 事件触发,自动发布到 npm。dist-tag 按规则自动判定:版本号大于 npm 上当前 latest 时打 latest,否则打 legacy(工作流头部注释明确了该判定,防止旧分支覆盖新发布)。

7.2 预发布(Pre-release,面向 v1.0 阶段)

  1. master 拉分支(如 release-1.0.0-alpha.2);
  2. 更新 package.json 版本号为预发布标识(如 1.0.0-alpha.2);
  3. 运行 pnpm run changelog 生成变更日志;
  4. 提交变更并创建指向 master 的 Pull Request;
  5. 合并后,从 master 创建带匹配 tag 的 GitHub Release,并勾选 pre-release
  6. 工作流发布到 npm 时自动使用 next dist-tag——任何包含预发布标识(如 -alpha-beta)的版本号都会被判定为 next

7.3 Nightly 构建

masterv0 的 nightly 版本在每天 02:00 UTC 自动发布,前提是「自上一次 nightly 发布以来有新 commit」(工作流通过对比 HEAD 与该 dist-tag 最近一次发布记录的 gitHead 实现跳过逻辑),也可通过 workflow_dispatch 手动触发。nightly 在 npm 上的 dist-tag 为:masterdevv0nightly。定时触发时还会为两条分支分别指定 Node 版本(master 用 Node 24,v0 用 Node 20,见 publish-package.yml 的 matrix 逻辑)。

小结

围绕 DEVELOPER.md 的主线,TypeORM 开发者工作流可归纳为:pnpm install + cp ormconfig.sample.json ormconfig.json 完成环境准备 → docker compose up(或单库 docker compose up postgres-17)准备数据库 → pnpm run test(日常迭代用 compile -- --watch + test:fast + --grep 提速)→ pnpm run package / pnpm pack 产出可分发包 → 按双分支策略走稳定版、预发布或 nightly 发布。所有关键机制——连接过滤(skip / disabledIfNotEnabledImplicitly)、Mocha 编译产物规格(.mocharc.json)、打包管线(gulpfile.ts)与发布矩阵(publish-package.yml)——都可以在上述仓库文件中逐行查证。

登录后查看全文
热门项目推荐
相关项目推荐

项目优选

收起
kernelkernel
deepin linux kernel
C
33
18
ops-transformerops-transformer
本项目是CANN提供的transformer类大模型算子库,实现网络在NPU上加速计算。
C++
1.12 K
2.72 K
kernelkernel
openEuler内核是openEuler操作系统的核心,既是系统性能与稳定性的基石,也是连接处理器、设备与服务的桥梁。
C
528
588
ops-nnops-nn
本项目是CANN提供的神经网络类计算算子库,实现网络在NPU上加速计算。
C++
906
1.82 K
pytorchpytorch
作为 Ascend for PyTorch 社区的核心组件,TorchNPU 是昇腾专为 PyTorch 打造的深度学习适配插件,使 PyTorch 框架能够直接调用昇腾 NPU,为开发者提供昇腾 AI 处理器的超强算力。
Python
854
1.34 K
docsdocs
暂无描述
Markdown
891
5.78 K
jiuwenswarmjiuwenswarm
JiuwenSwarm 是一款基于openJiuwen开发的智能AI Agent,它能够将大语言模型的强大能力,通过你日常使用的各类通讯应用,直接延伸至你的指尖。
Python
3.53 K
1.01 K
ops-mathops-math
本项目是CANN提供的数学类基础计算算子库,实现网络在NPU上加速计算。
C++
1.34 K
1.45 K
cann-learning-hubcann-learning-hub
CANN 学习中心仓,支持在线互动运行、边学边练,提供教程、示例与优化方案,一站式助力昇腾开发者快速上手。
Jupyter Notebook
987
504
AscendNPU-IRAscendNPU-IR
AscendNPU-IR是基于MLIR(Multi-Level Intermediate Representation)构建的,面向昇腾亲和算子编译时使用的中间表示,提供昇腾完备表达能力,通过编译优化提升昇腾AI处理器计算效率,支持通过生态框架使能昇腾AI处理器与深度调优
C++
540
384