Skip to content

macOS 实机验证与 universal DMG 构建(v0.1.0 任务书) #4

Description

@Ychris12138

目的

本 issue 是 macOS 适配的实机验证与 DMG 构建任务书,全部工作在 macOS 机器上执行;对应 PR #3(feat/v0.1-macos-support,Windows 侧已完成并验证)。范围红线:只做平台验证与构建,不做任何新功能(不碰 2a/agent),不改 docs/release.md §5 的任何红线项。

Step 0 — 环境准备

xcode-select --install        # 只需 Command Line Tools,不需要完整 Xcode
rustup update
node --version && rustc --version
git clone https://github.com/Ychris12138/ResearchThread.git
cd ResearchThread
git checkout feat/v0.1-macos-support
npm ci

Step 1 — 第一轮:native 开发验证

npm run tauri dev

逐项过(有失败就停下记录):

  • 应用启动,欢迎卡(或主界面)正常渲染、无白屏
  • 创建 Space → Project → Task,写 context,重启应用后数据还在
  • 数据目录 ~/ResearchThread 已创建(Finder ⌘⇧G 输入 ~/ResearchThread 直达)
  • 设置 → 数据:「快照保护」显示正常或警告(取决于是否装 git);「创建快照」可用
  • 删除任务 → 数据目录 .trash/ 出现带时间戳的文件(不是物理删除)

Step 2 — PATH 验收(本适配的 P0,必须过)

npm run tauri build -- --bundles app,dmg
open src-tauri/target/release/bundle/macos/ResearchThread.app

必须从 Finder/open 启动,不能从 Terminal 里前台跑——这才是 GUI PATH 场景。启动后在应用内底部终端逐个执行:

  • git --version 有输出
  • claude --version 有输出(没装 claude 则记录“未安装”)
  • codex --version 有输出(同上)
  • 设置 → 数据 → 「打开」→ Finder 正确打开 ~/ResearchThread(opener 验证)

若 git 找不到:说明 fix_path_env 未生效,把现象与终端报错贴到本 issue,不要自行改 capabilities。

Step 3 — 第二轮:universal DMG

rustup target add aarch64-apple-darwin x86_64-apple-darwin
npm run tauri build -- --target universal-apple-darwin --bundles app,dmg
npm run make-release
  • DMG 产出在 src-tauri/target/universal-apple-darwin/release/bundle/dmg/
  • npm run make-release 归拢成功,打印 DMG 的 SHA-256
  • 双击 DMG 安装到「应用程序」→ 启动 → 重复 Step 2 的 PATH 三件套(Finder 启动)
  • 未签名验证:把 DMG 拷到另一台(或删除 app 重装)→ 首次启动右键 → 打开 → 能过 Gatekeeper

Step 4 — 完整矩阵(docs/release.md §4-6 的 macOS 部分)

  • 连续双击两次启动:第二实例只聚焦已有窗口(单实例)
  • ⌘⇧Space 唤起收件箱
  • 用文本编辑器/Obsidian 外改任务文件 → 应用保存时弹「文件已被外部修改」冲突提示
  • 强制退出(⌥⌘Q 或活动监视器杀进程)→ 重启:数据完整、无 .rt-tmp/.rt-bak 残留
  • 无 git 的 Mac(或临时把 git 移出 PATH):左下「快照保护未生效」持续警告出现;装 git 后设置 → 数据 → 重试恢复
  • 旧 DMG 装的版本 → 新 DMG 覆盖安装 → 数据完好;删 .app 卸载 → ~/ResearchThread 仍在

Step 5 — 回报

在本 issue 下评论:

  1. Step 1–4 的清单勾选结果(失败的注明现象 + 控制台报错原文)
  2. DMG 文件名 + SHA-256 + 机器芯片型号(M 系列第几代)/ macOS 版本
  3. xcrun lipo -archs src-tauri/target/universal-apple-darwin/release/bundle/macos/ResearchThread.app/Contents/MacOS/researchthread 的输出(应含 x86_64 与 arm64)

全部通过后由仓库所有者合并 PR #3,DMG 与 Windows exe 汇总发布 v0.1.0。

