Reasonix Studio v2.10.0
Pre-release
Pre-release
·
559 commits
to main-v2
since this release
本版三条主线:交付证据的出处改由宿主掌握;远程连接失败可诊断、远端目录可直接选择;Studio 的 Windows 产物开始走 Authenticode 签名。另修复一处并行数据竞争,以及会话侧栏在窄屏下折叠后无法恢复的缺陷(#9507)。自 2.9.0 起 25 个提交。
新增
交付证据的出处由宿主掌握
关闭五处「被审计方可以回答审计门」的路径:
- here-doc 正文中的
go test ./...被当作已执行的项目检查。SplitOutsideHereDoc现丢弃正文,仅保留其旁边的命令。 - 含 here-doc 的命令此前无法分解,导致同批执行的测试被判为未执行,且
python - <<PY可绕过拒绝python -c的 Delivery 门。shell 判定改为复用 permission 已有的解析结果。 cd backend && go test ./...与根目录执行共用同一身份,一次通过的根测试会清除子目录的失败。规范化现保留 check 之前的上下文段,仅丢弃拼写与管道差异。- 未分类回执把管道退出码当作检查结果,
go test ./... | tail可掩盖其覆盖的失败。 missingMutation已接通但从未计数。无法证明的改动现记为债务,仅可由观察结清。
其余变更:
- 义务由账本差分导出,不可自行声明或抹除;差分随产生它的结果一并返回模型。
- Delivery 不再拒绝不透明解释器,改为记为「未证实并欠账」。
- 声明检查保留任务起始时的基线,当前声明无法回收。测试判据在任何可能覆盖它的调用前从前像捕获,并通过
go test -overlay对替换后的代码求值。
远程连接失败可诊断
internal/remote/bootstrap为每种安装失败定义 sentinel:npm 缺失、npm 不在登录 PATH、本地二进制平台不匹配、无可用安装路线、落地二进制无法执行、serve 未上报端口。desktop/next经统一映射表转为点分错误码。此前均为无错误码的英文句子(HostState.Err为 string,refusal-path 守卫仅覆盖internal/serve)。- 主机表单新增安装策略、跳板机、口令环境变量三项控件。三者此前已可存储并随保存传输,仅缺 UI。
- 新增
Probe:单次会话内读取首连所依赖的全部信息,不修改远端状态;不可用的安装路线返回与真实失败一致的错误码。reasonix remote test及窗口内每行主机的按钮均调用它。 - 两处基于错误文本匹配的测试改为按错误身份匹配。
远端目录直接选择(#9475)
attach.Pool.Browse仅持有链路:不安装 reasonix、不启动 serve、不挂转发,经文件协议列目录,在未部署内核的机器上可用。应答后连接按定时器释放,避免逐级进入时重复拨号(带口令私钥会重复索要口令)。GET /remotes/{host}/dirs仅返回目录,路径、名称与上级目录均由远端机器给出,不在本地推断路径语法。超出上限时截断并明确告知。- 选择后即打开,并将远端解析后的路径写入主机簿(
~在远端展开,记录输入值会导致同一目录重复列出)。已存在则跳过写入。 - 侧栏可移除本机记录的目录;远端 tree 上报而本机未记录的行不提供该操作。
- 设置页路径输入框接入同一选择器,条件为该行已保存。
运行带显示余额与计划
- 钱包余额改走独立路由,触发时机为面板挂载、回合结束、点击标签。此前搭载
GET /status(回合运行时每秒轮询 4 次)。四个数值分列展示;无balance_url的供应商返回 204 且不渲染;超出保鲜期的值标注时间;读取失败返回错误码而非 0。 internal/billing按端点主机选择解码器。修复 Moonshot 钱包:其响应可被 DeepSeek 解码器无错解析为空余额,导致有余额账号显示为不可用。无法匹配任何形状的响应现返回ErrUnreadable。Plan.tsx与panels/Overview.tsx无任何导入者。Plan 恢复挂载至设计位置(改动文件旁);Overview 及其专用的六条翻译删除。- 新增两道守卫:
route_parity校验internal/serve路由与vite.config.ts代理清单一致;orphan.test.ts使无导入者的.tsx失败。
Windows 产物 Authenticode 签名
- 分两阶段签名:先签散文件形态的
reasonix-studio.exe,再基于该字节重建安装包并签名容器,由 artifact configuration 校验载荷签名。仅签容器会使安装后落盘的可执行文件无签名。 studio-build.sh拆出--windows-payload与--windows-package;一次性平台路径由两者组合,未签名构建与本地构建的产物逐字节不变。.signpath/声明本线契约(分支studio、工作流release-studio.yml),cmd/signpath-contract在构建前验证并取指纹。分支名钉死为studio,不从被检查文件读取。- 签名需同时满足
SIGNPATH_API_TOKEN与STUDIO_SIGNING_ENABLED。前者为仓库级 secret,单独启用会使下一个 tag 请求到策略尚不信任的签名。 - 重写
scripts/verify-windows-authenticode.ps1:原脚本描述已退役的桌面线产物布局,且被从未为真的HAS_SIGNPATH挡住。现校验载荷可执行文件、安装器、以及便携 zip 内副本(按哈希与已签名载荷比对,防止打包自更早的已签名构建)。已在真实 Windows 主机验证三种情形。
修复
- 窄屏下折叠的会话侧栏无法恢复(#9507)。宽度 ≤1200px 时侧栏折叠,
[data-fold~="rail"] .gutter-l { display: none }同时隐藏其分隔条,而该分隔条上的把手是唯一入口(keys.ts无对应快捷键)。1920×1080 在 175% 缩放下为 1097 逻辑像素。该规则基于「左栏被整块移除」的错误前提:实际是.app[data-rail="off"]将其收窄至 0px,且已有专门针对收起态分隔条的定位样式。右栏为同类问题——展开为横跨一行时隐藏分隔条正确,收起时错误,规则现按状态区分。 - 并行工具调用竞写检查基线。每个调用结束时查询本回合债务,该查询内含一次惰性写入(首次查询时捕获基线)。并行工具在各自完成时同时到达该写入,
-race在checkContract报出读写竞争,两份基线可互相覆盖。捕获移至回合开始处(单线程执行),查询变为纯读取;这同时更符合其自身约束:基线应取自任何调用改写声明之前的前像。 - 同一检查换外壳被计为两项。验证身份保留检查之前的所有段,
cd /w && ls -la && go test ./...与cd /w && go test ./...成为两项且互不取代。身份现仅保留决定执行上下文的段(cd、export、变量赋值)。 - 闲置窗口的装饰动画持续占用 CPU(#9481)。
.glowring停止时仅 opacity 归零,内部 150px 径向渐变仍以 60fps 沿offset-path运行并在mask-composite: exclude层重新光栅化;offset-distance非合成器属性,开销全部落在主线程。400 回合会话、空闲窗口实测主线程 44.0% / 渲染进程 1.11 核,移除动画后为 11.4% / 1.02 核。改为默认animation-play-state: paused,仅在.pane[data-run="running"]下运行。空闲态 44.0% → 11.4%(4x 降频)、9.8% → 2.9%(不降频),运行态不变。 - 外部服务连接失败以整块红色呈现。改为仅状态点着色,原因行使用运行带次要行的统一字号字重,移除左侧内嵌竖线。
- shell 未路由
/balance。钱包拆分路由时调用加入了sse.ts但遗漏apiPaths,请求落到静态资源,运行带读回 404。路由 parity 测试已捕获,但位于根go test ./...不可见的嵌套模块中。make test现覆盖 shell 与 SDK。 - 基线求值为未变更判据重复构建。范围较大的改动会捕获全部测试文件,未重写任何文件的回合仍为每个文件付出一次构建。工作区仍逐字节持有的判据不再产生构建;首次实际执行的求值会声明进入检查阶段。
内部
- 能力端口拆分为六个。
Capabilities单接口包含 56 个方法(skills、hooks、MCP、网络、shell、权限、沙箱、配置修复、扩展 UI、供应商目录),使驱动端口失去隔离作用。按前端实际用法拆为SlashDispatch、Skills、Hooks、MCPControl、RuntimeSettings、Extensions;CapabilityScope移入Lifecycle。ACP 的EditorAPI原嵌入整个接口,现仅声明其驱动的三个端口,隔离守卫未用计数由 3 降至 0。无实现变更。 - 回合请求由方法名改为值。六个正交部分(输入、@-ref 行、显示文本、编辑前原文、resolver、输出格式)加 sync/guarded 开关,此前展开为 40 个入口方法,选择逻辑为两条 if 中对三个变量赋闭包。折叠后剩 27 个入口方法,端口公开形状不变。此过程发现
runEditedGoalLoopWithImageRefsRawDisplay为runTurnLoopWithPreparedTurn的副本,e4e6936b1 的修复只应用于其一,导致重新提交的编辑在未完成验证时仍显示「继续」卡片;由TestEditedResubmitFinishesWhatItOwes覆盖。turnLoopRunner编辑分支未绑定输出格式的不对称保留未动。 - 临时目录清理重试。Windows 上被删文件保留目录项直至最后一个句柄关闭,
t.TempDir单次删除会因「非空」失败;实测约 2% 的会话保存触发,均在 10ms 内。testenv.TempDir重试RemoveAll并记录未释放项。desktop 模块无法导入它,其 15 个文件保留t.TempDir。 - 词表守卫此前恒为红。中文是合法 JS 标识符,
en_storage.ts写作占用: "Space used",而perf/i18n.mjs仅匹配带引号写法,17 个键不可见、其中 6 个被误报为缺翻译。修复后读出 1276 个键,与Object.keys(EN).length一致。新增「无法解析的行」上报并计入退出码。 - acp 的 31 处等待改用
rpcCallBudget。该助手已存在,其注释已说明「两秒在整棵树同时被测时会失败」,但仅用于一个调用点。31 处均为「等不到即失败」的挂起探测,无一为负向断言。TestE2EDeleteActiveSessionDoesNotRecreateFiles曾因此在 Windows CI 失败。 - 新增
perf/fold.mjs:折叠的列必须仍可达——自身在屏,或其把手可点击。判定读结构(沿父链检查 display/visibility/opacity,再经elementFromPoint确认未被遮挡),左栏跟踪至点击后确认恢复。panels.mjs原断言shown(".gutter-l") === false,即断言了该缺陷本身,已改为断言不变量。 - 新增
perf/idle.mjs:运行中的动画其元素必须可见;动画在闲置窗口的净开销(同机关闭动画后相减)须在预算内。已接入selfcheck.mjs。 ask到用户的通路纳入测试(#9509)。该通路仅一条:EnableInteractiveApproval装在执行器上的 Asker。此前无任何断言覆盖,装配失效时每个提问都会得到无人应答的回退且无守卫报告。两个方向均覆盖:已接入审批的控制器必须递出问题并收回答案,未接入的必须返回回退且不得发出无人可答的提问。当前版本两项均通过,即该通路本身完好。- wire-parity 纳入
port/remote.ts:RemoteHostView、RemoteListing、RemoteFolder与桌面端手写副本声明为对。RemoteHostEdit有意排除——内核仍接受旧行的单数workspace,写入页面有意只发送列表。
macOS 已用 Developer ID 签名并公证,打开时不需要清除隔离属性。Windows 包未签名 —— Authenticode 签名绑定在受保护的 main-v2 上,本分支拿不到它,所以 SmartScreen 会告警:选「更多信息」,再选「仍要运行」。Linux 从 .deb 安装。
三个平台都能自更新:Linux 走自己的包,Windows 运行下一个安装器,macOS 替换自身 bundle。