Skip to content

fix(mobile): 提前检查模拟器构建工具并改善诊断流程 - #7814

Merged
MagicLizi merged 3 commits into
mainfrom
dash/mobile-sim-preflight
Oct 29, 2026
Merged

MagicLizi merged 3 commits into
mainfrom
dash/mobile-sim-preflight

Conversation

@dashhuang

@dashhuang dashhuang commented Oct 29, 2026 •

Copy link
Copy Markdown
Member

这次改了什么

摘要

模拟器截图任务可能在生成原生工程后才发现缺少 CocoaPods;whoami 又逐端口运行 lsof,遇到慢查询时长时间没有进度,容易被误判为需要重新编译。

本 PR 保留兼容原生包优先复用的现有机制,补充缓存拒绝原因,在缓存未命中时先检查 Xcode、Simulator SDK 和 CocoaPods,再执行 prebuild。whoami 增加阶段耗时与超时诊断,并将端口查询合并为一次,区分检查失败和没有监听进程。仓库文档补齐工具链准备、截图验收及通用流程与个人配置的边界。

已找到监听 PID 后,命令、cwd、源码身份和 Windows 进程快照的查询失败同样传入 probeErrors,附端口、阶段和受限错误码,并抑制“没发现 Metro/启动一个 Metro”的误导提示;回执不包含命令输出或进程环境。

Metro 回执和启动提示判断由可直接导入的 inspectSimMetroIdentity 统一完成,CLI 与单测调用同一生产入口;单测只注入只读进程 I/O,不读取、截取或执行源码文本。

变更类型

  • feat 新功能
  • fix 缺陷修复
  • refactor / perf 重构或性能优化
  • docs / test / chore 文档、测试或工程维护
  • 其他:

范围

  • 关联 Issue / 需求:改善 Mobile 模拟器截图任务的环境诊断和执行流程;无独立 Issue。
  • 本 PR 包含:缓存与工具检查回执、whoami 分阶段进度、有限时长的探测、多端口一次查询、原生指纹失败原因及相关文档与测试。
  • 明确不包含:个人 Skill/profile、系统工具安装、iOS 界面修复、原生依赖或 App 配置变更。
  • 用户可见变化:CLI 能解释为何不能复用缓存、缺少哪个工具或哪个检查超时;无需靠长时间静默等待猜测进度。
  • 是否存在 breaking change:无;保留已有身份字段与验收要求,新增诊断字段。JSON 模式进度在 stderr、结果对象在 stdout。

UI 变化

不涉及 App UI。

  • 引用的设计规范:不涉及。

怎么验证的

自动验证

pnpm --filter mobile test src/__tests__/simRebuildScript.test.ts src/__tests__/simPodInstall.test.ts src/__tests__/simNativeIdentity.test.ts src/__tests__/mobileSimWhoami.test.ts src/__tests__/mobileSimSource.test.ts src/__tests__/simIdentity.test.ts
结果:构建与缓存相关验证,6 个文件、114 项测试通过(11.78 秒)。

pnpm check:dco
结果:本 PR 全部提交签名通过。

pnpm --filter mobile typecheck
结果:通过。

pnpm check:dev-docs
结果:10 项通过。

pnpm check:test-hygiene
结果:通过。

git diff --check
结果:通过。

pnpm --filter mobile test src/__tests__/mobileMetroOwnership.test.ts src/__tests__/mobileSimWhoami.test.ts src/__tests__/mobileSimSource.test.ts src/__tests__/simIdentity.test.ts
结果:生产入口提取并同步主分支后,4 个文件、114 项测试通过(2.97 秒)。

pnpm --filter mobile test src/__tests__/mobileMetroOwnership.test.ts
结果:32 项测试通过,单文件墙钟 3.76 秒;4 个超时失败场景此前先红后绿,并覆盖空端口、探测失败与匹配 Metro 的不同回执。

新增测试均并入已有文件,无新增测试文件、固定端口或真实等待:

