dsh-codex-style-computer-use 1.2.3 → 1.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,22 +1,35 @@
1
- # dsh-codex-style-computer-use · Codex-style desktop control
1
+ # Codex-style Computer Use
2
2
 
3
- **Give DeepSeek eyes and hands for Windows.**
3
+ **Bring a Codex-style desktop workflow to DeepSeek Harness.**
4
4
 
5
- Ask your agent to work with desktop apps: see the screen, find controls, click and type. Take over with your own mouse or keyboard whenever needed; the agent waits before continuing. Approval prompts remain enabled by default.
5
+ Describe the goal. Your agent observes the screen, locates controls, clicks and types, then checks the result. Work with native Windows apps from the conversation.
6
6
 
7
- Windows desktop computer use for **DeepSeek Harness**: 18 desktop tools plus an Agent activation entry that observe and drive
8
- native Windows applications through prebuilt C# workers included in the package. No PowerShell 7,
9
- SDK or install-time builds are needed.
7
+ English | [中文](README.zh.md) · [Install](#install-and-update-in-dsh-market) · [Changelog](CHANGELOG.md)
10
8
 
11
- English | [中文](README.zh.md)
9
+ ![Codex-style Windows desktop control: observe, act, verify](docs/images/01-codex-style.png)
12
10
 
13
- Windows only (`os: win32`). Requires Node.js ≥ 22 and the .NET Framework 4.x that Windows ships with.
11
+ - **See the target. Take the action.** Combine screenshots, UI Automation and numbered targets with mouse, keyboard, drag, scroll and window tools.
12
+ - **Take over. Let the agent wait. Hand back and continue.** Version 1.3.0 adds a 1.5-second notice before input. Use your computer normally outside actual actuation; after handback, the agent re-observes and resumes the original task.
13
+ - **Fewer round trips. More efficient token use.** Incremental control observations, cropped or downsampled screenshots and batches of known actions reduce repeated context and model calls.
14
14
 
15
- **1.2.3 automatic fix:** normal installation/update now installs the approval-attribution correction for computer-use calls on affected DSH hosts. No manual host patch is required for those calls. Host approvals and audit remain authoritative; follow the host's restart indication after updating an already loaded plugin. See [1.2.3](docs/RELEASE-1.2.3.md).
15
+ ![Human handoff: prepare, take over, continue](docs/images/02-handoff.png)
16
16
 
17
- **1.2.1 attention fix:** fixes a missing crypto import that prevented 1.2.0's native `probe` and `raise` requests from reaching the helper. Updating from 1.2.0 is required for this runtime fix; reinstalling 1.2.0 does not fix it. New releases are staged on npm's `next` tag before promotion to `latest`; the market's normal update follows `latest`. See [1.2.1 validation and release status](docs/RELEASE-1.2.1.md).
17
+ ![Token efficiency: focused observations, batched actions and result readback](docs/images/03-token-efficiency.png)
18
18
 
19
- **1.2.2 GitHub pre-release:** includes a separately deployed DSH host approval-attribution patch and 14 regression cases. Plugin input and approval behavior is retained from 1.2.1. See [release contents and deployment scope](docs/RELEASE-1.2.2.md); GitHub publication does not update npm or the market automatically.
19
+ These are **1.3.0 feature illustrations**. Actual token use depends on the task, model and observation strategy. Approvals remain enabled by default; explicit pause, cancellation and exit remain authoritative.
20
+
21
+ **Ready to install.** 18 desktop tools, with native helpers included. No SDK or install-time compilation. Requires Windows, Node.js ≥ 22 and the .NET Framework 4.x included with Windows. An independent community plugin; Codex describes the interaction style.
22
+
23
+ <details>
24
+ <summary>Current release and compatibility</summary>
25
+
26
+ **1.3.1** is the current release on npm's `latest` channel: `dsh-codex-style-computer-use@1.3.1`. It adds worker-side OCR with per-word coordinates, change/caret-aware waits, UAC and lock-screen awareness with automatic continuation, and IME-safe clipboard text. Follow the host's restart indication when updating a loaded version. See [1.3.1](docs/RELEASE-1.3.1.md) and [GitHub Releases](https://github.com/ltmroberthk915/dsh-computer-use/releases).
27
+
28
+ Version 1.3.1 reads text from the screen by name, notices the Windows secure desktop and resumes on its own, and keeps every colour on the same DPI-derived edge rail with a visible breathing floor. Version 1.3.0 releases desktop control when work ends while the chat continues.
29
+
30
+ Earlier fixes: [1.2.3 approval attribution](docs/RELEASE-1.2.3.md) · [1.2.1 native attention](docs/RELEASE-1.2.1.md) · [standalone host patch](docs/RELEASE-1.2.2.md).
31
+
32
+ </details>
20
33
 
21
34
  ## What it does
22
35
 
@@ -37,9 +50,9 @@ under `$DSH_HOME/data/computer-use/`.
37
50
 
38
51
  ## Install and update in dsh-market
39
52
 
40
- Once the catalog submission is merged and synced, search **computer-use** and select **dsh-codex-style-computer-use**, by **ltmroberthk915** (npm maintainer: **ltmroberthk**). Click **Install**. Later, use **Update** or **Update all** for versions admitted by the host's release policy. The package includes both native helpers; no PowerShell 7 or build permission is needed.
53
+ Search **computer-use** or **Codex-style** in the market. Look for repository **ltmroberthk915/dsh-computer-use** and npm package **dsh-codex-style-computer-use** (maintainer: **ltmroberthk**), then click **Install**. Use **Update** or **Update all** for stable-channel updates. Both native helpers are included; no PowerShell 7 or build permission is needed.
41
54
 
42
- Before catalog sync, use **Settings → Plugins → Add plugin**. The corrected version is **`dsh-codex-style-computer-use@1.2.1`**; the unversioned name still resolves to 1.2.0 until promotion. Do not paste the GitHub repository URL: that selects the source-download path instead of the small prebuilt npm package. The default non-strict pnpm 11.7.0 configuration can install 1.2.1 immediately; an explicitly strict host policy can require waiting as described below. A newly added bundle can load live on the official Desktop host; check that its tools and skill appear. Restart from the tray when replacing an already loaded version, when the client remains stale, or when DSH reports **restart-required**.
55
+ Alternatively, enter **`dsh-codex-style-computer-use`** in **Settings → Plugins → Add plugin** for the current stable channel, or **`dsh-codex-style-computer-use@1.3.0`** for the version illustrated here. Enter the npm package spec directly. Your host may apply a waiting period to fresh versions; follow its indication. A newly added bundle can load live on supported hosts; check that its tools and skill appear. Restart from the tray when replacing a loaded version, when the client remains stale, or when DSH reports **restart-required**.
43
56
 
44
57
  ### Releases less than 24 hours old
45
58
 
@@ -137,7 +150,7 @@ fields are detected through UI Automation's `IsPassword` and refused by default.
137
150
 
138
151
  ## Safety model
139
152
 
140
- - **Shared input** — physical typing, scrolling, mouse movement and mouse buttons immediately yield control. Continued input or a held key/button for 2 seconds enters automatic waiting. After all keys/buttons are released and 3 seconds pass without physical input, the agent takes a fresh observation and continues the authorized task. A brief touch also waits for the 3-second quiet interval. A gentle pale-yellow edge gradient shows human ownership.
153
+ - **Shared input** — ordinary user activity is allowed while the agent is thinking, observing or preparing. During actual actuation, typing, scrolling and buttons yield immediately; pointer movement has a 16-pixel displacement tolerance. Continued input or a held key/button for 2 seconds enters automatic waiting. After release and 3 quiet seconds, the agent must inspect the current target and continue the original task, without blindly replaying partial writes. A gentle pale-yellow edge gradient shows human ownership.
141
154
  - **Manual pause** — only physical `Ctrl+Esc` raises a persistent input brake; `Ctrl+Alt+R` resumes. Ordinary Esc, typing, scrolling, pointer distance/frequency and the screen corner do not create this pause. Explicit question/diagnostic holds remain separate.
142
155
  - **Exit** — `Ctrl+Alt+Q` ends the session: the overlay goes away, its listeners are torn down, and
143
156
  further actuation is refused until a later turn opens a new one.
package/README.zh.md CHANGED
@@ -1,23 +1,35 @@
1
- # dsh-codex-style-computer-use · Codex 风格桌面操控
1
+ # Codex 风格 Computer Use
2
2
 
3
- **让 DeepSeek 看得见,也点得动。**
3
+ **更接近 Codex 的电脑操控体验,带到 DeepSeek Harness。**
4
4
 
5
- 把 Windows 应用里的重复操作交给 AI:看屏幕、找控件、点鼠标、敲键盘。你一碰鼠标键盘,它就让出控制,等你操作完再继续;默认保留操作审批。
5
+ 你描述目标,AI 看屏幕、找控件、点鼠标、敲键盘,再检查结果。让原生 Windows 应用里的工作,也能在对话中完成。
6
6
 
7
- 给 **DeepSeek Harness** 用的 Windows 桌面操控插件:18 个桌面工具加一个 Agent 激活入口,通过一个 C# worker
8
- 观察并驱动原生 Windows 应用。发布包已包含编译好的原生组件,无需安装 PowerShell 7、SDK 或执行编译命令。
7
+ [English](README.md) | 中文 · [安装](#在-dsh-market-安装和更新) · [版本记录](CHANGELOG.md)
9
8
 
10
- [English](README.md) | 中文
9
+ ![Codex 风格 Windows 桌面操控:观察、操作、验证](docs/images/01-codex-style.png)
11
10
 
12
- 仅支持 Windows(`os: win32`)。需要 Node.js ≥ 22 与 Windows 自带的 .NET Framework 4.x。
11
+ - **看得准,也点得动。** 截图、控件树与编号定位配合使用,支持点击、输入、拖拽、滚动和窗口操作。
12
+ - **你接手,AI 等待,再接着做。** 1.3.0 提供 1.5 秒操作预告;非实际操控期间正常使用电脑,交回后重新观察并接续原任务。
13
+ - **更少往返,更省 Token。** 控件增量观察、区域与降采样截图,加上连续动作批量执行,减少重复观察和模型往返。
13
14
 
14
- **1.2.3 自动修复:**正常安装或更新插件,即会为受影响宿主中的 computer-use 调用安装审批归因修正,无需手工修改宿主。审批决定与审计仍由宿主处理;更新已加载插件后按宿主提示重启。详见 [1.2.3](docs/RELEASE-1.2.3.md)。
15
+ ![人工接管与续接:先提醒、可接管、再继续](docs/images/02-handoff.png)
15
16
 
16
- **1.2.1 提醒修复:**补齐 crypto 导入,修复 1.2.0 原生 `probe` / `raise` 请求还未发送就抛错的问题。这次是运行时代码修复,需要从 1.2.0 更新;重复安装 1.2.0 无效。新版本先发布到 npm 的 `next`,再提升为 `latest`,市场普通更新跟随 `latest`。详见 [1.2.1 验证和发布状态](docs/RELEASE-1.2.1.md)。
17
+ ![Token 效率:聚焦观察、合并操作、回读验证](docs/images/03-token-efficiency.png)
17
18
 
18
- 宿主在禁用审批弹窗时仍提示“用户拒绝工具”的问题,详见 [DSH 审批归因补丁与回归测试](docs/APPROVAL-ATTRIBUTION.md)。
19
+ 上图为 **1.3.0 功能示意**。实际 Token 用量取决于任务、模型和观察方式。默认保留操作审批;明确暂停、取消和退出始终有效。
19
20
 
20
- **1.2.2 GitHub 预发布:**收录独立部署的宿主审批归因补丁和 14 项回归测试。插件输入与审批行为延续 1.2.1,详见 [发布内容及部署范围](docs/RELEASE-1.2.2.md)。GitHub 发布不会自动更新 npm 或市场版本。
21
+ **安装即用。** 18 个桌面工具,原生组件随包提供,无需 SDK 或安装时编译。支持 Windows、Node.js ≥ 22 和系统自带的 .NET Framework 4.x。独立社区插件;Codex 用于说明交互风格。
22
+
23
+ <details>
24
+ <summary>当前版本与兼容性</summary>
25
+
26
+ **1.3.1** 是 npm `latest` 频道的当前版本:`dsh-codex-style-computer-use@1.3.1`。新增 worker 侧 OCR(逐词坐标)、可定位变化与识别光标闪烁的等待、UAC/锁屏感知与自动续接、以及绕过 IME 的剪贴板文本通道。更新已加载的旧版本后,按宿主提示重启。详见 [1.3.1](docs/RELEASE-1.3.1.md) 与 [GitHub Releases](https://github.com/ltmroberthk915/dsh-computer-use/releases)。
27
+
28
+ 1.3.1 可直接从屏幕读字定位控件,察觉 Windows 安全桌面并在其结束后自动续接;所有颜色共用同一条按 DPI 换算的边缘光环,呼吸谷值保持可见。1.3.0 起工具用完可主动释放,聊天继续;正常收尾自动退出。
29
+
30
+ 历史兼容修复:[1.2.3 审批归因](docs/RELEASE-1.2.3.md) · [1.2.1 原生提醒](docs/RELEASE-1.2.1.md) · [独立宿主补丁](docs/RELEASE-1.2.2.md)。
31
+
32
+ </details>
21
33
 
22
34
  ## 它能做什么
23
35
 
@@ -35,9 +47,9 @@
35
47
 
36
48
  ## 在 dsh-market 安装和更新
37
49
 
38
- 市场收录同步后,搜索 **computer-use**,选择 **dsh-codex-style-computer-use**,作者 **ltmroberthk915**(npm 维护者 **ltmroberthk**),点击**安装**。以后通过市场的**更新**或**全部更新**安装符合宿主发布策略的版本。两份原生组件都已随包提供,无需 PowerShell 7、SDK 或构建白名单。
50
+ 在市场搜索 **computer-use** 或 **Codex-style**,认准仓库 **ltmroberthk915/dsh-computer-use**、npm 包 **dsh-codex-style-computer-use**(维护者 **ltmroberthk**),点击**安装**。以后通过市场的**更新**或**全部更新**获取正式频道版本。两份原生组件都已随包提供,无需 PowerShell 7、SDK 或构建白名单。
39
51
 
40
- 目录尚未同步时,在 **设置 → 插件 → 添加插件** 输入修复版 **`dsh-codex-style-computer-use@1.2.1`**。正式标签提升前,省略版本号仍会装到 1.2.0。这里填 npm 包名即可;填写 GitHub 仓库网址会转为下载源码,容易受 GitHub 下载线路影响。默认非严格 pnpm 11.7.0 配置可以直接安装 1.2.1;宿主显式启用严格策略时,才可能需要等待冷却。首次新增 bundle 在官方桌面端可热加载;确认工具与 skill 已出现即可使用。替换已经加载的版本、客户端界面未刷新或界面明确提示 **restart-required / 需要重启** 时,再从托盘完整退出 DSH 并重新打开。
52
+ 也可在 **设置 → 插件 → 添加插件** 输入 **`dsh-codex-style-computer-use`**,安装当前正式频道;要体验本页展示的 1.3.0,输入 **`dsh-codex-style-computer-use@1.3.0`**。这里填 npm 包名即可。宿主可能对新版本设置等待期,以界面提示为准。首次新增 bundle 可在支持的宿主中热加载;确认工具与 skill 已出现即可使用。替换已经加载的版本、客户端界面未刷新或界面提示 **restart-required / 需要重启** 时,从托盘完整退出 DSH 并重新打开。
41
53
 
42
54
  ### 发布未满 24 小时
43
55
 
@@ -131,7 +143,9 @@ ID**:派发输入前会核对窗口身份与采样像素,因此过期的 mar
131
143
 
132
144
  ## 安全模型
133
145
 
134
- - **人机共用输入** —— 实体键盘、滚轮、鼠标移动或按钮操作立即让出控制。持续输入或按住键/按钮 2 秒进入自动等待;全部松开并静默 3 秒后,重新观察目标并继续已授权任务。短暂触碰也等待 3 秒静默。人操作时显示温和的淡黄色边缘渐变。
146
+ - **人机共用输入** —— 思考、观察和预告期间允许用户正常操作。实际操控时,键盘、滚轮和按钮立即触发让出;鼠标位移有 16 像素容差。持续输入或按住键/按钮 2 秒进入自动等待;全部松开并静默 3 秒后,agent 必须重新观察并接续原任务,不盲目重放部分写入。人操作时显示温和的淡黄色边缘渐变。
147
+ - **工具用完即释放** —— `computer_ctrl {action:"release"}` 结束电脑控制但保持聊天继续;正常收尾自动释放,不弹确认选项单。暂停和待回答问题不会被自动清除。
148
+ - **一个操作者** —— 会话/agent 所有权与跨 worker 独占锁覆盖整个控制周期,另一 agent 必须等当前操作者释放。
135
149
  - **人工暂停** —— 只有实体 `Ctrl+Esc` 触发持续输入刹车,`Ctrl+Alt+R` 恢复。普通 Esc、打字、滚动、鼠标距离/频率和屏幕左上角不再触发这种暂停;显式提问、诊断暂停保持独立。
136
150
  - **退出** —— `Ctrl+Alt+Q` 结束会话:覆盖层消失、监听全部拆除,后续注入被拒,直到之后某一轮重新开启。
137
151
  - **刹车是关于机器的事实,不属于某一个进程** —— 闩锁状态落盘,每个 worker 都会遵守,包括之后从命令行启动的。
package/icon.svg ADDED
@@ -0,0 +1,29 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="32" height="32" viewBox="0 0 32 32" fill="none">
2
+ <defs>
3
+ <linearGradient id="tile" x1="4" y1="0" x2="28" y2="32" gradientUnits="userSpaceOnUse">
4
+ <stop stop-color="#17243F"/>
5
+ <stop offset="1" stop-color="#05080F"/>
6
+ </linearGradient>
7
+ <radialGradient id="halo" cx="11" cy="27" r="20" gradientUnits="userSpaceOnUse">
8
+ <stop stop-color="#8B5CF6" stop-opacity=".2"/>
9
+ <stop offset="1" stop-color="#8B5CF6" stop-opacity="0"/>
10
+ </radialGradient>
11
+ <linearGradient id="rail" x1="5" y1="6" x2="27" y2="24" gradientUnits="userSpaceOnUse">
12
+ <stop stop-color="#5EEAD4"/>
13
+ <stop offset=".5" stop-color="#38BDF8"/>
14
+ <stop offset="1" stop-color="#A78BFA"/>
15
+ </linearGradient>
16
+ <radialGradient id="glow" cx="18.2" cy="19.4" r="7.6" gradientUnits="userSpaceOnUse">
17
+ <stop stop-color="#38BDF8" stop-opacity=".32"/>
18
+ <stop offset="1" stop-color="#38BDF8" stop-opacity="0"/>
19
+ </radialGradient>
20
+ </defs>
21
+ <rect width="32" height="32" rx="7.5" fill="url(#tile)"/>
22
+ <rect width="32" height="32" rx="7.5" fill="url(#halo)"/>
23
+ <rect x="5.6" y="5.9" width="20.8" height="16" rx="3" fill="#FFFFFF" fill-opacity=".06" stroke="url(#rail)" stroke-width="1.9"/>
24
+ <path d="M5.6 10.1 H26.4" stroke="url(#rail)" stroke-width="1.05" stroke-opacity=".5"/>
25
+ <circle cx="8.5" cy="8" r=".9" fill="#5EEAD4"/>
26
+ <circle cx="11.2" cy="8" r=".9" fill="#A78BFA" fill-opacity=".85"/>
27
+ <circle cx="18.2" cy="19.4" r="7.6" fill="url(#glow)"/>
28
+ <path d="M15.6 12.4 L15.6 21.2 L17.8 19 L19.3 22.4 L20.8 21.7 L19.3 18.5 L22.3 18.5 Z" fill="#F8FAFC" stroke="#070B14" stroke-width=".85" stroke-linejoin="round"/>
29
+ </svg>
package/lib/batch.js CHANGED
@@ -1,4 +1,5 @@
1
1
  // Serial execution and observation selection; no desktop or lifecycle side effects here.
2
+ import { handoffResult } from './continuation.js'
2
3
  const reads = new Set(['computer_state', 'computer_uia', 'computer_marks', 'computer_shot', 'computer_wait'])
3
4
  const isRead = (step) => reads.has(step?.tool) || (step?.tool === 'computer_clip' && step.args?.text === undefined)
4
5
  const isReadback = (step) => ['computer_state', 'computer_uia', 'computer_marks', 'computer_shot'].includes(step.tool) ||
@@ -10,37 +11,52 @@ export function actionRefusal (step, result) {
10
11
  return 'target window activation was not confirmed; subsequent actions were not dispatched'
11
12
  }
12
13
  if (step.tool === 'computer_ctrl' && step.args?.action === 'recover' && result?.recovered !== true) return result.reason || 'temporary pause recovery refused'
14
+ if (step.tool === 'computer_ctrl' && step.args?.action === 'release' && !result?.released && !result?.alreadyReleased) return result.reason || 'cycle release refused'
13
15
  return null
14
16
  }
15
17
 
16
- export async function runBatch ({ steps, handlers, signal, stopped, screenshot, shot = 'auto', exec }) {
18
+ export async function runBatch ({ steps, handlers, signal, stopped, screenshot, shot = 'auto', exec, assertOwnership }) {
17
19
  if (!Array.isArray(steps) || !['auto', 'always', 'never'].includes(shot)) throw new Error('invalid batch actions or shot mode')
18
20
  const actions = []
19
21
  let failed = false
22
+ let continuation = null
20
23
  for (const step of steps) {
21
24
  const name = step?.tool
22
25
  if (failed || signal?.aborted) {
23
- actions.push({ tool: name || '', ok: false, outcome: 'not-dispatched', error: signal?.aborted ? 'cancelled' : 'earlier action failed' })
26
+ actions.push({ tool: name || '', ok: false, outcome: 'not-dispatched',
27
+ ...(continuation && !signal?.aborted
28
+ ? { status: 'deferred', message: 'Resume this unfinished step after fresh target evidence; the original task must continue.' }
29
+ : { error: signal?.aborted ? 'cancelled' : 'earlier action failed' }) })
24
30
  failed = true
25
31
  continue
26
32
  }
27
33
  const fn = Object.hasOwn(handlers, name) && handlers[name]
28
34
  if (!fn) { actions.push({ tool: name || '', ok: false, outcome: 'not-dispatched', error: 'unknown tool' }); failed = true; continue }
29
35
  try {
36
+ assertOwnership?.()
30
37
  const stoppedBefore = stopped()
31
38
  const result = await fn(step.args || {}, exec)
32
39
  const refusal = actionRefusal(step, result)
33
40
  actions.push({ tool: name, ok: !refusal, result, ...(refusal ? { error: refusal } : {}) })
34
41
  failed = !!refusal || (!stoppedBefore && stopped()) ||
35
- (name === 'computer_ctrl' && ['stop', 'exit'].includes(step.args?.action))
42
+ (name === 'computer_ctrl' && ['stop', 'exit', 'release'].includes(step.args?.action))
36
43
  } catch (error) {
37
- actions.push({ tool: name, ok: false, error: String(error.message || error),
38
- code: error.code || 'action-error', outcome: error.outcome || 'unknown' })
44
+ const checkpoint = !signal?.aborted && !stopped() ? handoffResult(error) : null
45
+ if (checkpoint) {
46
+ continuation = { ...checkpoint.continuation, resumeFromActionIndex: actions.length }
47
+ actions.push({ tool: name, ...checkpoint, continuation })
48
+ } else {
49
+ actions.push({ tool: name, ok: false, error: String(error.message || error),
50
+ code: error.code || 'action-error', outcome: error.outcome || 'unknown' })
51
+ }
39
52
  failed = true
40
53
  }
41
54
  }
42
55
  const needsShot = shot === 'always' || (shot === 'auto' && steps.some(s => !isRead(s)) && !isReadback(steps.at(-1) || {}))
43
56
  const result = { actions, attachedShot: null }
57
+ if (continuation) Object.assign(result, {
58
+ status: 'continuation-required', taskStatus: 'continuing', transient: true, continuation,
59
+ })
44
60
  if (!failed && !signal?.aborted && !stopped() && needsShot) {
45
61
  try { result.attachedShot = await screenshot() }
46
62
  catch (error) { result.observationError = String(error.message || error) }
Binary file
@@ -3,5 +3,5 @@
3
3
  "platform": "win32",
4
4
  "architecture": "x64",
5
5
  "sourceSha256": "6e17308fc1cb0de1ece6f3164866b6de03ecdf74a42a6e78c0a8e6d02912c3bf",
6
- "binarySha256": "c15feb47d7ec975ccab12fea2ee4300ea0a4699069be21d0fb9d1fedebe26158"
6
+ "binarySha256": "f39e79148d0f1c8fa527f55607eb4e7440e82c3ab5b33162bde773528418fe5a"
7
7
  }
@@ -0,0 +1,14 @@
1
+ // Temporary ownership handoff is a task checkpoint, not a failed/cancelled task.
2
+ export function handoffResult (error) {
3
+ if (error?.code !== 'HUMAN_REOBSERVE' || !error.continuation?.required) return null
4
+ return {
5
+ ok: false,
6
+ status: 'continuation-required',
7
+ taskStatus: 'continuing',
8
+ transient: true,
9
+ code: error.code,
10
+ outcome: error.outcome || 'unknown',
11
+ message: error.message,
12
+ continuation: { ...error.continuation },
13
+ }
14
+ }
@@ -2,6 +2,6 @@
2
2
  "format": 1,
3
3
  "platform": "win32",
4
4
  "architecture": "x64",
5
- "sourceSha256": "7e24c3fa73fed54eb8209efc253753d44664037954d936573e7c80150caf5856",
6
- "binarySha256": "ee890a28d1aec984f98b48caf30acab536477ea4d9261892761ea6e8bd485c46"
5
+ "sourceSha256": "8427a18e1f161959043f638cab821e701714f3d83138911dc9c4fb2cbeb152bf",
6
+ "binarySha256": "0e9212f628ebd73655de1235b3e7bb4ce176c4b60da16c336f2ebae7397084a2"
7
7
  }
@@ -47,7 +47,11 @@ $refs = @(
47
47
  '/r:System.Web.Extensions.dll', '/r:System.Windows.Forms.dll',
48
48
  "/r:$gac\UIAutomationClient\v4.0_4.0.0.0__31bf3856ad364e35\UIAutomationClient.dll",
49
49
  "/r:$gac\UIAutomationTypes\v4.0_4.0.0.0__31bf3856ad364e35\UIAutomationTypes.dll",
50
- "/r:$gac\WindowsBase\v4.0_4.0.0.0__31bf3856ad364e35\WindowsBase.dll"
50
+ "/r:$gac\WindowsBase\v4.0_4.0.0.0__31bf3856ad364e35\WindowsBase.dll",
51
+ # Inbox OCR (2026-11-04): union winmd ships in the package next to this script.
52
+ "/r:$env:windir\Microsoft.NET\Framework64\v4.0.30319\System.Runtime.dll",
53
+ "/r:$gac\System.Runtime.WindowsRuntime\v4.0_4.0.0.0__b77a5c561934e089\System.Runtime.WindowsRuntime.dll",
54
+ "/r:$PSScriptRoot\winmd\Windows.winmd"
51
55
  )
52
56
 
53
57
  New-Item -ItemType Directory -Path $outDir -Force | Out-Null