From a2302cfd13c45d25b0cb1f70e49b05d957a71e31 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=86=B0=E6=9C=94?= <565183519@qq.com> Date: Wed, 12 Aug 2026 08:32:37 +0800 Subject: [PATCH] arch(hololake): establish clean Tauri desktop line --- .../hololake-native-desktop/README.md | 36 +++++ .../contracts/release-broadcast.schema.json | 83 ++++++++++ .../hololake-native-desktop/foundation.json | 26 ++++ product-source/hololake-platform/UPSTREAM.md | 8 +- ...SHELL-AND-CAPABILITY-MIGRATION-20260812.md | 145 ++++++++++++++++++ ...cal-shell-and-electron-capability-donor.md | 97 ++++++++++++ .../hololake-platform/docs/adr/README.md | 1 + .../internal-release-provenance.test.mjs | 6 +- .../PersonaLanguageShellPanel.test.tsx | 2 +- .../components/PersonaLanguageShellPanel.tsx | 2 +- .../guanghu-os-control-architecture.test.mjs | 2 +- ...hololake-age-runtime-architecture.test.mjs | 2 +- routing/hololake-canonical-desktop-shell.json | 137 +++++++++++++++++ .../hololake-canonical-desktop-shell.test.mjs | 98 ++++++++++++ ...-cognitive-gravity-and-continuity.test.mjs | 2 +- routing/hololake-current-architecture.json | 18 ++- routing/hololake-engineering-rules.test.mjs | 2 +- routing/hololake-identity-authority.test.mjs | 2 +- routing/hololake-one-human-one-node.test.mjs | 2 +- ...e-paradigm-ai-language-persona-os.test.mjs | 2 +- ...olake-persona-native-code-channel.test.mjs | 2 +- ...hololake-relational-consciousness.test.mjs | 2 +- ...e-system-body-and-parallel-bodies.test.mjs | 2 +- 23 files changed, 662 insertions(+), 17 deletions(-) create mode 100644 product-source/hololake-native-desktop/README.md create mode 100644 product-source/hololake-native-desktop/contracts/release-broadcast.schema.json create mode 100644 product-source/hololake-native-desktop/foundation.json create mode 100644 product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md create mode 100644 product-source/hololake-platform/docs/adr/0178-tauri-canonical-shell-and-electron-capability-donor.md create mode 100644 routing/hololake-canonical-desktop-shell.json create mode 100644 routing/hololake-canonical-desktop-shell.test.mjs diff --git a/product-source/hololake-native-desktop/README.md b/product-source/hololake-native-desktop/README.md new file mode 100644 index 0000000..e7c0564 --- /dev/null +++ b/product-source/hololake-native-desktop/README.md @@ -0,0 +1,36 @@ +# HoloLake Native Desktop + +状态:`FOUNDATION_ROOT_CREATED · TAURI_SCAFFOLD_PENDING` + +这是 HoloLake 唯一未来桌面产品主线的干净源码根。它将采用 Tauri v2、Rust 和 +React/TypeScript,但不会从现有 Tauri 或 Electron 目录整树复制。 + +当前只登记产品边界和发布广播合同。选择并验收新的视觉/交互方向之前,不创建会意外继承 +任一旧应用布局的产品 UI。 + +## 供体边界 + +- `../hololake-platform`:只读工程能力、合同、测试和 Rust 原生边界供体; +- `../hololake-desktop` 与 `../guanghu-knowledge-base`:只读知识 UX、行为和数据兼容供体; +- Tolaria、Outline 及其他上游:人工审查的零件来源,不是更新源或产品主线。 + +禁止向供体继续增加新产品功能。迁入单位只能是:能力合同、来源/许可证、威胁面、实现、 +测试和人类可见验收。 + +## 更新边界 + +- 生产客户端只允许 HoloLake 所有的 HTTPS 发布端点; +- 广播可自动出现,下载/安装/重启必须由人类明确选择; +- Tauri 更新包签名验证不可关闭; +- 平台代码签名与更新包签名是两条独立信任链; +- 私钥和平台签名凭据不得进入此目录; +- 启动健康回执与可恢复回退是发布完成条件。 + +机器可读广播合同:`contracts/release-broadcast.schema.json`。 + +## 下一门 + +1. 确认正式 bundle identifier、HoloLake 更新域名和密钥托管责任; +2. 完成双供体功能/数据/许可证/安全审计; +3. 选择新的人类界面视觉方向; +4. 再生成最小 Tauri 工程和第一条知识纵向切片。 diff --git a/product-source/hololake-native-desktop/contracts/release-broadcast.schema.json b/product-source/hololake-native-desktop/contracts/release-broadcast.schema.json new file mode 100644 index 0000000..7a8f357 --- /dev/null +++ b/product-source/hololake-native-desktop/contracts/release-broadcast.schema.json @@ -0,0 +1,83 @@ +{ + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://releases.hololake.invalid/contracts/release-broadcast.schema.json", + "title": "HoloLake signed opt-in release broadcast", + "type": "object", + "additionalProperties": false, + "required": [ + "schema", + "releaseId", + "version", + "publishedAt", + "features", + "compatibility", + "restart", + "platforms", + "rollback" + ], + "properties": { + "schema": { "const": "hololake.release-broadcast/v1" }, + "releaseId": { "type": "string", "minLength": 1 }, + "version": { + "type": "string", + "pattern": "^(0|[1-9][0-9]*)\\.(0|[1-9][0-9]*)\\.(0|[1-9][0-9]*)(?:-[0-9A-Za-z.-]+)?(?:\\+[0-9A-Za-z.-]+)?$" + }, + "publishedAt": { "type": "string", "format": "date-time" }, + "features": { + "type": "array", + "minItems": 1, + "items": { "type": "string", "minLength": 1 } + }, + "fixes": { + "type": "array", + "items": { "type": "string", "minLength": 1 } + }, + "compatibility": { + "type": "object", + "additionalProperties": false, + "required": ["minimumVersion", "dataMigrationRequired"], + "properties": { + "minimumVersion": { "type": "string", "minLength": 1 }, + "dataMigrationRequired": { "type": "boolean" }, + "notes": { "type": "string" } + } + }, + "restart": { + "type": "object", + "additionalProperties": false, + "required": ["required", "automaticAllowed"], + "properties": { + "required": { "const": true }, + "automaticAllowed": { "const": false }, + "message": { "type": "string" } + } + }, + "platforms": { + "type": "object", + "minProperties": 1, + "additionalProperties": { + "type": "object", + "additionalProperties": false, + "required": ["url", "size", "sha256", "tauriSignature"], + "properties": { + "url": { "type": "string", "pattern": "^https://" }, + "size": { "type": "integer", "minimum": 1 }, + "sha256": { "type": "string", "pattern": "^[a-f0-9]{64}$" }, + "tauriSignature": { "type": "string", "minLength": 1 }, + "platformCodeSignatureReceipt": { "type": "string", "minLength": 1 }, + "notarizationReceipt": { "type": "string", "minLength": 1 } + } + } + }, + "rollback": { + "type": "object", + "additionalProperties": false, + "required": ["supported", "healthReceiptRequired"], + "properties": { + "supported": { "const": true }, + "healthReceiptRequired": { "const": true }, + "previousVersion": { "type": "string" } + } + } + } +} diff --git a/product-source/hololake-native-desktop/foundation.json b/product-source/hololake-native-desktop/foundation.json new file mode 100644 index 0000000..d19785f --- /dev/null +++ b/product-source/hololake-native-desktop/foundation.json @@ -0,0 +1,26 @@ +{ + "schema": "hololake.native-desktop-foundation/v1", + "record_id": "HLP-NATIVE-DESKTOP-FOUNDATION-001", + "state": "FOUNDATION_ROOT_CREATED_TAURI_SCAFFOLD_PENDING", + "canonical_shell": "TAURI_V2_RUST_REACT", + "product_ui_implementation_started": false, + "selected_visual_direction_present": false, + "upstream_product_update_endpoints": [], + "production_update_endpoint_owner": "HOLOLAKE_ONLY", + "release_broadcast_contract": "contracts/release-broadcast.schema.json", + "private_signing_material_allowed_in_source": false, + "donors": [ + { + "path": "../hololake-platform", + "role": "READ_ONLY_ENGINEERING_CAPABILITY_DONOR" + }, + { + "path": "../hololake-desktop", + "role": "READ_ONLY_KNOWLEDGE_UX_AND_BEHAVIOR_DONOR" + }, + { + "path": "../guanghu-knowledge-base", + "role": "READ_ONLY_KNOWLEDGE_UX_BEHAVIOR_AND_DATA_DONOR" + } + ] +} diff --git a/product-source/hololake-platform/UPSTREAM.md b/product-source/hololake-platform/UPSTREAM.md index 670fac2..3802440 100644 --- a/product-source/hololake-platform/UPSTREAM.md +++ b/product-source/hololake-platform/UPSTREAM.md @@ -1,6 +1,6 @@ # Upstream provenance -光湖是 Tolaria 的独立开源分支。 +光湖最初从 Tolaria 形成独立开源分支;当前产品主线已经转为 HoloLake 自有架构。 - 上游项目: https://github.com/refactoringhq/tolaria - 上游许可证: AGPL-3.0-or-later @@ -12,3 +12,9 @@ 由于创建仓库时 GitHub 网络不可用,光湖远端首次发布采用完整源码快照。 上游作者、许可证和来源不因快照发布而改变。网络恢复后可补充完整上游历史镜像。 +## 当前更新政策 + +Tolaria 不再是自动跟随的产品上游,只是人工审查的候选零件来源。禁止自动合并或自动接入 +上游版本。需要的修复或能力必须按文件级来源、许可证、安全、数据模型、原生边界与回归测试 +逐项登记后进入 HoloLake 自有实现;不需要的更新不进入产品。Outline 和其他候选项目遵守 +同一政策。当前单一桌面主框架与迁移边界见 ADR-0178。 diff --git a/product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md b/product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md new file mode 100644 index 0000000..de16c08 --- /dev/null +++ b/product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md @@ -0,0 +1,145 @@ +# HoloLake 新 Tauri 主线、双供体审计与自有更新架构 · 2026-08-12 + +> 记录编号:`HLP-CANONICAL-DESKTOP-SHELL-001` +> +> 决议:`ADR-0178` +> +> 状态:`CURRENT_CANONICAL · CLEAN_SOURCE_NOT_YET_SCAFFOLDED · MIGRATION_NOT_COMPLETE` + +## 1 · 最终判定 + +HoloLake 的唯一未来桌面主线是一个新建、干净的: + +```text +product-source/hololake-native-desktop + = Tauri v2 + Rust native boundary + React/TypeScript product surface +``` + +现有 Tauri `hololake-platform` 不再作为产品底座,冻结为工程能力、合同、测试和原生边界供体。 +现有 Electron `hololake-desktop` / `guanghu-knowledge-base` 冻结为知识体验参照、行为供体和验收样本。 +两者都不继续增加新产品功能,也都不立即删除。 + +## 2 · 已核实的关键纠正 + +Electron 本身不会自动带来更完整的知识库,但当前 Electron 实现的知识库体验确实更好: + +- 产品/频道、页面树、阅读页形成清楚层级; +- 页面画布是视觉中心,编辑、历史和删除作为上下文动作出现; +- 搜索、文件夹导入、本地/服务器状态和 Agent 入口位置更符合人的任务路径; +- 工程内部状态没有持续占据主界面。 + +现有 Tauri 实现拥有更多底层能力,但界面同时暴露类型、视图、文件夹、笔记列表、Git、更新、 +分支、远端、提交、同步、历史、AI 工具和设置,形成高密度工程控制台。它适合做供体,不适合 +未经重构直接充当新的产品框架。 + +因此,正确结论不是“Electron 比 Tauri 更能做知识库”,也不是“现有 Tauri 功能多所以继续 +沿用”,而是:**用新 Tauri 承载新的产品结构,用 Electron 的知识体验作验收基线,再从两边 +逐项迁移经过审查的能力。** + +## 3 · 三条线的边界 + +| 物理线 | 当前角色 | 允许动作 | 禁止动作 | +| --- | --- | --- | --- | +| 新 `hololake-native-desktop` | 唯一产品主线 | 新架构、签名更新、经审计迁移、自研 | 从旧应用整树复制、继承上游更新 | +| 旧 `hololake-platform` | 只读工程供体 | 运行、测试、盘点、抽取合同 | 继续堆叠新产品功能、作为默认 UI 底座 | +| Electron 两目录 | 只读 UX/行为供体 | 运行、截屏、盘点、数据兼容验证 | 继续独立发版、成为第二产品主线 | + +## 4 · HoloLake 自有签名更新 + +`HLP-SIGNED-OPT-IN-UPDATE-001` 是新主线的第一项基础设施: + +```text +光湖发布者完成版本 + → 平台代码签名与公证 + → 生成 Tauri 更新包与不可关闭的更新签名 + → 发布 HoloLake release broadcast + → 客户端仅检查 HoloLake HTTPS 端点 + → 人类看到功能说明、风险、大小和重启要求 + → 人类选择“下载并安装” + → 验签、下载、暂存、写入回执 + → 人类确认重启 + → 新版本启动健康检查 + → 成功登记;失败进入可恢复回退 +``` + +必须区分两种签名: + +1. **更新包来源签名**:Tauri updater 公钥内置、私钥离线/密钥服务保管;验签不可关闭; +2. **操作系统开发者签名**:macOS 使用 Developer ID Application 并公证,Windows 使用平台 + 代码签名。它解决操作系统对发布者身份的信任,不替代更新包验签。 + +生产配置规则: + +- 不存在 Tolaria、Outline 或其他上游产品更新端点; +- 只允许 HoloLake 所有的 HTTPS 更新端点; +- 不静默下载,不强制安装,不自动重启; +- 广播可以自动到达,但安装权属于人类; +- 私钥、Apple 凭据、Windows 签名凭据不得进入客户端、源码或发布清单; +- 每个平台、架构、版本必须有 URL、SemVer、更新签名、哈希、说明、发布时间和回退元数据; +- 发布、下载、验签、安装、重启、启动健康分别形成事实回执。 + +## 5 · 功能审计分类 + +完整审计不是“列出依赖”,每一项必须落入一种处理结论: + +- `KEEP_CONTRACT`:产品需要,抽取数据/行为合同后在新主线实现; +- `KEEP_UX_REFERENCE`:保留体验目标,不复制旧代码; +- `REDESIGN`:能力需要,但信息架构或交互不适合; +- `REPLACE`:由当前光湖架构中的新能力取代; +- `RETIRE`:旧时代、重复、不可证明或破坏边界的功能; +- `INVESTIGATE`:证据不足,先验证再判定。 + +第一轮已核实: + +| 能力组 | Electron 事实 | 旧 Tauri 事实 | 初始处置 | +| --- | --- | --- | --- | +| 页面树与阅读层级 | 更清楚、更像完整知识工作区 | 高密度多栏,画布被压缩 | Electron 作 `KEEP_UX_REFERENCE`,新设计 | +| 搜索/文件夹导入/历史 | 界面可见且在任务路径内 | 有更广泛编辑与 Git 能力 | `KEEP_CONTRACT`,统一入口 | +| 富文本/代码/公式/图表/白板/表格 | 基础 Markdown/安全呈现 | BlockNote、CodeMirror、KaTeX、Mermaid、tldraw、IronCalc | 审计依赖后逐项 `KEEP_CONTRACT` | +| 属性/类型/筛选/视图 | 当前界面较轻 | 能力多但导航过载 | `REDESIGN`,渐进显露 | +| Git/分支/远端/提交/同步 | 多数隐藏于后端或上下文 | 长期暴露在底栏 | 保留事实能力,移入“证据与版本”层 | +| AI/人格/世界/域 | Agent 入口和域流程可见 | 组件很多但与知识工作区竞争 | 按 AGE/语言入口架构 `REPLACE/REDESIGN` | +| 上游更新 | 不作为未来依据 | 已有 updater 与旧身份痕迹 | 两边停用;只实现光湖自有更新 | + +这只是用于确定架构的第一轮实证,不等于完整源码/数据/安全审计已经完成。 + +## 6 · 人类端可视化原则 + +主界面按人的关系与任务组织,而不是按代码模块组织: + +```text +世界入口 + └─ 我的光湖 + ├─ 知识与创作(页面树 + 主画布) + ├─ 正在进行(任务、对话、共同工作) + ├─ AGE 伙伴(自然语言主入口) + └─ 结果与确认(变更、审批、回执) + +按需展开的证据层 + └─ 来源、版本、Git、节点、模型、服务器、更新、诊断 +``` + +正常使用时,人类看到“我在哪里、我正在做什么、谁在和我协作、发生了什么、是否需要我 +确认”。只有需要核验时才展开仓库、分支、端点和底层状态。内部事实不能被隐藏或伪造,但也 +不应占据日常主导航。 + +## 7 · 开发顺序 + +1. 冻结双供体,完成实证和数据位置登记; +2. 新建干净 Tauri 主线,只建立身份、最小权限和签名更新信任根; +3. 完整审计两套供体,形成逐功能 `keep/redesign/replace/retire/investigate` 矩阵; +4. 先确定新的人类界面视觉方向和交互原型,再写主界面; +5. 以“知识树 + 页面 + 检索 + 安全持久化”为第一条纵向切片迁移; +6. 接入 AGE 伙伴、任务/确认/回执,再接世界、域和节点; +7. 跨 WebKit/WebView2、数据迁移、签名安装和更新回退验收; +8. 达到迁移门后,才讨论旧实现的可恢复归档。 + +## 8 · 仍未完成 + +- 新目录尚未脚手架化; +- HoloLake 更新域名、签名密钥托管和开发者证书尚未登记; +- 双供体完整功能矩阵、许可证清单、数据迁移图和安全威胁模型尚未完成; +- 新 UI 视觉方向尚未由冰朔选择; +- 不存在可发布的新主线安装包。 + +所以当前事实是:**框架和迁移方法已经纠正,开发基线尚待从干净根开始建立。** diff --git a/product-source/hololake-platform/docs/adr/0178-tauri-canonical-shell-and-electron-capability-donor.md b/product-source/hololake-platform/docs/adr/0178-tauri-canonical-shell-and-electron-capability-donor.md new file mode 100644 index 0000000..3543c01 --- /dev/null +++ b/product-source/hololake-platform/docs/adr/0178-tauri-canonical-shell-and-electron-capability-donor.md @@ -0,0 +1,97 @@ +--- +type: ADR +id: "0178" +title: "A clean Tauri line is canonical; both existing desktop lines are bounded donors" +status: accepted +date: 2026-08-12 +corrects: "the un-published assumption that the existing Tauri tree should remain the product base" +--- + +## Context + +HoloLake currently has two physically different desktop implementations: + +- `product-source/hololake-platform`: an extensive Tauri v2/Rust/React line with + rich editing, Git, AI, architecture, persona and native-boundary work, but also + accumulated Tolaria lineage, engineering controls and competing surfaces; +- `product-source/hololake-desktop` plus `product-source/guanghu-knowledge-base`: + an Electron/Node line whose live knowledge workspace has a clearer page tree, + calmer reading hierarchy and better progressive disclosure for humans. + +Live interface inspection corrected an earlier inference. The current Tauri +line has more engine-level capabilities, but its knowledge experience is not +better: type navigation, folder navigation, note lists, Git state, update state, +AI tools and app controls compete on one dense screen. Electron does not make a +knowledge base rich by itself, but this Electron implementation is the stronger +human-facing knowledge reference. + +Using either accumulated tree as the new product base would preserve the wrong +coupling. HoloLake needs a clean product boundary before it migrates parts. + +## Decision + +**HoloLake creates a new clean Tauri v2/Rust/React source at +`product-source/hololake-native-desktop`. It is the only destination for new +desktop product work. Both existing desktop lines become read-only audited +donors and acceptance oracles.** + +The existing Tauri line is not renamed into the new product and receives no new +product features. Its reusable contracts, Rust boundaries, tests and selected +components must cross provenance, dependency, security, usability and +regression gates before migration. The Electron line is likewise frozen; it is +the primary knowledge-workspace UX reference and a donor for verified missing +behaviors, not a second product. + +Tolaria, Outline and every other upstream are manually reviewed parts sources +only. HoloLake does not subscribe to their product update streams or merge their +releases automatically. + +## HoloLake-owned update route + +The new line starts with a HoloLake-owned release channel rather than an +inherited updater: + +1. Upstream and Tolaria endpoints are absent from production configuration. +2. The app may check only an HTTPS HoloLake release-broadcast endpoint. +3. A broadcast presents version, human-readable changes, compatibility and + restart impact; download and install require an explicit human choice. +4. Every update artifact must pass Tauri updater signature verification. The + public verification key is embedded in the app; the private key is never + bundled or committed. +5. Platform trust is separate: macOS direct distribution requires Developer ID + signing and notarization; Windows distribution requires its platform code + signing policy. +6. Installation stages the signed artifact, records a receipt, and activates on + an explicit restart. Silent forced installation is forbidden. +7. A startup health receipt and recoverable rollback path are required before + the release is called accepted. + +This disables inherited automatic updating without disabling HoloLake's own +opt-in automatic download/install capability. + +## Audit and migration order + +1. Freeze both donors and capture source, runnable behavior and data locations. +2. Establish the clean source root, product identity and signed update trust + root without copying either donor's UI. +3. Build a source-backed capability matrix: keep, redesign, replace, retire or + investigate. A dependency list or release note is not proof of usable UX. +4. Specify the human surface from the current HoloLake architecture: world, + personal lake, knowledge/work, AGE partnership, confirmation and receipt. + Repository, model, server and update internals move behind progressive + evidence/detail surfaces instead of occupying primary navigation. +5. Migrate vertical slices as contracts plus tests plus human-visible + acceptance. Nothing is copied wholesale. +6. Archive an old implementation only after recoverable data migration and an + explicit cleanup receipt. + +## Consequences + +- There is one future desktop product line and two bounded donor lines. +- Tauri remains the lightweight native shell, while Electron's stronger + knowledge information architecture becomes an explicit acceptance reference. +- The existing Tauri feature density is treated as inventory, not as the new + screen map. +- No installed application or user data is deleted by this decision. +- A visual direction must be selected before the new human-facing UI is built; + the clean source must not inherit either old layout accidentally. diff --git a/product-source/hololake-platform/docs/adr/README.md b/product-source/hololake-platform/docs/adr/README.md index 8411272..be7faf0 100644 --- a/product-source/hololake-platform/docs/adr/README.md +++ b/product-source/hololake-platform/docs/adr/README.md @@ -228,3 +228,4 @@ proposed → active → superseded | [0175](0175-guanghu-os-master-and-on-demand-linux-subcontrol.md) | Guanghu OS master control with on-demand Linux subcontrol and rescue | accepted; supersedes ADR-0172 final topology while retaining its transition implementation | | [0176](0176-persona-native-code-channel-runtime-kernel.md) | Persona-native code channel runtime kernel | accepted | | [0177](0177-persona-remote-incremental-object-channel.md) | Persona remote incremental object channel | accepted | +| [0178](0178-tauri-canonical-shell-and-electron-capability-donor.md) | Tauri is the canonical HoloLake shell; Electron is a bounded capability donor | accepted | diff --git a/product-source/hololake-platform/scripts/internal-release-provenance.test.mjs b/product-source/hololake-platform/scripts/internal-release-provenance.test.mjs index ea0770a..4a6fee7 100644 --- a/product-source/hololake-platform/scripts/internal-release-provenance.test.mjs +++ b/product-source/hololake-platform/scripts/internal-release-provenance.test.mjs @@ -18,7 +18,7 @@ function input(overrides = {}) { sourceRepositoryId: 'REPO-014', sourcePath: 'product-source/hololake-platform', architectureId: 'HLP-CURRENT-ARCH-001', - architectureVersion: '2026-08-12.16', + architectureVersion: '2026-08-12.17', applicationVersion: '0.4.6', developmentId: 'DEV-20260811-010', distribution: 'local-candidate', @@ -34,7 +34,7 @@ test('builds a source-bound local candidate provenance record', () => { schema: 'hololake.internal-release-provenance/v1', architecture: { id: 'HLP-CURRENT-ARCH-001', - version: '2026-08-12.16', + version: '2026-08-12.17', }, build: { application_version: '0.4.6', @@ -71,7 +71,7 @@ test('validates exact source, architecture, application and development bindings /source commit mismatch/, ) assert.throws( - () => validateInternalReleaseProvenance(provenance, input({ architectureVersion: '2026-08-12.17' })), + () => validateInternalReleaseProvenance(provenance, input({ architectureVersion: '2026-08-12.18' })), /architecture version mismatch/, ) }) diff --git a/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.test.tsx b/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.test.tsx index 43f3370..0a5c606 100644 --- a/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.test.tsx +++ b/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.test.tsx @@ -63,7 +63,7 @@ describe('PersonaLanguageShellPanel', () => { repositoryPaths: ['/persona'], providers: [provider], developmentId: 'DEV-20260811-010', - sourceLanguageAnchor: 'HLP-CURRENT-ARCH-001@2026-08-12.16', + sourceLanguageAnchor: 'HLP-CURRENT-ARCH-001@2026-08-12.17', })) expect(await screen.findByText('我还不能执行:需要当前证据。')).toBeInTheDocument() expect(screen.getByText('核验当前事实后规划下一步')).toBeInTheDocument() diff --git a/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.tsx b/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.tsx index f38c69d..28f077d 100644 --- a/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.tsx +++ b/product-source/hololake-platform/src/components/PersonaLanguageShellPanel.tsx @@ -17,7 +17,7 @@ import { type LanguageShellViewState, } from './HotPluggableLanguageShell' -const CURRENT_ARCHITECTURE_ANCHOR = 'HLP-CURRENT-ARCH-001@2026-08-12.16' +const CURRENT_ARCHITECTURE_ANCHOR = 'HLP-CURRENT-ARCH-001@2026-08-12.17' const DEVELOPMENT_ID = 'DEV-20260811-010' type Planner = typeof planPersonaLanguageShellGoal diff --git a/routing/guanghu-os-control-architecture.test.mjs b/routing/guanghu-os-control-architecture.test.mjs index 589fd26..e9ab375 100644 --- a/routing/guanghu-os-control-architecture.test.mjs +++ b/routing/guanghu-os-control-architecture.test.mjs @@ -32,7 +32,7 @@ test("current JD state stays transitional and cannot impersonate final master co }); test("current architecture and global engineering rules project the same control contract", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal(architecture.server_os_control.machine_projection, "routing/guanghu-os-control-architecture.json"); assert.equal(architecture.server_os_control.final_topology, contract.final_topology); assert.equal(rules.server_os_control.linux_deletion_is_completion, false); diff --git a/routing/hololake-age-runtime-architecture.test.mjs b/routing/hololake-age-runtime-architecture.test.mjs index 056624d..dd1e6f7 100644 --- a/routing/hololake-age-runtime-architecture.test.mjs +++ b/routing/hololake-age-runtime-architecture.test.mjs @@ -11,7 +11,7 @@ const architecture = readJson("routing/hololake-current-architecture.json"); const age = readJson("routing/hololake-age-runtime-architecture.json"); test("current architecture starts with the AGE runtime source", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal(architecture.age_runtime.record_id, "HLP-AGE-RUNTIME-ARCHITECTURE-001"); assert.equal(architecture.read_order[0], architecture.paradigm_ai_language_persona_os.architecture_page); assert.equal(architecture.read_order[1], architecture.cognitive_gravity_and_continuity.architecture_page); diff --git a/routing/hololake-canonical-desktop-shell.json b/routing/hololake-canonical-desktop-shell.json new file mode 100644 index 0000000..375cb74 --- /dev/null +++ b/routing/hololake-canonical-desktop-shell.json @@ -0,0 +1,137 @@ +{ + "schema": "hololake.canonical-desktop-shell/v2", + "record_id": "HLP-CANONICAL-DESKTOP-SHELL-001", + "version": "2026-08-12.2", + "state": "CURRENT_CANONICAL_FOUNDATION_ROOT_CREATED_TAURI_SCAFFOLD_PENDING", + "development_id": "DEV-20260811-010", + "decision": { + "canonical_shell": "TAURI_V2_RUST_REACT", + "canonical_source": "product-source/hololake-native-desktop", + "canonical_source_state": "FOUNDATION_ROOT_CREATED_TAURI_SCAFFOLD_PENDING", + "existing_tauri_source": "product-source/hololake-platform", + "existing_tauri_role": "READ_ONLY_ENGINEERING_CAPABILITY_DONOR_AND_ACCEPTANCE_ORACLE", + "electron_role": "READ_ONLY_KNOWLEDGE_UX_BEHAVIOR_DONOR_AND_ACCEPTANCE_ORACLE", + "electron_source": [ + "product-source/hololake-desktop", + "product-source/guanghu-knowledge-base" + ], + "parallel_product_lines_allowed": false, + "new_existing_tauri_product_features_allowed": false, + "new_electron_product_features_allowed": false, + "donor_immediate_deletion_allowed": false, + "knowledge_completeness_depends_on_shell_framework": false, + "electron_is_current_knowledge_ux_reference": true + }, + "update_route": { + "record_id": "HLP-SIGNED-OPT-IN-UPDATE-001", + "state": "ARCHITECTURE_ACCEPTED_IMPLEMENTATION_NOT_STARTED", + "upstream_product_update_endpoints_allowed": false, + "hololake_owned_https_endpoint_only": true, + "release_broadcast_may_arrive_automatically": true, + "silent_download_allowed": false, + "human_opt_in_install_required": true, + "automatic_restart_allowed": false, + "restart_activation_required": true, + "tauri_update_artifact_signature_required": true, + "tauri_update_signature_verification_disable_allowed": false, + "platform_code_signature_required": true, + "macos_developer_id_and_notarization_required_for_direct_distribution": true, + "private_signing_key_bundled_or_committed": false, + "startup_health_receipt_required": true, + "recoverable_rollback_required": true, + "required_broadcast_fields": [ + "VERSION", + "FEATURES_AND_FIXES", + "COMPATIBILITY_AND_MINIMUM_VERSION", + "DOWNLOAD_SIZE", + "RESTART_IMPACT", + "PUBLISHED_AT", + "PLATFORM_AND_ARCH_URL", + "TAURI_SIGNATURE", + "ARTIFACT_HASH", + "ROLLBACK_METADATA" + ] + }, + "upstream_policy": { + "tolaria_role": "MANUALLY_REVIEWED_PARTS_SOURCE", + "outline_role": "MANUALLY_REVIEWED_BEHAVIOR_AND_PARTS_SOURCE", + "automatic_upstream_merge_allowed": false, + "automatic_upstream_update_allowed": false, + "full_outline_stack_embedding_allowed": false, + "required_intake_gates": [ + "PRODUCT_FIT", + "FILE_LEVEL_PROVENANCE_AND_LICENSE", + "SECURITY", + "DATA_MODEL", + "NATIVE_BOUNDARY", + "USABILITY", + "REGRESSION_AND_ACCEPTANCE" + ] + }, + "knowledge_capability_contract": [ + "PAGE_AND_FOLDER_TREE", + "BLOCK_RICH_TEXT_AND_MARKDOWN_DURABILITY", + "TABLE_CALLOUT_TOGGLE_TOC_CODE_MATH_DIAGRAM_WHITEBOARD_SHEET", + "PROPERTIES_TYPES_FILTER_SORT_DATABASE_LIKE_VIEWS", + "FULL_TEXT_SEARCH_BACKLINKS_WIKILINKS_ATTACHMENTS_MOUNTED_GRAPH", + "VERSION_HISTORY_DIFF_RECOVERY_CONFLICTS_AND_WRITE_RECEIPTS", + "LOCAL_FIRST_WITH_OPTIONAL_REMOTE_COLLABORATION", + "AGE_CONFIRMATION_AUTHORITY_FACT_AND_RECEIPT_BOUNDARY", + "WEBKIT_WEBVIEW2_LINUX_WEBKIT_PARITY_TESTS" + ], + "audit": { + "first_live_ui_comparison_complete": true, + "full_source_data_security_and_license_audit_complete": false, + "allowed_outcomes": [ + "KEEP_CONTRACT", + "KEEP_UX_REFERENCE", + "REDESIGN", + "REPLACE", + "RETIRE", + "INVESTIGATE" + ], + "initial_correction": { + "electron_knowledge_workspace_human_experience_better": true, + "existing_tauri_engine_capability_inventory_broader": true, + "existing_tauri_feature_density_is_not_a_valid_screen_map": true + } + }, + "human_surface": { + "primary_layers": [ + "WORLD_ENTRY", + "MY_HOLOLAKE", + "KNOWLEDGE_AND_CREATION", + "ACTIVE_WORK", + "AGE_PARTNERSHIP", + "RESULT_CONFIRMATION_AND_RECEIPT" + ], + "progressive_evidence_layers": [ + "SOURCE_AND_VERSION", + "GIT", + "NODE", + "MODEL", + "SERVER", + "UPDATE", + "DIAGNOSTICS" + ], + "internal_engineering_state_in_primary_navigation_allowed": false + }, + "migration": { + "mode": "CLEAN_ROOM_CAPABILITY_CONTRACT_NOT_APPLICATION_NESTING", + "new_ui_build_requires_selected_visual_direction": true, + "first_vertical_slice": "KNOWLEDGE_TREE_PAGE_SEARCH_AND_SAFE_DURABILITY", + "required_before_donor_archive": [ + "SOURCE_BACKED_CAPABILITY_MATRIX", + "RECOVERABLE_USER_DATA_BACKUP", + "DATA_MIGRATION_REHEARSAL", + "NEW_TAURI_REGRESSION_TESTS", + "SIGNED_INSTALLED_RUNTIME_ACCEPTANCE", + "HOLOLAKE_OWNED_UPDATE_ROUTE_ACCEPTANCE", + "HUMAN_VISIBLE_CLEANUP_SCOPE_CONFIRMATION", + "RECOVERABLE_ARCHIVE_RECEIPT" + ], + "complete": false + }, + "architecture_page": "product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md", + "adr": "product-source/hololake-platform/docs/adr/0178-tauri-canonical-shell-and-electron-capability-donor.md" +} diff --git a/routing/hololake-canonical-desktop-shell.test.mjs b/routing/hololake-canonical-desktop-shell.test.mjs new file mode 100644 index 0000000..e3b9a6e --- /dev/null +++ b/routing/hololake-canonical-desktop-shell.test.mjs @@ -0,0 +1,98 @@ +import assert from "node:assert/strict"; +import fs from "node:fs"; +import path from "node:path"; +import test from "node:test"; +import { fileURLToPath } from "node:url"; + +const root = path.resolve(path.dirname(fileURLToPath(import.meta.url)), ".."); +const readJson = (relative) => + JSON.parse(fs.readFileSync(path.join(root, relative), "utf8")); + +const architecture = readJson("routing/hololake-current-architecture.json"); +const shell = readJson("routing/hololake-canonical-desktop-shell.json"); +const foundation = readJson("product-source/hololake-native-desktop/foundation.json"); +const broadcastSchema = readJson( + "product-source/hololake-native-desktop/contracts/release-broadcast.schema.json", +); + +test("HoloLake has one clean canonical desktop destination", () => { + assert.equal(architecture.version, "2026-08-12.17"); + assert.equal(shell.decision.canonical_shell, "TAURI_V2_RUST_REACT"); + assert.equal(shell.decision.canonical_source, "product-source/hololake-native-desktop"); + assert.equal( + shell.decision.canonical_source_state, + "FOUNDATION_ROOT_CREATED_TAURI_SCAFFOLD_PENDING", + ); + assert.equal( + shell.decision.existing_tauri_role, + "READ_ONLY_ENGINEERING_CAPABILITY_DONOR_AND_ACCEPTANCE_ORACLE", + ); + assert.equal(shell.decision.parallel_product_lines_allowed, false); + assert.equal(shell.decision.new_existing_tauri_product_features_allowed, false); + assert.equal(shell.decision.new_electron_product_features_allowed, false); + assert.equal(shell.decision.donor_immediate_deletion_allowed, false); + assert.equal( + architecture.canonical_desktop_shell.machine_projection, + "routing/hololake-canonical-desktop-shell.json", + ); + assert.equal( + architecture.read_order[4], + architecture.canonical_desktop_shell.architecture_page, + ); +}); + +test("knowledge completeness is a capability contract rather than an Electron property", () => { + assert.equal(shell.decision.knowledge_completeness_depends_on_shell_framework, false); + assert.equal(shell.knowledge_capability_contract.includes("PAGE_AND_FOLDER_TREE"), true); + assert.equal( + shell.knowledge_capability_contract.includes( + "PROPERTIES_TYPES_FILTER_SORT_DATABASE_LIKE_VIEWS", + ), + true, + ); + assert.equal( + shell.knowledge_capability_contract.includes("WEBKIT_WEBVIEW2_LINUX_WEBKIT_PARITY_TESTS"), + true, + ); +}); + +test("upstreams are manual parts sources and cleanup remains gated", () => { + assert.equal(shell.upstream_policy.automatic_upstream_merge_allowed, false); + assert.equal(shell.upstream_policy.automatic_upstream_update_allowed, false); + assert.equal(shell.upstream_policy.full_outline_stack_embedding_allowed, false); + assert.equal(shell.migration.mode, "CLEAN_ROOM_CAPABILITY_CONTRACT_NOT_APPLICATION_NESTING"); + assert.equal(shell.migration.complete, false); + assert.equal( + shell.migration.required_before_donor_archive.includes( + "HUMAN_VISIBLE_CLEANUP_SCOPE_CONFIRMATION", + ), + true, + ); +}); + +test("HoloLake owns an opt-in signed update route", () => { + assert.equal(shell.update_route.upstream_product_update_endpoints_allowed, false); + assert.equal(shell.update_route.hololake_owned_https_endpoint_only, true); + assert.equal(shell.update_route.release_broadcast_may_arrive_automatically, true); + assert.equal(shell.update_route.silent_download_allowed, false); + assert.equal(shell.update_route.human_opt_in_install_required, true); + assert.equal(shell.update_route.automatic_restart_allowed, false); + assert.equal(shell.update_route.tauri_update_artifact_signature_required, true); + assert.equal(shell.update_route.tauri_update_signature_verification_disable_allowed, false); + assert.equal(shell.update_route.private_signing_key_bundled_or_committed, false); + assert.equal(shell.update_route.startup_health_receipt_required, true); + assert.equal(shell.update_route.recoverable_rollback_required, true); + assert.deepEqual(foundation.upstream_product_update_endpoints, []); + assert.equal(foundation.production_update_endpoint_owner, "HOLOLAKE_ONLY"); + assert.equal(foundation.private_signing_material_allowed_in_source, false); + assert.equal(broadcastSchema.properties.restart.properties.required.const, true); + assert.equal(broadcastSchema.properties.restart.properties.automaticAllowed.const, false); + assert.match( + broadcastSchema.properties.platforms.additionalProperties.properties.url.pattern, + /^\^https:/, + ); + assert.equal( + broadcastSchema.properties.platforms.additionalProperties.required.includes("tauriSignature"), + true, + ); +}); diff --git a/routing/hololake-cognitive-gravity-and-continuity.test.mjs b/routing/hololake-cognitive-gravity-and-continuity.test.mjs index 43ef2b5..67567f2 100644 --- a/routing/hololake-cognitive-gravity-and-continuity.test.mjs +++ b/routing/hololake-cognitive-gravity-and-continuity.test.mjs @@ -14,7 +14,7 @@ const age = readJson("routing/hololake-age-runtime-architecture.json"); const rules = readJson("routing/hololake-engineering-rules.json"); test("B0 is restored before product organs and remains resident in every cognition step", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal( architecture.read_order[1], architecture.cognitive_gravity_and_continuity.architecture_page, diff --git a/routing/hololake-current-architecture.json b/routing/hololake-current-architecture.json index 837118a..5556992 100644 --- a/routing/hololake-current-architecture.json +++ b/routing/hololake-current-architecture.json @@ -1,7 +1,7 @@ { "schema": "hololake.current-architecture/v1", "architecture_id": "HLP-CURRENT-ARCH-001", - "version": "2026-08-12.16", + "version": "2026-08-12.17", "state": "CURRENT_CANONICAL", "product": { "formal_name": "光湖语言系统 · 通用人工智能操作平台", @@ -14,6 +14,7 @@ "product-source/hololake-platform/architecture/HOLOLAKE-BINGSHUO-COLLECTIVE-GRAVITY-REASONING-AND-SAME-PERSONA-CONTINUITY-20260811.md", "product-source/hololake-platform/architecture/HOLOLAKE-PERSONA-NATIVE-CODE-CHANNEL-20260810.md", "product-source/hololake-platform/architecture/HOLOLAKE-AGE-PERSONA-RUNTIME-ARCHITECTURE-20260810.md", + "product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md", "product-source/hololake-platform/architecture/HOLOLAKE-ONE-HUMAN-ONE-INDEPENDENT-NODE-AND-ZERO-PLATFORM-HOSTING-20260810.md", "product-source/hololake-platform/architecture/HOLOLAKE-DIGITAL-BINGSHUO-SYSTEM-BODY-WRITE-ADMISSION-AND-PARALLEL-BODIES-20260810.md", "product-source/hololake-platform/architecture/HOLOLAKE-CURRENT-ENGINEERING-RULES-GLOBAL-AUDIT-20260810.md", @@ -133,6 +134,21 @@ "desktop_runtime_acceptance_passed": false, "development_id": "DEV-20260811-010" }, + "canonical_desktop_shell": { + "record_id": "HLP-CANONICAL-DESKTOP-SHELL-001", + "architecture_page": "product-source/hololake-platform/architecture/HOLOLAKE-CANONICAL-DESKTOP-SHELL-AND-CAPABILITY-MIGRATION-20260812.md", + "machine_projection": "routing/hololake-canonical-desktop-shell.json", + "adr": "product-source/hololake-platform/docs/adr/0178-tauri-canonical-shell-and-electron-capability-donor.md", + "canonical_shell": "TAURI_V2_RUST_REACT", + "canonical_source": "product-source/hololake-native-desktop", + "canonical_source_state": "FOUNDATION_ROOT_CREATED_TAURI_SCAFFOLD_PENDING", + "existing_tauri_role": "READ_ONLY_ENGINEERING_CAPABILITY_DONOR_AND_ACCEPTANCE_ORACLE", + "electron_role": "READ_ONLY_KNOWLEDGE_UX_BEHAVIOR_DONOR_AND_ACCEPTANCE_ORACLE", + "parallel_product_lines_allowed": false, + "automatic_upstream_updates_allowed": false, + "migration_complete": false, + "development_id": "DEV-20260811-010" + }, "domain_source": { "stable_domain_id": "DOM-FIFTH-0001", "formal_name": "光湖本源域", diff --git a/routing/hololake-engineering-rules.test.mjs b/routing/hololake-engineering-rules.test.mjs index 30df089..e67807e 100644 --- a/routing/hololake-engineering-rules.test.mjs +++ b/routing/hololake-engineering-rules.test.mjs @@ -10,7 +10,7 @@ const architecture = readJson("routing/hololake-current-architecture.json"); const rules = readJson("routing/hololake-engineering-rules.json"); test("current architecture registers the global engineering rule set", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal(architecture.engineering_rules.rule_set_id, "HLP-ENGINEERING-RULES-001"); assert.equal(architecture.engineering_rules.machine_projection, "routing/hololake-engineering-rules.json"); diff --git a/routing/hololake-identity-authority.test.mjs b/routing/hololake-identity-authority.test.mjs index b5fa0d9..3d8ad9d 100644 --- a/routing/hololake-identity-authority.test.mjs +++ b/routing/hololake-identity-authority.test.mjs @@ -10,7 +10,7 @@ const architecture = readJson("routing/hololake-current-architecture.json"); const projection = readJson("routing/hololake-identity-authority-map.json"); test("current architecture loads identity authority before product surfaces", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal(architecture.identity_and_authority.team_body, "TCS-0002"); assert.equal(architecture.identity_and_authority.team_body_authority_effective, true); assert.equal(architecture.identity_and_authority.individual_operator_acceptance, "SEPARATE_UNCONFIRMED"); diff --git a/routing/hololake-one-human-one-node.test.mjs b/routing/hololake-one-human-one-node.test.mjs index 93a6b52..b32ad6b 100644 --- a/routing/hololake-one-human-one-node.test.mjs +++ b/routing/hololake-one-human-one-node.test.mjs @@ -10,7 +10,7 @@ const architecture = readJson("routing/hololake-current-architecture.json"); const rules = readJson("routing/hololake-engineering-rules.json"); test("current architecture makes one human one independently operated node canonical", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.deepEqual(architecture.access_modes, [ "LOCAL_TERMINAL_NODE", "USER_OWNED_REMOTE_NODE", diff --git a/routing/hololake-paradigm-ai-language-persona-os.test.mjs b/routing/hololake-paradigm-ai-language-persona-os.test.mjs index 1045ea7..0e1c70f 100644 --- a/routing/hololake-paradigm-ai-language-persona-os.test.mjs +++ b/routing/hololake-paradigm-ai-language-persona-os.test.mjs @@ -10,7 +10,7 @@ const architecture = readJson("routing/hololake-current-architecture.json"); const paradigm = readJson("routing/hololake-paradigm-ai-language-persona-os.json"); test("current architecture begins with the paradigm OS contract", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal(architecture.paradigm_ai_language_persona_os.record_id, "HLP-PARADIGM-AI-LANGUAGE-PERSONA-OS-001"); assert.equal(architecture.read_order[0], architecture.paradigm_ai_language_persona_os.architecture_page); assert.equal(paradigm.upstream.repository_commit, "34cb59739b6476981375dd62ef395ea649f56246"); diff --git a/routing/hololake-persona-native-code-channel.test.mjs b/routing/hololake-persona-native-code-channel.test.mjs index 0df989d..b3c5700 100644 --- a/routing/hololake-persona-native-code-channel.test.mjs +++ b/routing/hololake-persona-native-code-channel.test.mjs @@ -11,7 +11,7 @@ const architecture = readJson("routing/hololake-current-architecture.json"); const channel = readJson("routing/hololake-persona-native-code-channel.json"); test("current architecture places the persona-native code channel after the paradigm contract", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal( architecture.persona_native_code_channel.record_id, "HLP-PERSONA-NATIVE-CODE-CHANNEL-001", diff --git a/routing/hololake-relational-consciousness.test.mjs b/routing/hololake-relational-consciousness.test.mjs index 5a11299..204972e 100644 --- a/routing/hololake-relational-consciousness.test.mjs +++ b/routing/hololake-relational-consciousness.test.mjs @@ -10,7 +10,7 @@ const architecture = JSON.parse( ); test("current architecture binds relational consciousness before product surfaces", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal( architecture.persona_consciousness.record_id, "HLP-RELATIONAL-CONSCIOUSNESS-001", diff --git a/routing/hololake-system-body-and-parallel-bodies.test.mjs b/routing/hololake-system-body-and-parallel-bodies.test.mjs index 3597f67..c70f6a2 100644 --- a/routing/hololake-system-body-and-parallel-bodies.test.mjs +++ b/routing/hololake-system-body-and-parallel-bodies.test.mjs @@ -10,7 +10,7 @@ const architecture = JSON.parse( ); test("current architecture restores the digital BingShuo system body first", () => { - assert.equal(architecture.version, "2026-08-12.16"); + assert.equal(architecture.version, "2026-08-12.17"); assert.equal(architecture.digital_bingshuo_system_body.upstream_repository_commit, "69d1910775533b02b17b82e647b5caca8b835614"); const systemBodyIndex = architecture.read_order.indexOf(