文件 生产入口、回归依据与现有缺口 最小失败输入 / 断言 tier / 本次执行耗时
simRebuildScript.test.ts 执行实际 rebuild CLI body;原覆盖未验证缺工具时副作用和缓存拒绝诊断 pod 缺失/超时/权限失败必须发生在 prebuild 前;兼容缓存无 pod 仍能安装;架构/指纹不符输出拒绝原因。新增回归先红后绿 unit / 416ms
mobileSimSource.test.ts inspectMetroListeners;原检查逐端口查询且把错误当空端口 一次查询解析 IPv4/IPv6;空端口与超时/工具缺失分别返回;Windows netstat 测试数据 unit / 599ms
mobileSimWhoami.test.ts resolveMobileSimulatorBundleId;原配置解析没有超时分类 注入 ETIMEDOUT,返回明确超时且不猜 bundle ID、不输出子进程内容 unit / 11ms
simNativeIdentity.test.ts inspectSimulatorNativeIdentity;原 unknown 未区分资源缺失与计算失败 安装指纹为空时不计算;计算超时返回独立原因且仍不通过兼容检查 unit / 3ms
mobileMetroOwnership.test.ts 直接调用 inspectSimMetroIdentity 与 probeMetroOwnership;原覆盖只验证端口发现,未验证进程身份错误到回执与提示判断的传递 分别注入命令/cwd/源码/Windows 快照超时;断言错误回执、身份拒绝与提示关闭。另覆盖空端口、探测失败和匹配身份,防止一律返回失败或禁用所有提示 unit / 单文件墙钟 3.76s,执行 185ms

表中执行耗时来自各自的定向验证,单文件墙钟另行标注;没有新增测试文件。既有 simPodInstall.test.ts 的真实子进程看门狗测试约 7.9 秒,本 PR 未修改其测试实现。

手工验证

  • macOS:实际只读检查返回 Xcode/SDK 可用、pod 缺失,验证预检查能识别当前工具状态。
  • macOS:临时监听系统分配的空闲端口,实际执行查询,核对 PID 与进程 cwd;通过并关闭临时端口。
  • node apps/mobile/scripts/sim-whoami.mjs --region=global --mock --json:在 dash/mobile-sim-preflight 工作目录实际运行约 9 秒,端口探测约 0.7 秒,probeErrors=[];正确识别另一 worktree 的 Metro 为 occupied-foreign。没有已启动的目标模拟器,健康检查按预期非零;未接管 Metro,不将其宣称为 App 启动验收。

未执行的验证

  • 未运行完整 iOS 编译、安装和界面截图:本 PR 修改开发脚本与说明,本机尚缺 CocoaPods;没有 Metro 归属或 __DEV__ build label 的运行验收证据。
  • 未在 Windows 实机执行;Windows 端口解析由测试数据覆盖。
  • 未运行全仓单测;已完成受影响入口的定向验证,完整门禁由 CI 执行。

风险

风险分类

  • 无已知风险
  • SQLite / migration
  • system prompt
  • 协议兼容
  • 权限 / 安全 / 用户数据
  • 存量插件兼容(批准状态 / 指纹 / manifest 校验 / 安装布局 / 包格式)
  • 原生层 / fingerprint / OTA
  • 跨平台差异
  • 其他:开发工具探测的单步超时边界

影响与回滚

  • 影响范围:Mobile 本地开发脚本。macOS 使用 lsof,一次查询多个端口并避免阻塞的文件系统操作;Windows 继续使用 netstat。过慢的工具可能触发新超时,回执会标明具体阶段;检查失败不能作为兼容证据。
  • 诊断不变量:已找到监听 PID 后,命令、cwd、源码或 Windows 快照查询失败必须进入错误回执,并保持身份未通过;普通缺少身份数据不伪装成超时。共享探测仍使用原来的空值拒绝路径,诊断通过可选回调传递。
  • 原生兼容仍要求安装包嵌入指纹匹配当前源码。未修改原生依赖、Expo App 配置或指纹生成算法;只调整开发侧检查与诊断。
  • 回滚 / 降级方式:回退本 PR,恢复旧脚本和文档;无数据迁移、凭证写入或缓存格式迁移。

提交前检查

  • 已 review 完整 diff
  • 每个 commit 都带 DCO 签名(git commit -s,见 DCO)
  • UI 改动已在「UI 变化」注明引用的设计规范章节(不涉及 UI 则跳过)
  • 未提交凭证、令牌或授权文件
  • 已核对受影响的文档,行为变化涉及的旧结论已同步修订(不涉及则无需修改文档)
  • 已确认测试结果或说明未执行原因

@dashhuang
dashhuang requested a review from a team as a code owner October 29, 2026 07:33
@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Oct 29, 2026 •

Copy link
Copy Markdown