Activity

  1. Ychris12138 commented on Sep 12, 2026

    @Ychris12138
    OwnerAuthor

    macOS 实机验证与 universal DMG 构建回报

    环境:Apple M5(arm64)/ macOS 26.6.2 / Node 24.19 / CLT + rustup(stable 1.98.1,aarch64 + x86_64 双 target)
    分支:feat/v0.1-macos-support(验证基于 e19f840,期间发现并修复 2 个问题,见文末)

    Step 0 环境准备 ✅

    xcode-select CLT 已装;rustup 经 Homebrew 安装(RUSTUP_HOME=/opt/homebrew/var/rustup);npm ci 正常。

    Step 1 native 开发验证 ✅(修复 bug 后全过)

    • 应用启动渲染:四区 IDE 布局完整,无白屏
    • 创建 Space → Project → Task(中文 slug「科研/第一个/2026-09-12-审稿意见回复.md」)、写上下文条目(日期+署名正确),重启后数据完好
    • 数据目录 ~/ResearchThread 启动即创建(含 settings.yaml / AGENTS.md / .mcp.json / .activity)
    • 设置→数据:快照保护「正常」;「创建快照」生成 git commit(snapshot: 2026-09-12T…);每日首启自动提交正常(init: ResearchThread data directory)
    • 删除任务 → .trash/2026-09-12T14-52-58_2026-09-12-审稿意见回复.md(带时间戳,非物理删除)

    Step 2 PATH 验收(P0)✅ 全绿

    open(Finder 场景)启动 release .app,进程 PATH 为完整登录 shell PATH(ps eww 验证含 ~/.nvm/.../bin)。应用内底部终端实测:

    RT > git --version      → git version 2.50.1 (Apple Git-155)  [exit 0]
    RT > claude --version   → 2.1.235 (Claude Code)               [exit 0]
    RT > codex --version    → codex-cli 0.149.0                   [exit 0]
    
    • 设置 → 数据 → 「打开」→ Finder 正确打开 ~/ResearchThread(opener 正常)

    Step 3 universal DMG ✅

    • lipo -archs → x86_64 arm64
    • DMG 产出 src-tauri/target/universal-apple-darwin/release/bundle/dmg/ResearchThread_0.1.0_universal.dmg
    • npm run make-release 归拢成功
    • DMG 安装到「应用程序」→ Finder 启动 → PATH 三件套复测通过;重装/覆盖安装数据完好
    • Gatekeeper(真实下载链验证,见下文发现 ②):未签名包被拦 → 系统设置 → 隐私与安全性 →「仍要打开」→ Touch ID 确认 → 成功放行启动

    Step 4 完整矩阵 ✅(1 项未测)

    • 连续两次启动:单实例生效,仅聚焦已有窗口
    • ⌘⇧Space 唤起收件箱(与系统无冲突)
    • 外部编辑器改任务文件 → watcher 秒级刷新;有未保存编辑时出「文件在外部被修改」横幅;保存被阻止弹「覆盖保存/重新加载/取消」,覆盖保存后磁盘内容正确
    • kill -9 强杀 → 重启:数据完整,无 .rt-tmp/.rt-bak 残留
    • 无 git 的 Mac:未测(本机有 git,且 git 在 /usr/bin 难以安全模拟;逻辑有测试覆盖)
    • 旧 DMG 重装/覆盖 → 数据完好;删 .app 卸载 → ~/ResearchThread 保留

    回报要求的信息

    • DMG:release/ResearchThread_0.1.0_universal.dmg
    • SHA-256:b9a7ad3acfd62ea49e4e8a0fca272b624402c325b929187ae88c091c7df37e49(构建提交 51c45a8 干净树)
    • 机器:Apple M5 / macOS 26.6.2
    • lipo:xcrun lipo -archs …/ResearchThread.app/Contents/MacOS/researchthread → x86_64 arm64

    验证过程中发现并修复的 2 个问题

    ① P1:macOS 上数据层初始化必失败(已修复,3e1ab0b)
    应用启动即白屏报「数据层初始化失败:forbidden path: ~/ResearchThread/.activity」。根因:tauri-plugin-fs 的 require_literal_leading_dot 只从 tauri.conf.json 的 plugins.fs 插件配置读取(capabilities 里 fs:scope 的同名字段被静默忽略);未设置时 Unix 默认 true(** 不匹配点路径),Windows 默认 false——所以 Windows 全绿、macOS 全挂。修复 = tauri.conf.json 增加 "plugins": { "fs": { "requireLiteralLeadingDot": false } }(对 Windows 是 no-op),并清理 capabilities 里的死配置。这颗雷证明 GUI 实机验证不可省——进程存活检查全部通过,只有真正看到 UI 才暴露。

    ② macOS 15+ 的 Gatekeeper「右键 → 打开」通道已被移除(文档已修正,51c45a8)
    用 Chrome 真实下载 DMG(带真实 quarantine)验证:无论双击还是右键 → 打开,未签名包都弹硬拦截「移到废纸篓 / 完成」,无「打开」选项。正确放行路径 = 系统设置 → 隐私与安全性 →「仍要打开」→ Touch ID/密码。已按系统版本分流更新 docs/seed-manual.md、docs/release.md(§3/§4-6/§7)、scripts/make-release.mjs README 模板、AGENTS.md。这也印证 §7 红线:面向陌生用户分发前必须 Developer ID + 公证。

    结论

    Step 1–4 全部通过(仅「无 git 场景」1 项未测,逻辑有测试覆盖)。两个 commit(3e1ab0b 修复、51c45a8 文档)已在 PR #3 分支,请仓库所有者审阅合并。后续建议(新 issue,不在本 PR 夹带):DMG 内放「安装须知」引导文件;首启检测 quarantine 出提示卡;申请 Apple Developer Program 做 Developer ID 签名 + 公证。

  2. Ychris12138 commented on Sep 12, 2026

    @Ychris12138
    OwnerAuthor

    补充:Gatekeeper 放行流程复测通过(真实下载链)

    按种子用户路径完整重演:Chrome 真实下载本 DMG(SHA b9a7ad3a…e49 核验一致,quarantine 来源 Chrome)→ 双击弹「移到废纸篓 / 完成」→ 点完成 → 系统设置 → 隐私与安全性 →「仍要打开」→ Touch ID → 放行成功,之后正常启动。与 51c45a8 更新后的手册指引逐字一致。

    注:手动 xattr 写 quarantine 不会触发 Gatekeeper 评估(syspolicyd 零记录,应用直接启动)——验证此流程必须走真实浏览器下载。macOS 侧验证至此全部完成。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions