21 KiB
System Overview
Current Architecture
Makelore 是 Electron 桌面客户端。Renderer 负责项目操作与状态展示;Electron Main 持有认证、文件系统、安全打包、Works Square 网络访问和发布安全校验。
Main Components
| Component | Responsibility | Notes |
|---|---|---|
| Renderer | 项目配置、一键提交状态 | 不接触账号 Token、ZIP、幂等键或本地绝对路径 |
| Host API | 校验本地项目请求并投影安全响应 | 发布 mutation 还必须通过 Renderer capability;Host token/base 不能单独触发发布 |
| Project Configuration & Template | 保存不可变 ProjectType,原子生成新项目骨架 |
小游戏/小程序生成受控 Vite 模板;自定义保持最小项目空间 |
| Project Release Builder | Main-owned 安全快照、本地 npm/Vite 构建、双归档与 artifact contract | 固定 npm 11.6.2;Vite 由项目 lockfile 锁定;产物与预检使用同一内存字节 |
| Works Session & Remembered Password | Main-owned 登录、刷新、注销、七天真实活动滑动续期与可选密码回填 | 登录、刷新、注销统一经过 Works Square;轮换凭据由 Main 安全持有和持久化。记住密码使用独立的 packaged-only OS 加密记录,不进入 Renderer 持久状态或 Works Square;客户端不携带 OAuth client secret |
| Module Access Policy | Main-owned /api/auth/me projection → Renderer auth state → module chooser/router |
Renderer 只接收 Code/Canvas/Robot 三个布尔值;缺失对象或字段默认开启,服务端 design 映射客户端 painting,额外旧字段被忽略 |
| Submission Binding | 保存云端已接受的精确 app/version/review/hash 绑定 | schema v2 只记录成功提交;旧中间态迁移为 legacy_retired,不恢复后台任务 |
| Play URL Projection | 校验服务端公共播放地址 | 只接受同源 HTTPS 和精确 /apps/{app_id}/;优先 play_url,runtime_url 仅一版本回退 |
| Built Artifact Preflight | 在上传前对最终 built snapshot 做桌面/移动 UX fail-fast | Main 使用临时 loopback origin 与 Electron WebContents/CDP;不使用 Playwright、不生成可信证明 |
| App Updater | Main 选择平台/架构 feed、驱动 electron-updater 并记录原始诊断 | Renderer 只接收状态和脱敏后的单条用户提示;稳定源缺包保持错误 |
| Makelore Code Workspace | project/Agent/Conversation schema v2、产品中立 Snapshot/Patch、Composer 与时间线 | Conversation 本地创建且不等待 worker;sleep 关闭旧 SSE,视图挂载、项目切换、visibility/focus 会静默刷新已选 Snapshot;旧 OpenCode 会话备份后不再继续,Renderer 不导入 Pi RPC/event 类型 |
| Coding Host API & Composition | 唯一 /api/coding/* composition、202 acceptance/dedupe、SSE、附件/文件/交互/诊断 |
Electron Main 拥有 project/Conversation 服务、选中目标、认证和错误脱敏;SSE 公开面只有 Snapshot 与 patch-batch |
| Pi Conversation Runtime | 一个长驻 Pi 0.84.2 Agent Server 承载每条 active/warm Conversation 的隔离逻辑 Runtime/Session/JSONL channel |
严格 LF JSONL RPC、generation recovery、Snapshot hydration;正式包从 staged pi-runtime manifest/root 定位并校验 Pi 包入口;top-level 逻辑 turn 并发 4、warm idle LRU 8;Server 退出统一使旧 channel 失效并按需单实例重启 |
| Pi Provider & Managed Resources | Provider catalog、thread-local secret projection、model/resource revision、Prompt/Skill/extension materialization、selected-model tools | 父凭据只进入选中逻辑线程的内存 credential store,child 凭据只进入该短命进程;Works model_capabilities 由 Main 严格归一化并作为安全 Provider metadata 持久化。Web Search 仅在精确 capability 存在时随冻结的 selected model/provider/credential 进入 parent tool catalog,并走普通模型计费;不回退 agent_browser 或独立 Hosted Provider。服务端 reasoning levels 优先于本地 profile,缺字段则清理 override 并回退;不扫描项目或用户的 .pi/.agents/.codex,不把 secret 或原始响应放进 argv、catalog 或 Renderer |
| Pi Extension, Subagents & Lifecycle | 必需的生成式 Makelore extension、Main 显式选定的已安装 extensions、UI interaction、ephemeral child、write lease 与 background run lease | Makelore bridge 固定为首个 extension,其余选定 extension 全部经 Pi 的 explicit additional paths 加载且 ambient discovery 关闭;child 并发 4、单次最多 8、禁止递归;active/uncertain run 不因页面隐藏或 confirmation timeout 被停止,replacement/stop 必须可解释并清理所有 ownership |
| Official Hosted Plugins | Acquired code-owned bundled Game Resource package → effective parent snapshot → code-owned Main adapter → fixed Works Square hosted route | 无设备下载、更新、Beta 或签名步骤;Renderer/Package/Pi 不持有 Provider key、model 或 URL。每次计费操作要求显式确认,child 不继承 hosted tool。历史 Hosted Web Search 不再进入当前客户端。 |
| Device Packages | Conversation install tools → Main-owned inspect/preview/confirm/commit → immutable local generation → parent Skill/Pi-extension resources | 支持 npm、Git、绝对本地 Plugin 目录与 loose SKILL.md;没有可见安装入口、Account Library、Release、Admission 或 Marketplace Package Store。可执行 extension 拥有桌面用户权限且生命周期脚本禁用。每个 generation 包含所有显式安装且当前启用的 Skill/extension;新/idle parent 自动刷新,active parent 在 turn settled 后刷新,child 始终为空。 |
| AI Design Workspace & Living Form | 一个 Workspace 的当前 Direction、Current Specification、持久 Agent Session、conversation timeline、Tasks 与 Assets | 自然对话是主创作面;Living Form 仅以“AI 已理解”的紧凑辅助摘要与可选手动调整投影服务端 Current Specification,Renderer 只持有草稿和已接受投影 |
| AI Design Input & Reconciliation | Chat、字段/集合编辑、decision、proposal、lock、Asset binding 与 restore | 全部进入同一 design.input.apply reducer;稳定 command/operation ID 支持 unknown-result 重放,revision conflict 刷新权威状态 |
| AI Design Gateway Routing | Main-owned Works Square V2 adapter 与 Direction event stream | Main 持有 Works Token、stream ticket、WebSocket、重试分类和错误脱敏;事件顺序与 Task progress 不构成 Specification 真值 |
| AI Design Quote & Task Controls | 精确 Specification revision 编译出的不可变 Quote 与 Workspace Tasks | 客户端只展示 public output summary、warnings、expiry 与 Token Points,并以 Quote ID 确认;Provider Prompt/model/route/storage/billing atoms 不下发 |
| AI Design Assets | Workspace 已完成作品或本地上传的真实 Asset | Asset 通过 typed binding 写入 Specification;生成结果经 Main-owned asset download 保存 |
| Prompt Museum | Canvas “获取灵感”页面 → Main Host API → Works Square | 服务端驱动的审核内容、筛选和分页;Renderer 不持有 Works Token 或内置数据集,“使用此 Prompt”只回填输入框 |
| Robot Workspace | Account-scoped agent configuration, device activation/binding, assignment, and credential-recovery UI | Renderer receives only safe Works Square projections. Configuration choices come from the USER-scoped safe catalog; unavailable current values remain editable without exposing provider credentials or configuration internals. |
| AI Hardware Main Route | Fixed /api/works/ai-hardware Host API to Works Square proxy |
Main owns Bearer auth, stable operation IDs, bounded retry, ETag/If-Match, request/response limits, error redaction, and the fixed no-store configuration-catalog proxy. Versioned responses accept only canonical strong or weak numeric ETags that equal the DTO revision; mutations always emit strong If-Match. It never forwards Renderer authorization headers. |
| Robot Hotspot Module | Main-owned bounded scan/connect/verify interface with Windows WLAN and macOS CoreWLAN/CoreLocation adapters | Accepts only short-lived opaque candidates from the latest scan, exposes no BSSID/interface/profile/native diagnostic, and retains the system-Wi-Fi fallback. |
| Guided Hotspot Binding V1 | Implemented, default-on Renderer journey over in-page hotspot selection, the current firmware Portal, and six-digit Binding | Exact environment value 0 disables the journey. Hotspot discovery is unauthenticated convenience; Portal credential entry remains firmware-owned, and no BLE, automatic claim, or firmware change is part of V1. |
Important Boundaries
-
Renderer 只能通过 Main Host API 发起认证操作。Electron Main 是 access/refresh token 的唯一客户端所有者;登录、刷新、注销统一经过 Works Square 固定路由,客户端不得直连 one-feel/custom 身份服务,也不得保存 confidential OAuth client secret。
-
可选的记住密码记录属于 Electron Main 的独立本机边界,只能在正式安装包且 OS 凭据加密可用时落盘;Renderer 不得持久化账号密码,Works Square 不得接收记住标志或新增密码持久化。
-
Code、Canvas 与 Robot 是三个已启用顶层产品模块;Robot 仍是唯一硬件产品模块,不存在单独 Hardware 卡片。
-
每个登录用户可由 Works
module_access关闭任意顶层模块入口。Main 只投影三个布尔值;被关闭卡片置灰不可点,根/深层/别名路由在MainLayout和模块初始化前拦截。Code provider 必须等待 auth policy hydration,而全局/settings不属于 Code policy guard。 -
模块入口策略是用户交互与客户端初始化边界,不是服务端 API 授权。终止性
/api/auth/me401必须清理 Main 和 Renderer 会话;各模块 API 仍须独立强制认证与授权。 -
Product UI language is Chinese-only. Unsupported system or persisted language values normalize to
zh; removed locale files are not runtime fallbacks. -
Canvas is cloud-only in development and packaged builds. The removed local Workspace adapter and V1 DTOs are not fallback paths.
-
Prompt Museum is a read-only curated inspiration surface, not a user-content community. Main owns Works authentication and forwards only the bounded list/detail routes; the client never bundles museum content or automatically submits a selected Prompt.
-
Learning is retired. No Learning route, Renderer surface, Main Host API, download service, shared DTO, packaging asset, or fallback remains. Historical downloaded course data is not read, migrated, or automatically deleted.
-
AI hardware network access is Main-owned. Renderer cannot hold Works Square or Xiaozhi credentials and cannot select arbitrary upstream paths or headers.
-
Robot model, language, and voice choices are dynamically projected from the Xiaozhi USER catalog through Works Square and Electron Main; the catalog is bounded, account-scoped, and
private, no-storeat each public hop. -
One local account maps to one server-side Xiaozhi account binding. Agents and devices are resources beneath that account binding, not separate Xiaozhi users.
-
Robot/Canvas/module-selection routes must not initialize AI Programming projects or providers.
-
Makelore Code 的唯一 production runtime 是精确 pin 的 Pi
0.84.2;不得恢复 OpenCode fallback、双 runtime、兼容执行路径或 Renderer 直连本地 runtime。上游@earendil-works/pi-ai内名称含opencode的静态 Provider adapter 不属于产品旧 runtime。 -
Renderer 只消费共享的产品中立 project/Conversation/Snapshot/Patch DTO,并经
src/lib/host-api.ts或src/lib/api-client.ts访问 Main。Pi RPC、event、Provider credential 和本地 runtime 路径保持 Main-private。 -
accepted/uncertain Coding mutation 不得自动重放;RPC confirmation timeout 后仍保留 target run permit、process ownership 和 background lease,直到迟到 success/failure/exit/abort 权威收敛。其他 Conversation 必须继续可用。
-
Main 发出
lifecycle:sleep时 Coding 页面必须关闭旧事件流;编程视图挂载、项目上下文变化、页面重新可见或窗口 focus 时必须从 Main 静默刷新已选 Conversation 的权威 Snapshot。该只读收敛不得转化为 prompt/interaction 的自动重放。隐藏 Conversation 红点只代表新的 pending interaction 或新的 completed/failed/aborted terminal transition。 -
正式包中的 Agent Server 必须以显式 staged
pi-runtime的 manifest/root 解析 Pi 依赖,校验导入入口未逃逸对应包目录;不得依赖脚本相邻目录、应用node_modules或系统包解析作为 fallback。 -
selected Provider credential 只投影到目标父逻辑线程的内存 credential store 或目标 child 进程;跨账号模型变化必须重建目标逻辑线程。确定性 Works user-context 缺失是 Provider-auth failure:失效缓存 credential、fail fast、固定脱敏提示,不得归类为 Pi crash。
-
Works 下发的 per-model reasoning capability 是可选 Main-owned metadata,不是 Renderer 或 one-api 的权威。存在时只接受受支持的安全形状并覆盖目标模型的 本地 effort map;缺失时移除旧 override 并使用已验证本地 profile。
off在 Pi wire 上表示thinking.type=disabled且不发送reasoning_effort,启用档位保持 provider 原生值,当前 DeepSeek 产品投影为off/low/high/max。 -
Guided Hotspot Binding is implemented behind a Main-owned capability that is true by default; exact
NIANCODE_AI_HARDWARE_GUIDED_HOTSPOT_BINDING=0disables it, while capability-read failure falls back to direct six-digit Binding. The guided state is process-local, opener failures expose only the same fixed address for manual copy, and Binding conflicts refresh the safe account overview. -
Robot hotspot scanning and connection are local Main operations that return before Works credentials/upstream access. Renderer may submit only an opaque candidate ID from the latest bounded scan; Main alone filters open printable
Xiaozhi-*SSIDs, performs platform association, and verifies the exact current SSID. -
Hotspot discovery and connection do not authenticate a Robot. BSSID, interface/profile details, native diagnostics, location data, and Wi-Fi credentials never cross the Main boundary; permission or platform failure keeps the system-settings/manual path available.
-
The fixed portal action may open only
http://192.168.4.1/in the system browser and must not acquire cloud credentials or call Works Square. Renderer never supplies a portal URL and never handles Wi-Fi credentials. -
A successful Binding means account ownership was established; it is not evidence that the Robot is currently online or protocol-ready.
-
发布只有现有项目配置底部的一个入口,不新增发布工作台、侧栏或资源卡。
-
创建者发布唯一调用链是
ProjectPublishAction → publishWorksProjectSource → Main-owned release build → preflightStaticArtifact → source+built+artifact_contract 上传 → 状态轮询;客户端不再提供 Compose runner、deploy-check、watcher/arm/upload 协调或手工 ZIP 上传入口。 -
release builder 对 Main-owned 安全快照运行安装包内固定 npm 11.6.2 的
ci --ignore-scripts,并显式调用项目package-lock.json锁定的 Vite。不得使用全局 PATH、预存node_modules或 Renderer 提供的路径/origin。项目 Vite config/plugins 以桌面用户权限执行,该边界不是 sandbox。 -
preflightStaticArtifact以临时 HTTP loopback origin 提供最终built_archive的同一内存文件快照,并用 fresh 非持久、未挂载的 Electron WebContents/CDP 检查桌面/移动视口、错误、白屏及外域访问;不安装/调用 Playwright。 -
客户端预检是可绕过的 UX fail-fast:没有可信 receipt,也不复刻生产 opaque-origin。服务端不执行项目 Vite,而是独立重算和校验 source/built/contract 字节、固化不可变 Release;人工审核仍不可绕过。未来若要求 runtime 强门禁,需由可信 verifier 绑定精确构建产物。
-
ProjectType由创建请求写入项目配置,UI 与 Host API 不提供类型变更;缺少类型的旧配置归一为custom。 -
本地
projectType只选择产品路径和内部构建 preset,不是可信授权声明;Main 仍需安全打包,服务端仍需独立校验清单和包体。 -
云端确认上传成功后,本机 submission binding 失败只能产生固定、无路径的
binding_warning,不能把请求改判为失败;Renderer 仍继续轮询服务端校验与 Release 固化状态。 -
公共播放投影只有在上游
playable === true、版本名非空且 URL 通过同源 HTTPS、无 userinfo/loopback、长度、精确路径和无 query/fragment 校验时才可播放;不可信数据 fail closed。 -
Renderer 只能获得安全状态字段和安全投影的公共播放 URL,不得持有发布凭据、归档路径或自动部署状态。
-
落盘文件名
works-cloud-deploy.json仅为已安装客户端的数据兼容;领域模型和代码接口是 submission binding,不表示仍存在 cloud deployment coordinator。 -
AI Design 的一个 Workspace 公开一个当前 Direction、一个持久 Agent Session 和一个 Current Specification;conversation timeline 是交互历史,不是独立创建或选择的语义权威。
-
Living Form 与 chat、direct edit、decision、proposal、lock、Asset binding、restore 共用同一服务端 reducer。Renderer 草稿在 accepted 前不进入 canonical state。
-
AI Design Renderer 必须把自由描述与 Agent 的自然追问放在主交互面。Specification 投影只复述当前理解并提供默认收起的细节和可选手动调整;普通 Decision Prompt 不得自动渲染成要求青少年逐项完成的表单。
-
Main 通过
design.input.apply、design.quote.request和design.generation.confirm访问 V2。unknown transport result 必须复用原 command/operation identity;结构化业务错误不得重放,未知上游文本不得穿透安全投影。 -
Main-owned Canvas Workspace JSON 请求和 shared Works token refresh 的完整生命周期最多 30 秒,超时 abort transport 并以固定
504 DESIGN_WORKSPACE_REQUEST_TIMEOUT结束 Renderer 等待。Electronnet.fetch失败后的 Node fetch 透明回退只允许GET、HEAD、OPTIONS;PATCH/POST 等 mutation 只允许由持有显式幂等身份的上层协议决定重试,不能由底层 transport 隐式重放。该边界不改变上面的 WebSocket→REST 幂等 fallback。 -
Renderer 的异步与流式结果必须核对 Workspace、Direction、revision 和 operation identity;Direction snapshot 是 Specification 真值,Task/Asset 事件只更新 Workspace resource projection。
-
确认生成只提交不可变 Quote ID。Task 事务已提交但事件迟到时可刷新 Workspace projection;Task progress 不得改写 Living Form 或授权新的生成操作。
-
Updater feed 选择、原始错误日志、下载和安装生命周期只属于 Electron Main。Renderer 不得把缺失稳定 manifest 投影为“已是最新版”,也不得显示原始堆栈、URL、路径或错误码;并发检查共享同一错误事件时只发送一次错误状态,后续独立重试仍可重新报告。
-
图片与视频复用同一个单图来源选择器。图片 Brief 可从当前 Workspace 的已完成作品或本地上传中选择一张参考图继续生成;视频 Brief 使用同一入口绑定首帧。两条路径都必须通过现有 Workspace Asset 上传/选择契约提交一个真实
attachmentAssetIds,不得用本地路径或自然语言描述代替资产身份。 -
Canvas generation confirmation must use the immutable server Quote for the exact current Specification revision. The client confirms only the Quote identity and never edits or derives provider Prompt, model, dimensions, supplier pricing, or Token Point cost.
-
Canvas project deletion is an explicit destructive Workspace mutation guarded by exact project-name confirmation. Renderer clears the deleted Workspace's local state and selects the most recently updated remaining Workspace; upstream hiding, cancellation, reservation release, and settlement remain service-owned behavior.
-
图片/视频输入以 typed Asset binding 和 Current Specification medium 决定用途,不再从本地化 quick-reply 文案或 V1 Brief 推断行为。
Related Decisions
- 当前长期边界记录于 README、ADR-002 至 ADR-007(ADR-001 与 ADR-005 已 supersede)及各 Integration Gate;后续如改变唯一入口、凭据所有权、构建执行边界、Living Form/Specification 状态归属、Pi 单 runtime/worker/lease 边界、Marketplace/Web Search 分发边界、Robot 配网边界、重新引入 Learning 或重新引入客户端部署协调器,应新增 ADR。
Last Updated
2026-09-04