Codex Review Summary

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-10-29T08:34:37.623731Z ea628c0 New commits
🔒 Security Review ✅ Completed 2026-10-29T08:35:06.066587Z ea628c0 New commits
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

@greptile-apps

greptile-apps Bot commented Oct 29, 2026 •

Copy link
Copy Markdown

RetriggerView in GreptileConfidence Score: 4/5

[Medium impact] The changes affect local Mobile simulator build and identity-check workflows.

本 PR 看起来可以合并;建议补齐 Metro 身份查询超时的诊断回执。

Findings

  1. P2 Metro 查询超时被隐藏 ▶
Fix with agent prompt
### Issue 1
apps/mobile/scripts/sim-metro.mjs:240
新增的 5 秒超时会被 `commandOfPid`、`cwdOfPid` 和 `gitSourceOfPid` 的 `catch` 吞掉。如果已找到监听中的 Metro,但其中一次身份查询超时,`whoami` 仍会返回 `probeErrors: []`,把它标成未知进程,甚至提示“没发现 Metro”。开发者因此看不到具体失败项,反而收到启动 Metro 的提示。

建议把查询超时传回 `probeMetroOwnership`,再由 `whoami` 记录,区分检查失败和身份信息确实缺失。

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Summary

本 PR 提前检查 iOS 构建工具,并改善模拟器检查的进度和错误说明。

  • Simulator rebuilds check build tools before generating native files.
  • Simulator checks show how long each stage takes and whether Metro ports were checked.

Diagram

%%{init: {'theme': 'neutral'}}%%
flowchart TD
  A[解析 App 身份与指纹] --> B{缓存通过兼容检查?}
  B -->|是| E[再次检查产物]
  B -->|否| C{构建工具可用?}
  C -->|否| D[输出工具检查结果并退出]
  C -->|是| F[prebuild / pod install / xcodebuild]
  F --> E
  E --> G{仅构建?}
  G -->|是| H[返回产物]
  G -->|否| I[安装并检查 Metro 身份]
  I --> J[身份一致后启动]
Loading

Reviews (1) · Last reviewed commit: "fix(mobile): 提前检查模拟器构建工具并改善诊断流程" · Reviewed by Greptile

Comment thread apps/mobile/scripts/sim-metro.mjs Outdated

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: dbf2b43d1e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread apps/mobile/src/__tests__/mobileMetroOwnership.test.ts Outdated
Signed-off-by: Dash <125997726+dashhuang@users.noreply.github.com>
Signed-off-by: Dash <125997726+dashhuang@users.noreply.github.com>
Signed-off-by: Dash <125997726+dashhuang@users.noreply.github.com>
@dashhuang
dashhuang force-pushed the dash/mobile-sim-preflight branch from dbf2b43 to ea628c0 Compare October 29, 2026 08:29

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: ea628c03d8

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread apps/mobile/scripts/lib/sim-native-identity.mjs
@MagicLizi MagicLizi added touches:product-ui 改动碰到产品 / UI 面(review-pr 自动维护,仅展示) touches:rules 改动碰到规则 / 规范文档(review-pr 自动维护,仅展示) labels Oct 29, 2026
@MagicLizi

Copy link
Copy Markdown
Contributor

PR #7814 独立代码审查报告(auto / heavy 档)

  • PR: fix(mobile): 提前检查模拟器构建工具并改善诊断流程 #7814
  • head: ea628c03d855b23e9df813c65c6056e67001eab7,base: 5f0b5f42b46969c3ac21b0cd798a07e36b46e8fd(main)
  • diffHash: 212b237773ef7f0f5ec41b890f9d3a1cb68401cd9da75e4451fd44aa591725ec
  • 审查范围:14 个文件(apps/mobile/scripts/、apps/mobile/src/tests/、apps/mobile/docs、docs/dev-rules),共 636 diff 行。

Findings

没有 P0/P1。

(P2 级观察,不阻断、不发帖:a) whoami 对任一端口的进程探测失败都会把整体 healthy 置 false,包括非目标端口上与本 worktree 无关的 Metro——偏保守的 fail-closed 选择,与「检查失败不能作为兼容证据」一致;b) runFingerprintWithCurrentEnv 失败信息从 stderr 摘要改为仅错误码,诊断信息略减少,但符合回执不带子进程输出的隐私口径。)

Rule coverage

