ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

Meteor 核心开发指南:从 Git 检出运行、Dev Bundle 构建到四层测试与发布流程全解析

Meteor 核心开发指南:从 Git 检出运行、Dev Bundle 构建到四层测试与发布流程全解析 Meteor 核心开发指南从 Git 检出运行、Dev Bundle 构建到四层测试与发布流程全解析【免费下载链接】meteorMeteor, the JavaScript App Platform项目地址: https://gitcode.com/gh_mirrors/me/meteor本指南面向想要为Meteor Core 本身而非 Meteor 应用贡献代码、提交 Pull Request 或进行二次开发的工程师系统讲解从 Git 检出直接运行 Meteor、理解并重建 Dev Bundle、运行四层测试体系、遵循代码规范与提交信息约定以及借助 AI Skills 完成 beta/RC/官方发布全流程的完整方法论。读完本文你将能够在本仓库根目录下独立完成环境搭建、源码级调试、fork 分支测试、dev_bundle 重建与发布流程编排。文档定位与适用范围本文档DEVELOPMENT.md是 Meteor 官方仓库中面向修改 Meteor 核心本身的开发者手册。它与面向应用开发者的文档不同目标读者是提交 Pull Request、修复 core bug、为meteor工具链或packages/下的 Atmosphere 包做贡献的人。文档开篇甚至给出了一条友好的建议如果你在开发过程中发现了某个有用但未被记录的 Meteor 特有流程请考虑直接编辑本文档并提交 Pull Request——这份文档本身就是由社区持续维护的活文档。注意文中所有命令均应在仓库根目录gh_mirrors/me/meteor下执行且针对的是仓库自带的./meteor脚本而不是全局安装的meteor命令。从 Git 检出直接运行 Meteor1. 克隆仓库务必带--recursive本仓库使用Git submodules因此克隆时必须使用递归标志否则会在后续运行时报错典型的症状是 Depending on unknown package$ git clone --recursive https://github.com/meteor/meteor.git $ cd meteor如果此前克隆时漏掉了--recursive、git pull之后发现子模块失同步或遇到了 Depending on unknown package 错误在仓库根目录执行以下命令即可重新同步$ git submodule update --init --recursive从仓库的 .gitmodules 可以看到当前仓库实际挂载的子模块例如packages/non-core/blaze指向meteor/blaze以及npm-packages/cordova-plugin-meteor-webapp/src/ios/GCDWebServer指向meteor/GCDWebServer。这些子模块是构建完整 Meteor 发行版所必需的。2. 运行第一条 Meteor 命令安装依赖克隆完成后直接运行仓库根目录下的./meteor脚本即可触发依赖安装若未预先编译依赖这一步还会自动下载预编译的二进制包即下文要讲的 dev_bundle$ ./meteor --helpWindowsPowerShell特别说明在 PowerShell 中请使用.\meteor而不是./meteorMeteor 可能需要PATH中存在7z.exe才能下载/解压二进制包dev_bundle验证where.exe 7z若缺失请安装 7-Zip 并确保其位于 PATH例如choco install 7zip -y或scoop install 7zip。3. 开始使用本地检出安装完成后本地检出的 Meteor 就绪可以把它当作系统级meteor的替代品在任何位置使用。例如在应用目录中$ cd my-app/ $ /path/to/meteor-checkout/meteor run实用技巧 1——创建别名为频繁使用配置一个易记的别名alias mymeteor/path/to-meteor-checkout/meteor之后即可用mymeteor代替meteor使用。若希望在每次登录 shell 时都生效把它追加到~/.bashrc或.zshrc即可。实用技巧 2——调试 Meteor 工具本身当需要调试meteor工具内部逻辑时可用TOOL_NODE_FLAGS环境变量为工具进程注入 Node 调试参数TOOL_NODE_FLAGS--inspect-brk mymeteor然后在 Chrome 浏览器中打开chrome://inspect即可使用 Chrome DevTools 调试器。从源码看TOOL_NODE_FLAGS在 meteor 脚本的exec $DEV_BUNDLE/bin/node ...调用中被展开因此它实际上把参数直接传给了 Node 进程。tools/README.md 中还有更详细的说明TOOL_NODE_FLAGS支持--debug、--debug-brk及自定义端口写法如--debug-brk6060而调试self-test派生出的测试应用时应改用SELF_TEST_TOOL_NODE_FLAGS建议指定不同端口以避免冲突例如SELF_TEST_TOOL_NODE_FLAGS--debug-brk5859。测试 fork 分支审查他人 Pull Request 或测试贡献者 fork 中的改动时仓库提供了一个自动化脚本 scripts/checkout-pr.js可通过 npm scriptcheckout:pr一键完成添加 remote → fetch 分支 → 创建本地分支的流程# 从 PR 链接需要 gh CLI否则回退到 curl 调用 GitHub API $ npm run checkout:pr -- https://github.com/meteor/meteor/pull/PR-number # 从 user:branch 简写 $ npm run checkout:pr -- user:branch # 从完整的 fork 仓库 URL 分支名HTTPS $ npm run checkout:pr -- fork-repo-url branch # 从完整的 fork 仓库 URL 分支名SSH $ npm run checkout:pr -- gitgithub.com:user/repo.git branch脚本会依次完成若远程仓库尚不存在将 fork 添加为 git remote以 fork 所有者的名字命名fetch 目标分支创建或更新名为fork/owner/branch的本地分支打印切回原分支的操作提示。对于meteor/meteor自身的 upstream PR分支就在本仓库内脚本会检测已有的originremote直接检出该分支而不加fork/前缀。如果对同一个 fork 分支重复运行脚本它会 fetch 最新改动并更新本地分支方便反复同步审查。从检出运行的注意事项与安装版相比从 checkout 运行时有以下必须注意的差异无法将应用固定到特定 Meteor 版本也不能通过--release切换发行版。这是因为 checkout 模式直接以本地工具链运行不走 release 语义。Dev BundleMeteor 工具的依赖内核什么是 Dev Bundledev bundle在目录结构中标识为dev_bundle是一份预生成的代码、包与工具集合是 Meteor 工具meteor及其构建出的应用 bundle 提供完整功能的基础。当你从 checkout 运行meteor时脚本会自动下载一份dev_bundle对绝大多数开发场景已经够用。从 meteor 脚本的install_dev_bundle函数可以看到完整的安装逻辑脚本按dev_bundle_${PLATFORM}_${BUNDLE_VERSION}.tar.gz的命名从https://d3sqy0vbqsdhku.cloudfront.net/下载 tarball解压后校验${BUNDLE_TMPDIR}/bin/node可执行然后原子替换dev_bundle目录并写入.bundle_version.txt记录版本后续每次运行时都会比对.bundle_version.txt中的版本号与BUNDLE_VERSION是否一致不一致则重新安装。什么情况下需要重建 Dev Bundle以下组件的改动需要重建dev_bundleNode.js 版本npm 版本MongoDB 版本TypeScript 版本meteor-tool 使用的包server bundle 使用的包例如 scripts/dev-bundle-tool-package.js 中定义了工具链依赖清单npm、typescript、meteorjs/babel、meteorjs/reify、babel/runtime、underscore等这些版本最终由generate-dev-bundle.sh处理成一个package.json并打包进 dev_bundle。需要提醒的是修改这些变量看似诱人但请充分考虑后果尤其是兼容性与稳定性并做大量测试——特别是 Node.js 与 MongoDB 的主版本升级通常需要连带修改大量其他组件。Dev Bundle 版本号管理将被下载或生成的 dev_bundle 工作版本号保存在 meteor 脚本顶部的BUNDLE_VERSION中当前仓库的取值为24.15.0.3。提交会改变 dev_bundle 组件的 Pull Request 时至少应递增 minor 版本号在本地开发中建议使用一个不同的主版本号例如100.0.0以免与本地缓存的官方版本冲突。要启用下载 tarball 的本地缓存请在运行 Meteor 前设置SAVE_DEV_BUNDLE_TARBALL环境变量SAVE_DEV_BUNDLE_TARBALL1 ./meteor缓存下来的 tarball 存放在 checkout 根目录。保留它们可以避免在分支间切换时重复下载但会随着时间累积变得非常庞大请按需清理。从 meteor 的源码可见设置该变量后脚本会把curl下载的内容落盘为$SCRIPT_DIR/$TARBALL下次运行检测到本地已有同名 tarball 就会直接解压跳过网络下载。重建 Dev Bundle重建需要 C/C 编译器、autotools和scons。从零构建并重新打包依赖只需运行$ ./scripts/generate-dev-bundle.sh该脚本会在 checkout 根目录生成一个新的 tarball命名形如dev_bundle_Platform_arch_version.tar.gz。假设你已递增了BUNDLE_VERSION那么新版本会在下次运行./meteor时被自动解压使用如果重建的是同一版本或没有递增版本号请先删除已有的dev_bundle目录确保下次运行./meteor时解压的是新 tarball。从脚本实现看它会从meteor脚本中自动读取BUNDLE_VERSIONperl -ne print $1 if /BUNDLE_VERSION(\S)/ meteor并依次下载/构建 Node、MongoDB 等组件。提交 Dev Bundle 相关 Pull Request 的注意事项需要特别说明虽然dev_bundle相关的 PR 会被接收/审查但只有 Meteor Software 的正式成员才能把新 dev_bundle 发布到 Meteor 基础设施。这意味着提交的 dev_bundle PR 其构建工具测试与包测试一开始必然失败因为新 dev_bundle 尚未被 Meteor Software 构建/发布Meteor 的 CI 环境无法下载它。仓库协作者会注意到包含 dev_bundle 改动的 PR并把构建/发布新 dev_bundle的请求转发给 Meteor Software。深入了解 Meteor Core哪里找文档Meteor 核心最好的文档就在代码本身不过许多组件在自己的目录下也带有README.md仓库中有一部分被拆分为独立包见 packages/ 目录几乎每个包目录内都有README.md例如 packages/ddp/README.md、packages/ecmascript/README.md、packages/tinytest/README.md其余组件则在各自目录附近寻找README.md例如 tools/isobuild/README.md构建系统 Isobuild 的高层描述或 tools/cordova/README.mdtools/README.md 还额外覆盖了性能分析.cpuprofile生成与调试器的用法配合 tools/PERFORMANCE.md 使用。测试体系四层测试架构运行使用./meteor的测试时务必确保是对着检出的副本运行而不是全局安装的版本——这样才能保证测试针对的是你的本地开发版本。仓库共有四层测试覆盖不同的范围命令层级覆盖范围npm run test:unit单元测试Jesttools/、scripts/与辅助函数中的纯逻辑速度快无需 Meteor 运行时npm run test:e2e端到端测试Jest PlaywrightBundler 集成与 skeleton 应用创建真实 Meteor 项目并启动浏览器./meteor self-test自测试自定义框架Meteor CLI 工具本身会派生沙箱化的 Meteor 进程逐命令端到端验证./meteor test-packages包测试TinyTestpackages/ 中的 Atmosphere 包在带完整响应式运行时的 Meteor 应用内运行单元测试Jest单元测试覆盖不需要 Meteor 运行时的纯辅助函数、脚本与工具逻辑。它们使用 Jest配置位于 tools/unit-tests/其中的jest.config.js与package.json定义了隔离的 Jest 环境依赖swc/core、swc/jest、jest等目标文件为tools/**/*.test.js与scripts/**/*.test.js。# 首次运行前安装依赖 npm run install:unit # 运行全部单元测试 npm run test:unit # 运行指定测试文件 npm run test:unit -- tools/path/to/file.test.js # 按名称模式匹配运行 npm run test:unit -- -t my test name测试文件应放在被测模块旁边并使用*.test.js命名约定Jest 会自动发现它们。端到端测试Jest Playwrighttools/e2e-tests/ 中的端到端测试用于验证 Meteor skeleton 与 bundler 集成的正确性它们会创建真实的 Meteor 应用、启动开发服务器并在无头 Chromium 浏览器中断言行为。# 首次运行前安装依赖含 Playwright 浏览器 npm run install:e2e # 运行全部 E2E 测试 npm run test:e2e # 运行指定套件 npm run test:e2e -- -tReact每个测试都有对应的应用 fixture 放在 tools/e2e-tests/apps/ 中例如react、blaze、coffeescript、server-only、monorepo等目录新增 E2E 测试时可参考该目录中的示例。以reactfixture 为例其package.json同时声明了meteor run启动脚本、meteor test使用meteortesting:mocha驱动包以及playwright依赖。自测试Meteor 工具Meteor CLI 拥有自己的self-test框架它会派生沙箱化的 Meteor 进程测试create、build、deploy、publish等命令# 列出所有自测试 ./meteor self-test --list # 运行全部自测试 ./meteor self-test # 用正则匹配运行测试 ./meteor self-test ^[a-b] # 排除匹配正则的测试 ./meteor self-test --exclude ^[a-b] # 开发期间跳过重试 ./meteor self-test --retries 0包测试TinyTest处理核心 Atmosphere 包时使用test-packages通过 packages/tinytest/README.md 中介绍的 TinyTest 运行其测试。这会启动一个 Meteor 应用测试结果可在http://localhost:3000查看# 测试所有包 ./meteor test-packages # 测试指定包 ./meteor test-packages mongo # 按测试名过滤支持正则使用 --filter 或 -f ./meteor test-packages --filter collection - call new Mongo.Collection # 等价的环境变量写法 TINYTEST_FILTERcollection - call new Mongo.Collection ./meteor test-packages从源码可以印证--filter与TINYTEST_FILTER的等价关系tools/cli/commands.js 中定义了filter: { type: String, short: f }选项并在doTestCommand中执行process.env.TINYTEST_FILTER options.filter二者最终殊途同归。如需无头headless控制台输出可使用PUPPETEER_DOWNLOAD_PATH~/.npm/chromium ./packages/test-in-console/run.shpackages/test-in-console/run.sh 会设置METEOR_HOME为 checkout 根目录在需要时通过./meteor npm install -g puppeteer安装 Puppeteer并将$METEOR_HOME加入PATH后执行无头测试。持续集成每当有人提交 Pull Request 或直接向devel分支推送 commit 时CI 服务器会自动启动持续集成测试。需要运行的测试与运行环境由 scripts/ci/run-selftest-ci.sh 定义——该脚本也可以在本地运行以复现 CI 的精确测试行为它内部依次执行 TypeScript 类型检查、./meteor --get-ready、以及分段执行的./meteor self-test --headless并支持--limit、--skip、--retries等参数。此外 .github/workflows/ 下的 GitHub Actions 工作流如unit-tests.yml、e2e-tests.yml、test-packages.yml、test-tools.yml、windows-selftest.yml等负责在托管 CI 上编排这些任务。并非测试规范中定义的每个测试都会被 CI 实际运行有些测试运行时间过长有些则已不再相关。例如测试框架中存在一组归入slow标记的超慢测试可通过在self-test命令上附加--slow选项来执行。Windows 说明目前尚无针对 Windows 的 CI 系统且并非所有测试都确认能在 Windows 上运行。如果你有时间改进这些测试将非常感谢目前还没有官方的已知无法在 Windows 上运行的测试清单提交一个 PR 在此记录并修复它们将是最理想的。代码风格新贡献应尽可能遵循 Meteor Style Guide其与 Airbnb Style Guide 非常接近但有少数显著差异当改动范围较小时新代码应与周边既有代码保持一致较大规模的新代码则遵循 Style Guide不要修改与当前功能/bug 无关的代码基本 lint 检查通过运行仓库根目录的npm run lint完成当前仓库使用oxlint忽略规则见 .oxlintignore格式检查通过npm run fmt:check使用oxfmt忽略规则见 .fmtignore。仓库还通过 lefthook.yml 配置了pre-push钩子推送前会自动执行npm run fmt:check与npm run lint确保合入代码符合格式与风格要求。说明DEVELOPMENT.md 原文提到的scripts/admin/eslint/eslint.sh在当前仓库快照中已不存在当前的 lint/format 工具链已迁移为根目录package.json中声明的oxlintoxfmtESLint 相关依赖仍保留在 devDependencies 中.eslintrc风格配置位于package.json的eslintConfig字段extends 自vazco规则集请以当前仓库的实际命令为准。提交信息规范良好的提交信息非常重要请务必解释改了什么以及为什么。提交信息应包含简短有用的标题最长 80 个字符若改动不能从标题中一目了然则应有清晰说明改动的描述正文——有点描述总是有帮助的在描述正文中按编号引用相关的 issue 与 pull-request例如#9999如果该提交能完全解决某个 issue在 issue 编号前加上 Fixes例如Fixes #9999。发布流程beta → RC → 官方Meteor 的发布遵循生命周期beta → RCrelease candidate→ 官方official。发布在release-VERSION分支上准备例如release-3.4.1并与devel分支进行对比。支撑发布流程的 AI Skills三个 AI skill 支撑整个发布流程它们以 markdown 文件形式定义在 .github/skills/ 下任何支持读取项目上下文的 AI 编程助手都可在发布分支上的任意会话中触发使用Skill用途Skill 文件changelog从已合并的 PR 生成并更新 changelog 条目v3-docs/docs/generators/changelog/versions/version-bump为 beta、RC 或官方发布递增包版本packages/*/package.js、发布配置文件docs-gap识别发布改动缺失的用户文档在docs/plans/输出 gap 报告这三个 skill 都遵循相同的分支模型发布在release-VERSION分支准备主开发分支为devel变更范围 release 分支上有而devel上没有的全部改动用git log devel..HEAD查看。其中changelog skill 规定所有 changelog 文件位于v3-docs/docs/generators/changelog/versions/每个版本一个文件命名格式为MAJOR.MINOR.PATCH.md无v前缀、无后缀由生成器消费产出公开 changelog严禁直接编辑生成输出version-bump skill 定义了两套版本方案meteor-tool 与其他所有包、track number 推导规则release 分支数字去掉点号拼接如release-3.4.1→341、以及git diff devel --dirstatfiles -- ./packages/的变更检测方法docs-gap skill 只做差距分析、不写文档输出到docs/plans/DATE-docs-gap-VERSION.md。准备 Beta 发布Beta 是某个新版本的第一个预发布版本它为所有发生变更的包追加-betaXXX.0后缀。第一步——更新 changelogUpdate the changelog for 3.4.1 from the current branch compared to devel. Check all merged PRs and complete with the missing fixes and features.第二步——递增版本Apply the version-bump skill for a beta.0 release on this branch against devel.AI 助手会分析每个发生变更的包根据 diff 判定是 patch 还是 minor 递增以表格形式呈现原因并在确认后应用。第三步——检查文档缺口Run the docs-gap skill to analyze what documentation is missing for this release.准备 RC 发布RC 将 beta 版本过渡为 release candidate基础版本号保持不变只改变后缀。第一步——更新 changelog与 beta 相同可捕获自上个 beta 以来新合并的 PR。第二步——递增版本Apply the version-bump skill to move from beta to RC on this branch.准备官方发布官方发布会去掉所有预发布后缀并更新发布配置与 npm 安装器。第一步——收尾 changelogFinalize the changelog for 3.4.1 — set the release date and replace any RC version references with final versions.第二步——递增版本Apply the version-bump skill for an official release on this branch.这是一个两步提交的过程先提交 packages 与 release 配置再提交 npm 安装器。发布配置文件可从 scripts/admin/meteor-release-official.json 中看到实际形态包含track、version、recommended、official、description字段。第三步——验证文档覆盖Run the docs-gap skill and apply any missing documentation for this release.其他常用提示词# 在 changelog 中把 Rspack 的改进与其他改动分开 Update the changelog separating Rspack improvements from other contributions. # 覆盖某个特定包的递增幅度 The roles package should be a minor bump because it adds getUserIdsInRoleAsync. # 只生成 gap 报告不应用修复 Run the docs-gap skill to produce a gap report only — dont write any docs yet. # 检查与 devel 相比哪些包发生了变化 What packages have changed on this branch compared to devel?结语Meteor 核心的日常开发并不神秘从一条git clone --recursive与./meteor --help开始就能获得一份可调试、可替换全局工具的本地开发环境dev_bundle是其依赖内核理解BUNDLE_VERSION、缓存与重建机制是触碰 Node/npm/MongoDB/TypeScript 等底层组件的前提四层测试体系Jest 单元、Playwright E2E、self-test、TinyTest 包测试为每一类改动划定了验证边界而changelog、version-bump、docs-gap三个 AI Skill 则把 beta/RC/官方发布的重复性工作沉淀为可复现的流程。无论你是想修复一个 core bug、提交一个 dev_bundle PR还是完整走一遍发布流程本文的每一步都对应着仓库中的真实脚本与配置文件可以直接照着执行并深入验证。【免费下载链接】meteorMeteor, the JavaScript App Platform项目地址: https://gitcode.com/gh_mirrors/me/meteor创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进