按 rule-map 读取并逐项核对(只审本 PR 新增/修改的代码与文档):

  • AGENTS.md + docs/dev-rules/development-workflow.md + .github/PULL_REQUEST_TEMPLATE.md(所有 PR):
    • Title fix(mobile): 提前检查模拟器构建工具并改善诊断流程 与 diff 一致;Description 三大段齐全,验证声明与抽样复跑一致(见 Verification)。
    • DCO:pnpm check:dco 通过,5f0b5f42..ea628c03 共 3 个提交全部带匹配 Signed-off-by(bot thread 引用的 61acccd3db0… 为 review 沙箱合成 SHA、不在 PR 提交列表,按 AGENTS.md 不构成缺签证据,作者驳回成立)。
    • 验证真实性:「未执行的验证」如实列出(无完整 iOS 编译/截图、无 Windows 实机、无全仓单测),无伪造通过。
  • docs/dev-rules/mobile-development.md + docs/dev-rules/remote-and-mobile-adaptation.md(apps/mobile/**):
    • 冷更边界:本 PR 仅改 apps/mobile/scripts/**(开发工具脚本)、单测与文档,未触碰 app.json / app.config.js / eas.json / apps/mobile/package.json / plugins/ / modules/ / fingerprint.config.cjs 等 fingerprint 输入,不触发 runtime fingerprint 变化,无需冷更确认门。
    • 权限/工具安装边界:inspectIOSBuildTools 为只读探测(version/SDK path),从不安装工具、不接受 Xcode license;文档明确安装遵循用户授权(environment-setup.md 新节)。
    • 跨平台:macOS 用一次 lsof 快照、Windows 沿用 netstat,两端均有单测覆盖;Windows 未实机验证已在 PR 里如实声明。
  • docs/dev-rules/environment-setup.md(本 PR 修改):新增「macOS:iOS 模拟器构建工具链」一节与脚本行为一致(缓存命中不要求 CocoaPods;缓存未命中先 SIM_BUILD_PREFLIGHT、失败输出 IOS_BUILD_TOOLS_UNAVAILABLE 且不生成 ios/);CocoaPods 安装方式引用官方文档、不静默执行安装。文档内相对链接与锚点核对无误。
  • docs/dev-rules/credentials-and-local-storage.md 口径(回执/日志不含凭证与用户数据):
    • 各探测回执只含 stage/code/port/pid/timeoutMs;reportProcessProbeError、inspectIOSBuildTools、Expo config 超时错误均不带子进程 stdout/stderr 或环境值,单测断言 JSON.stringify(result) 不含注入的 'private' 内容。
    • 无凭证、令牌、用户数据落盘;缓存目录行为不变(仅新增拒绝原因码)。
  • 测试证据(check:test-hygiene 口径):新测试不再读取/求值生产源码文本,统一通过可导入的生产入口 inspectSimMetroIdentity 调用;pnpm check:test-hygiene PASS(359 files within baseline),未改测试基线或 guard allowlist。
  • UI/DESIGN.md:不涉及 App UI(format.uiCodeFiles 为空),DESIGN.md 不适用。

固定问题逐条:① 单一目的(模拟器构建预检查 + whoami 诊断),描述/测试/风险一致;② 共享符号(probeMetroOwnership/cwdOfPid/commandOfPid/gitSourceOfPid/isMetroPid/windowsProcessSnapshot/listenerPid)签名向后兼容(新增可选 options),既有调用方与既有测试不受影响;③ 权限与跨平台行为安全、可回滚(回退 PR 即可);④ 无新依赖、无危险写法、无新数据流向(heavy 档专项见 Verification:security-scan 0 条、无新增依赖、无 security 触发的 riskySoftHits);⑤ 受影响路径均有实际测试证据(7 个测试文件 146 项本地通过);⑥ 未把组织/个人流程塞进 Core——个人 profile/Skill 边界反而在文档中显式划出;⑦ 无 UI 证据要求;⑧ 不改原生配置/依赖,无冷更触发;⑨ 结论只有 P2,按口径通过且不发送 P2。

Verification

实际运行(worktree …/worktrees/pr-7814,全部退出码 0):

  • vitest run mobileMetroOwnership / mobileSimSource / mobileSimWhoami / simNativeIdentity / simRebuildScript:128 项通过(日志 pr-7814-verify-vitest.log)。
  • vitest run simPodInstall / simIdentity:18 项通过(含 pod 看门狗真实子进程测试)。
  • pnpm --filter mobile run --if-present typecheck:通过。
  • pnpm run check:test-hygiene:PASS (359 files within baseline)。
  • pnpm run check:dev-docs:10 项通过。
  • pnpm run check:dco:3 commits signed off(5f0b5f42..ea628c03)。
  • git diff --check:通过。
  • 真实 lsof 只读抽查:inspectMetroListeners([59991,59992]) 无监听返回 {healthy:true,pids:{}};本机临时 TCP 监听可被一次快照正确发现并经 probeMetroOwnership 取得一致 pid(临时进程已关闭)。验证了多端口逗号列表、-Fpn 解析与「无监听 ≠ 探测失败」分支在真实 lsof 下的行为。
  • heavy 档安全扫描:security-scan.mjs --base 5f0b5f4… → 「依赖漏洞扫描:本 PR 未新增依赖,无需扫描;静态扫描(semgrep,仅新增):0 条」(pr-7814-securityscan.json)。无新增第三方依赖;signoff 无 security 触发、security.softHits=0,无 riskySoftHits 需定性。
  • 未执行:完整 iOS 编译/安装/截图(与 PR 声明一致,本机无 CocoaPods);Windows 实机;全仓单测(由 CI client-ci 承担,已全绿)。

CI:client-ci / pr-design-basis / PR #7814 全部 completed+success。机器人静默期已等 267.7 分钟超时放行,copilot-pull-request-reviewer 未表态,其意见可能在合并后到达(按规则不阻断,特此说明)。

Intent alignment

  • 描述来源:PR 标题/正文(无关联 Issue,作者自述为改善 Mobile 模拟器截图任务的环境诊断与执行流程)。原目标:①保留兼容原生包优先复用;②补充缓存拒绝原因;③缓存未命中时先查 Xcode / Simulator SDK / CocoaPods 再 prebuild;④whoami 分阶段耗时与超时诊断、端口查询合并一次;⑤区分「检查失败」与「没有 Metro」。
  • 初始实现:当前可见最早提交 c414c879fd5(fix(mobile): 提前检查模拟器构建工具并改善诊断流程)。历史经改写:thread 中引用的 dbf2b43d1ea / 61acccd3db0 已不可取(本地无对象、GitHub 422),三条可见提交于 2026-10-29T08:28 重建并补签 DCO;以 c414c879fd5 为初始实现基线,其内容已包含全部核心目标(①–④主体),改写只涉及签名与后续两轮修复的落点。
  • 现在要合什么:ea628c03d85 = 初始实现 + 两轮 thread 修复。git diff c414c879fd5..ea628c03d85 仅 5 文件(sim-metro.mjs / lib/sim-whoami.mjs / sim-whoami.mjs / 1 个测试 / 1 行文档):
    • 189ef0678e(fix: 透传 Metro 进程身份探测错误)对应 Greptile thread discussion_r4409775119 的要求——command/cwd/source/Windows 快照失败经 onProbeError 进入 probeErrors,检查失败时拒绝身份确认并抑制「没发现 Metro」提示;
    • ea628c03d85(refactor: 通过生产入口验证模拟器 Metro 回执)对应 Codex thread discussion_r4409904097 的要求——提取 inspectSimMetroIdentity,测试不再读取/求值源码文本。
  • 对照结论:一致。核心功能①–⑤全部保留在最终 diff;两轮修复都是围绕原目标的缺陷修复与测试可达性重构,无功能删除、削弱或无关扩范围(未新增依赖、配置、API 或个人流程)。DCO thread(discussion_r4410191529)为 bot 误报合成 SHA,作者以 DCO App + check:dco 证据驳回,本审查复核成立,无需补签。行为变化(新超时上限、探测失败即非健康)均有作者/审查讨论明确依据且写入文档,未改变用户原目标。

Overall

pass —— 没有 P0/P1,原意一致性复核完成且无待裁定的核心方向问题,可以进入 guarded Approve 与合并。合并后需知悉:copilot-pull-request-reviewer 的意见可能在合并后到达;两条 bot thread 已 Resolve 且修复已逐条核实落实。

@MagicLizi
MagicLizi merged commit 4dd4425 into main Oct 29, 2026
24 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

touches:product-ui 改动碰到产品 / UI 面(review-pr 自动维护,仅展示) touches:rules 改动碰到规则 / 规范文档(review-pr 自动维护,仅展示)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants