@sema-agent/client-core 0.23.0 → 0.24.0
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 +2 -2
- package/dist/adapt/arms.d.ts +4 -4
- package/dist/adapt/arms.js +6 -6
- package/dist/adapt/toolCards.d.ts +2 -2
- package/dist/adapt/turnFlags.d.ts +2 -2
- package/dist/adapt.js +2 -2
- package/dist/adapter/downstream/eventToSdkMessage.d.ts +1 -1
- package/dist/adapter/downstream/eventToSdkMessage.js +5 -5
- package/dist/adapter/downstream/terminalToSdkResult.js +1 -1
- package/dist/adapter/runStream.js +1 -1
- package/dist/adapter/types.d.ts +1 -1
- package/dist/agentSession/backgroundView.d.ts +2 -2
- package/dist/agentsWireCaps.d.ts +2 -2
- package/dist/agentsWireCaps.js +2 -2
- package/dist/attachmentsWireCaps.d.ts +2 -2
- package/dist/attachmentsWireCaps.js +3 -3
- package/dist/classifierVerdictWire.d.ts +1 -1
- package/dist/classifierVerdictWire.js +1 -1
- package/dist/detachWire.d.ts +3 -1
- package/dist/engineWireSdk.d.ts +4 -3
- package/dist/engineWireSdk.js +3 -2
- package/dist/engineWireTarget.d.ts +2 -1
- package/dist/engineWireTarget.js +4 -3
- package/dist/goalStopHook.d.ts +1 -1
- package/dist/goalStopHook.js +1 -1
- package/dist/headlessPermissionModeWire.d.ts +1 -1
- package/dist/headlessPermissionModeWire.js +1 -1
- package/dist/headlessReconnectWire.d.ts +1 -1
- package/dist/headlessReconnectWire.js +1 -1
- package/dist/hitl/approvalsFeed.d.ts +1 -1
- package/dist/hitl/frameRouter.js +1 -1
- package/dist/hitl/gateLedger.d.ts +1 -1
- package/dist/hitl/hitlHostSurface.d.ts +1 -1
- package/dist/hitl/hitlHostSurface.js +1 -1
- package/dist/hitl/toolApprovalWire.d.ts +1 -1
- package/dist/hitl/toolApprovalWire.js +4 -4
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/interactiveToolsWire.d.ts +1 -1
- package/dist/interactiveToolsWire.js +1 -1
- package/dist/limitsWire.d.ts +1 -1
- package/dist/limitsWire.js +1 -1
- package/dist/liveInitToolFace.d.ts +1 -1
- package/dist/liveInitToolFace.js +1 -1
- package/dist/notifications.d.ts +2 -2
- package/dist/notifications.js +2 -2
- package/dist/permissionWireCaps.d.ts +1 -1
- package/dist/permissionWireCaps.js +1 -1
- package/dist/retryStatus.d.ts +2 -2
- package/dist/seam.d.ts +2 -2
- package/dist/skillsWireCaps.d.ts +1 -1
- package/dist/subagent/engineRowStopGate.d.ts +1 -1
- package/dist/subagent/engineRowStopGate.js +1 -1
- package/dist/subagent/engineTaskHandleWire.js +1 -1
- package/dist/toolResult.d.ts +3 -3
- package/dist/toolResult.js +1 -1
- package/dist/workflow.d.ts +2 -2
- package/dist/workflow.js +2 -2
- package/package.json +3 -3
package/README.md
CHANGED
|
@@ -23,7 +23,7 @@ Renamed from **`@sema-agent/wire-cc-adapter`** (0.1.x, deprecated — see *Migra
|
|
|
23
23
|
|
|
24
24
|
## Scope
|
|
25
25
|
|
|
26
|
-
**Version:** 0.
|
|
26
|
+
**Version:** 0.24.0
|
|
27
27
|
|
|
28
28
|
- **Today** — the adapter seam, the whole `adapt()` pipeline (all 14 A-layer arms plus the
|
|
29
29
|
B/D/E tool-card layers), the notification/caps/model families, the adapter kernel (stream driver
|
|
@@ -53,7 +53,7 @@ Renamed from **`@sema-agent/wire-cc-adapter`** (0.1.x, deprecated — see *Migra
|
|
|
53
53
|
`SseIdleError`, `probeHealth`, `APIError` and `TaskStopConflictError` are imported as values in
|
|
54
54
|
five modules, and the browser bundle really bundles the SDK through (the portability guard would
|
|
55
55
|
exit 3 rather than quietly mark it external).
|
|
56
|
-
- The declared floor is `>=6.
|
|
56
|
+
- The declared floor is `>=6.11.0`, and it is *witnessed*: the guard checks that an actually
|
|
57
57
|
installed SDK at that line still exports every value-level symbol this package imports and still
|
|
58
58
|
declares `TaskStats.costMicroUsd` (the key `costOrNull` reads). A floor nobody ever ran is a
|
|
59
59
|
promise, not a contract.
|
package/dist/adapt/arms.d.ts
CHANGED
|
@@ -5,15 +5,15 @@
|
|
|
5
5
|
* · 每条臂是一个具名 generator,`break` 变 `return`(语义逐条对位,`default:` 空臂 = 表里查不到);
|
|
6
6
|
* · 臂拿不到驱动壳的局部变量 —— 它要什么状态,必须写在自己的 deps 类型里。
|
|
7
7
|
*
|
|
8
|
-
* 🔴 表用 `Map` 而不是普通对象(
|
|
8
|
+
* 🔴 表用 `Map` 而不是普通对象(复审结论 3):对象表被 `{type:'__proto__'}` /
|
|
9
9
|
* `{type:'toString'}` 这种帧一命中就是原型污染(wire 帧是 UNTRUSTED 的开集)。
|
|
10
10
|
*
|
|
11
11
|
* 🔴 **两级 deps 是判别力本身,不是洁癖**(矩阵 §3.5):
|
|
12
12
|
* `ProjectionArmFn` 只吃 `{ctx, idOf}` —— 于是「这几条臂碰不到任何适配器状态」这件事从
|
|
13
13
|
* 注释里的断言变成**编译期事实**。全量注入(一个大 deps 喂所有臂)会让封闭性声明失去判别力,
|
|
14
|
-
* 那正是 A 族
|
|
14
|
+
* 那正是 A 族 对抗复审里 5/11 那次翻车的根因。
|
|
15
15
|
*
|
|
16
|
-
* 🔴 **7 组由输入帧顺序耦合的臂对**(
|
|
16
|
+
* 🔴 **7 组由输入帧顺序耦合的臂对**(复审结论 3 的清单;源码级无顺序耦合 —— 每帧单键分发 +
|
|
17
17
|
* return,但**帧到达顺序**会改判别结果)。逐条点名在下面各臂的注释里,标记 `⟨帧序耦合 N/7⟩`:
|
|
18
18
|
* 1. assistant(开卡)→ task_progress(FIFO 猜父只认**已开**的卡)
|
|
19
19
|
* 2. assistant(Workflow 卡)→ task_progress(判据③ 认 seenWorkflowToolCallIds)
|
|
@@ -62,6 +62,6 @@ export type ProjectionArmFn = (m: Frame, deps: ProjectionArmDeps) => Generator<A
|
|
|
62
62
|
export type ArmFn = (m: Frame, deps: ArmDeps) => Generator<AdapterOutput>;
|
|
63
63
|
/**
|
|
64
64
|
* 帧类型 → 臂。**Map 而不是对象字面量**:`{type:'__proto__'}` 这种 UNTRUSTED 帧命中对象表
|
|
65
|
-
* 就是原型污染(
|
|
65
|
+
* 就是原型污染(复审结论 3)。表里查不到 = 拆分前 `switch` 的 `default:` 空臂,行为同。
|
|
66
66
|
*/
|
|
67
67
|
export declare const ARMS: ReadonlyMap<string, ArmFn>;
|
package/dist/adapt/arms.js
CHANGED
|
@@ -16,7 +16,7 @@ const assistantArm = function* (m, { ctx, idOf, text, cards, inst }) {
|
|
|
16
16
|
const toolUseIdx = blocks.findIndex(b => b?.type === 'tool_use');
|
|
17
17
|
// 拆分同批消掉一处 `!` 非空断言(规范禁用):`findIndex >= 0` 与「取到的不是 undefined」
|
|
18
18
|
// 本来就是同一件事(判别式 `b?.type === 'tool_use'` 对 undefined 恒假),写成显式取值即可。
|
|
19
|
-
// 收货裁定(
|
|
19
|
+
// 收货裁定(对抗复审 #4):旧版此处直接取值使用,畸形帧(accessor/稀疏形,非 JSON 数据帧)
|
|
20
20
|
// 会抛 TypeError;guard 保留=有意的健壮性变化 —— 正常 wire 帧(JSON.parse 产物)下
|
|
21
21
|
// `findIndex >= 0 ⇒ 恒非 undefined`,零行为差。
|
|
22
22
|
//
|
|
@@ -213,7 +213,7 @@ const workspaceChangedArm = function* (m, { idOf }) {
|
|
|
213
213
|
});
|
|
214
214
|
};
|
|
215
215
|
/**
|
|
216
|
-
* FIX⑦(2026-08-07
|
|
216
|
+
* FIX⑦(2026-08-07,[3017]/[3020])—— `human_input` 生命周期账本帧。
|
|
217
217
|
*
|
|
218
218
|
* 姿势抄同族的 `steering_injected` / `workspace_changed`(都是「引擎侧发生了一件事,壳记一笔」的
|
|
219
219
|
* 非持久帧,归 chrome),但**不走 `attachment` 臂**:那三条 attachment 是要在转录流里渲出一行给
|
|
@@ -249,7 +249,7 @@ const humanInputArm = function* (m) {
|
|
|
249
249
|
...(str(m.issuer) !== undefined ? { issuer: str(m.issuer) } : {}),
|
|
250
250
|
...(actor !== undefined && Object.keys(actor).length > 0 ? { actor } : {}),
|
|
251
251
|
...(str(m.entryId) !== undefined ? { entryId: str(m.entryId) } : {}),
|
|
252
|
-
// 宿主幂等落账的键(
|
|
252
|
+
// 宿主幂等落账的键(对抗复审二轮):重放同一条账本帧必须得到同一个 eventId。
|
|
253
253
|
...(str(m.eventId) !== undefined ? { eventId: str(m.eventId) } : {}),
|
|
254
254
|
});
|
|
255
255
|
};
|
|
@@ -343,7 +343,7 @@ const taskProgressArm = function* (m, { ctx, cards, panel, inst }) {
|
|
|
343
343
|
// 都在 footer 铸一条幽灵 local_agent 行,还能骑错 run_workflow 卡的 inline stats)。
|
|
344
344
|
// 判据三级:① 帧带 workflowRunId(一手证据)② wa+16hex 形 id(core BCE 合成 id)
|
|
345
345
|
// ③ 显式父指向本会话见过的 Workflow 工具卡(实例台账,覆盖 uuid 形子代 id + 跨 turn 迟到 tick)。
|
|
346
|
-
// 🔴
|
|
346
|
+
// 🔴 复审独立发现的拆分风险:**本门必须先于任何 panel 写**,否则重造 workflow 幽灵前台行 ——
|
|
347
347
|
// 这也是它在本臂第一段、`bind()` 之前的原因,别按「先绑定再分类」重排。
|
|
348
348
|
const workflowRunId = typeof m.workflowRunId === 'string' ? m.workflowRunId : undefined;
|
|
349
349
|
if (workflowRunId !== undefined ||
|
|
@@ -659,7 +659,7 @@ const retryStatusArm = function* (m, { ctx, flags }) {
|
|
|
659
659
|
// (TurnFlags 的「主 lane 内容帧到达即清」)可能已经清过了:已安装 core 在内容流跑完的 finally
|
|
660
660
|
// 里发 `recovered`,所以 `retrying → 内容 → recovered` 才是常态顺序。故用 `takeRetryOverlay()`
|
|
661
661
|
// 的**原子读落**决定要不要发:旗还在 ⇒ 发这一发并落旗;旗已落 ⇒ 沉默(没有覆盖层可摘)。
|
|
662
|
-
// 首版写成「无条件发 + clearRetryOverlay」,在常态顺序上双清(
|
|
662
|
+
// 首版写成「无条件发 + clearRetryOverlay」,在常态顺序上双清(对抗复审命中)。
|
|
663
663
|
if (status === null) {
|
|
664
664
|
if (flags.takeRetryOverlay())
|
|
665
665
|
yield chrome({ kind: 'retry_status', laneProof: MAIN, status: null });
|
|
@@ -671,7 +671,7 @@ const retryStatusArm = function* (m, { ctx, flags }) {
|
|
|
671
671
|
};
|
|
672
672
|
/**
|
|
673
673
|
* 帧类型 → 臂。**Map 而不是对象字面量**:`{type:'__proto__'}` 这种 UNTRUSTED 帧命中对象表
|
|
674
|
-
* 就是原型污染(
|
|
674
|
+
* 就是原型污染(复审结论 3)。表里查不到 = 拆分前 `switch` 的 `default:` 空臂,行为同。
|
|
675
675
|
*/
|
|
676
676
|
export const ARMS = new Map([
|
|
677
677
|
['assistant', assistantArm],
|
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
* (TodoWrite 划删线 diff 的 oldTodos)三行状态 + C4 mintResponseId / C10 buildToolResult /
|
|
6
6
|
* C11 sweepOpenCards 三个闭包 + `PendingToolUse` 形本身。
|
|
7
7
|
*
|
|
8
|
-
* 🔴 拆分硬约束(SPLIT-03
|
|
8
|
+
* 🔴 拆分硬约束(SPLIT-03,复审结论 2 采纳形):**S1 复位在 `close()` 内部、第一个 `yield`
|
|
9
9
|
* 之前**。理由是生成器语义 —— yield 之后的语句只有消费者再要下一个值时才跑,消费者早退
|
|
10
10
|
* (`it.return()` / break)时永不执行。把复位留在调用方,调用方就还能写出「yield 后复位」的形;
|
|
11
11
|
* 收进被调方之后,这条时序由**一处**保证。原 `tool_end_result` 臂 :1054-1056(delete → 复位 →
|
|
@@ -16,7 +16,7 @@
|
|
|
16
16
|
* turn 级,两行之后紧跟 `break`,早退时生成器已死、再无读者 ⇒ 零可观测后果),所以前移是
|
|
17
17
|
* **纯一致性改动、零行为差**。反钉见矩阵 §2.2:前移不影响 mint —— 影响窗口只有
|
|
18
18
|
* 「复位语句与原复位点(yield 之后)」之间那几行,窗口内无 mint 点;三条支随即退出本臂,
|
|
19
|
-
* 后续帧的 mint 走各自臂的常规路径,与拆分前同(
|
|
19
|
+
* 后续帧的 mint 走各自臂的常规路径,与拆分前同(对抗复审校准:break 退出的是臂不是 turn)。
|
|
20
20
|
*
|
|
21
21
|
* 🔴 `pending` 是唯一跨 M2→M3 的数据面(矩阵 §1.2 注):面板族只读两个字段(`name` 判
|
|
22
22
|
* SUBAGENT_TOOL_NAMES / `rawInput` T50 双形读)。所以对外给的是 `OpenCardView` **只读视图**,
|
|
@@ -29,7 +29,7 @@ export interface TurnFlags {
|
|
|
29
29
|
emitTurnUsageEnd(outputTokens: number): Generator<AdapterOutput>;
|
|
30
30
|
/** A7 `result`:只有还没发过 end 且这帧真带了 outputTokens 时才补发(`!endEmitted` 门)。 */
|
|
31
31
|
/** `readOutputTokens` 惰性:只在真的要发 end 度量时才读 usage(与拆分前「`!endEmitted`
|
|
32
|
-
* 门内才读 `m.usage`」逐字同语义 ——
|
|
32
|
+
* 门内才读 `m.usage`」逐字同语义 —— 对抗复审 #3 收货修)。 */
|
|
33
33
|
emitResultEndIfNeeded(readOutputTokens: () => number | undefined): Generator<AdapterOutput>;
|
|
34
34
|
/** A15 `retry_status`:挂旗(下一帧主 lane 内容到达即清)。 */
|
|
35
35
|
noteRetryOverlay(): void;
|
|
@@ -37,7 +37,7 @@ export interface TurnFlags {
|
|
|
37
37
|
* A15 `retry_status` 的反向动作(#3004 跟修批 2026-08-08):**引擎直报恢复**(`recovered` 相)那一拍
|
|
38
38
|
* 调它 —— 返回「本次是否**仍需**发清除」并同时落旗(**原子**:读+落一步完成)。
|
|
39
39
|
*
|
|
40
|
-
* 🔴 为什么必须是「take」而不是「clear」(
|
|
40
|
+
* 🔴 为什么必须是「take」而不是「clear」(对抗复审命中的双清):两条清除腿共用同一个布尔位,
|
|
41
41
|
* 而它们的触发顺序两个方向都真实存在 ——
|
|
42
42
|
* · `retrying → recovered`:直报腿先到,旗还在 ⇒ 本次要发清除,发完落旗;间接腿之后看不到旗。
|
|
43
43
|
* · `retrying → 主lane内容 → recovered`:**间接腿先到**(已发过一次 null 并落了旗),直报腿这一拍
|
package/dist/adapt.js
CHANGED
|
@@ -160,7 +160,7 @@ class WireToCcAdapterImpl {
|
|
|
160
160
|
}
|
|
161
161
|
};
|
|
162
162
|
const s = state;
|
|
163
|
-
// 单次快照(
|
|
163
|
+
// 单次快照(对抗复审 #2 收货修):拆分前这里对 `renderedNotifications` 恰一次属性读。
|
|
164
164
|
const rendered = s.renderedNotifications;
|
|
165
165
|
if (Array.isArray(rendered))
|
|
166
166
|
n += this.ledger.takeRenderedNotifications(rendered);
|
|
@@ -278,7 +278,7 @@ class WireToCcAdapterImpl {
|
|
|
278
278
|
if (m.type !== 'stream_event')
|
|
279
279
|
yield* text.drainLive();
|
|
280
280
|
// ── 分派(拆分前是一个 600 行的 switch;`default:` 空臂 = 表里查不到,行为同)────────────
|
|
281
|
-
// 单读快照(
|
|
281
|
+
// 单读快照(对抗复审 #1 收货修):旧 switch 对 `m.type` 恰一次属性读,`typeof m.type
|
|
282
282
|
// ? m.type` 是两读 —— 对 accessor 形帧可观测,降回一读。
|
|
283
283
|
const rawType = m.type;
|
|
284
284
|
const armKey = typeof rawType === 'string' ? rawType : undefined;
|
|
@@ -73,7 +73,7 @@ export type EventProjectionDropReason =
|
|
|
73
73
|
| 'unknown_arm'
|
|
74
74
|
/**
|
|
75
75
|
* 类型面**认得**这条臂、它也带着用户可见的决策内容,但本包**今天没有任何消费口**
|
|
76
|
-
* (2026-08-08
|
|
76
|
+
* (2026-08-08 对抗复审第 4/5 轮命中,首例 = `approval_request`)。
|
|
77
77
|
*
|
|
78
78
|
* 为什么不能并进 `not_in_slice`:那一档的语义是「本切片不投影,**因为别处接了/本来就没有可渲染物**」,
|
|
79
79
|
* 它走 `kind:'none'` —— 而 `none` 是**静默**的,只有 `dropped` 会经 `reportDroppedFrame` 走宿主
|
|
@@ -88,7 +88,7 @@ function assertNeverArm(_ev) {
|
|
|
88
88
|
*/
|
|
89
89
|
export function eventToSdkMessage(ev, ctx) {
|
|
90
90
|
switch (ev.type) {
|
|
91
|
-
// ── `human_input`(core 5.14.0 design/171 / server 7.4.0 SSE
|
|
91
|
+
// ── `human_input`(core 5.14.0 design/171 / server 7.4.0 SSE,[3017]/[3020])────────────
|
|
92
92
|
// 🔴 **到期复核已兑现(sdk 6.9.0 提货,2026-08-08)**:本臂此前是 switch **之前**的一条 raw
|
|
93
93
|
// 预分派(理由 = 它还没进 SDK 6.3.0 的 `AgentEvent` union,`case 'human_input'` 在 `ev.type`
|
|
94
94
|
// 上是编译错),头注写着「在 union 里的那天就把它搬进 switch」。sdk 6.9.0 的 events.d.ts
|
|
@@ -254,7 +254,7 @@ export function eventToSdkMessage(ev, ctx) {
|
|
|
254
254
|
...(retryInMs !== undefined ? { retryInMs } : {}),
|
|
255
255
|
...(attempt !== undefined ? { attempt } : {}),
|
|
256
256
|
...(maxRetries !== undefined ? { maxRetries } : {}),
|
|
257
|
-
// 🔴 §E2 lane 身份必须透传(2026-08-08
|
|
257
|
+
// 🔴 §E2 lane 身份必须透传(2026-08-08 对抗复审二轮复审命中的**跨 lane 状态破坏**)。
|
|
258
258
|
// `status` 臂本来就是 `& EventIdentity`(SDK events.d.ts),server 两腿共用的
|
|
259
259
|
// `brainStatusEventData` 也经 `identityFields` 发 eventId/parentToolCallId —— 而本层此前
|
|
260
260
|
// 把两键都剥掉了。后果:`arms.ts` 的 `retryStatusArm` 首行那条子代断闸
|
|
@@ -287,7 +287,7 @@ export function eventToSdkMessage(ev, ctx) {
|
|
|
287
287
|
// `workflowRunId`/`workflowAgentLabel`(lane 归属自描述位)。此前这层 spread 白名单把两键剥掉,
|
|
288
288
|
// bridge 想判 lane 也判不了(「送到了但没人读」的精确坐标其实是「没转」)。additive 透传,
|
|
289
289
|
// 防御读(旧 core/server 缺席 ⇒ 形状不变)。注意 server 侧 project.ts 投影白名单在 1.272.0
|
|
290
|
-
// 仍剥这两键(server a76bd77
|
|
290
|
+
// 仍剥这两键(server a76bd77 才修,[1619])——真 wire 于 1.273+ 才带,此处先备好通路。
|
|
291
291
|
const workflowRunId = ev.workflowRunId;
|
|
292
292
|
const workflowAgentLabel = ev.workflowAgentLabel;
|
|
293
293
|
return projected(stamp(ctx, armBody({
|
|
@@ -485,7 +485,7 @@ export function eventToSdkMessage(ev, ctx) {
|
|
|
485
485
|
/**
|
|
486
486
|
* `approval_request`(design/172 流内审批协议,server ≥7.3.0、7.5.0 起默认开)。
|
|
487
487
|
*
|
|
488
|
-
* 🔴 与上面两条**不同源**,所以单列(2026-08-08
|
|
488
|
+
* 🔴 与上面两条**不同源**,所以单列(2026-08-08 对抗复审第 4 轮命中:首版把三条并成一句
|
|
489
489
|
* 「都由 frameRouter 消费」—— 而 `isToolApprovalFrame` 只认 tool_approval/tool_approval_complete,
|
|
490
490
|
* 这条帧在**包内今天零消费口**,那句话是假的;pure 门 058⑬ 段把这个事实钉住了)。
|
|
491
491
|
*
|
|
@@ -556,7 +556,7 @@ function humanInputProjection(ev, ctx) {
|
|
|
556
556
|
...(str(ev.issuer) !== undefined ? { issuer: str(ev.issuer) } : {}),
|
|
557
557
|
...(actor !== undefined && Object.keys(actor).length > 0 ? { actor } : {}),
|
|
558
558
|
...(str(ev.entryId) !== undefined ? { entryId: str(ev.entryId) } : {}),
|
|
559
|
-
// 🔴 `eventId` 必须带到底(
|
|
559
|
+
// 🔴 `eventId` 必须带到底(对抗复审二轮):durable 腿按 `Last-Event-ID` 续读会**重放**同一条
|
|
560
560
|
// 账本帧,而本地行 id 是现铸的 —— 审计/时间线消费者若没有引擎铸的稳定键,一次人工注入会被
|
|
561
561
|
// 记成多次。`inputId`/`entryId` 在公开形上都是可选的,`eventId` 是那个恒在的身份位。
|
|
562
562
|
...(str(ev.eventId) !== undefined ? { eventId: str(ev.eventId) } : {}),
|
|
@@ -261,7 +261,7 @@ export function doneToSdkResult(ev, ctx) {
|
|
|
261
261
|
ctx.sessionId = echoedSid;
|
|
262
262
|
// P1-5 — modelUsage/usage 的构造已收敛到 `flattenUsage` / `modelUsageFor`(REF-CC-055/062),
|
|
263
263
|
// 四个 error 臂经 `errorResult` 信封拿到同一份,success 臂在下方直接调 —— 同一输入同一输出。
|
|
264
|
-
// clay P0 壳半场(
|
|
264
|
+
// clay P0 壳半场([450],2026-07-05):上游 4xx(如无 vision 模型收到 image)时
|
|
265
265
|
// 引擎的 done 帧本体带 result.status='failed' + errorMessage —— 传播链没吞,断点在这:
|
|
266
266
|
// 此前无条件投影 subtype:'success'/is_error:false,把失败洗成"成功空回复"= 用户看到的
|
|
267
267
|
// 静默卡死。status failed → 走 SDKResultError 形态(errors[] 渲染线现成)。
|
|
@@ -118,7 +118,7 @@ function sanitizeFrameType(type) {
|
|
|
118
118
|
* 🔴 已知限制(诚实披露):Ink 挂载后宿主会吞 console,所以 TUI 里这行未必上屏 —— 那正是
|
|
119
119
|
* `EventProjection.dropped` 存在的意义:想在自己那一端把它渲出来的宿主,读返回值即可。
|
|
120
120
|
*
|
|
121
|
-
* ── [C77]① 宿主出口 `ctx.onDroppedFrame`(2026-08-02
|
|
121
|
+
* ── [C77]① 宿主出口 `ctx.onDroppedFrame`(2026-08-02,协作板 web-client 请托)────────────────
|
|
122
122
|
* 上一段那条「读返回值即可」只对**自己驱动投影器**的宿主成立;经 `runStream` 消费的宿主
|
|
123
123
|
* (web/desktop 都是)看不到 `EventProjection`,于是丢帧对它只剩一行 stderr。装了 sink 的宿主
|
|
124
124
|
* 从此收到结构化的 `{type, why}`,自己那一端想渲成告警条还是计数器随它。
|
package/dist/adapter/types.d.ts
CHANGED
|
@@ -75,7 +75,7 @@ export interface EmitContext {
|
|
|
75
75
|
*/
|
|
76
76
|
emitChrome?(event: ChromeEvent): void | Promise<void>;
|
|
77
77
|
/**
|
|
78
|
-
* [C77]① 新增(
|
|
78
|
+
* [C77]① 新增(协作板 web-client 请托)—— **丢帧留痕的宿主出口**。runStream 的 `dropped` 臂
|
|
79
79
|
* (引擎发了一帧、这个 build 渲不出来)此前只有包侧一行 `console.error`,宿主拿不到结构化的
|
|
80
80
|
* `{type, why}`:web 想把它并进自己的 frame-warnings 面只能去 scrape stderr,而 Ink 宿主
|
|
81
81
|
* 干脆把 console 吞了。形制与上面的 `emitChrome` 同款 —— **可选注入,缺席 = 该宿主不消费**
|
|
@@ -26,7 +26,7 @@
|
|
|
26
26
|
* 能探则探:`GET /v1/capabilities` 的 **`approvals`** 位为 false ⇒ 'not-configured';
|
|
27
27
|
* caps 面自己不可达 ⇒ 判别缺席,**如实回 'ok'**(绝不编造判别)。
|
|
28
28
|
*
|
|
29
|
-
* 🔴 件 3 考据(
|
|
29
|
+
* 🔴 件 3 考据(读错键的定谳,协作板 [C33]③.3 → server [C34],server 3.13.0 已把辖域写进
|
|
30
30
|
* 代码注与 ARCHITECTURE):本实现此前读 `scheduler`,那是**错的键**。
|
|
31
31
|
* · `/v1/assistant/*` 的挂载条件是 `checkpointStore`(server `routes/approvals-assistant.ts:67`
|
|
32
32
|
* 的分支头:`if (deps.checkpointStore && (url.startsWith("/v1/approvals") ||
|
|
@@ -53,7 +53,7 @@
|
|
|
53
53
|
* 两处逐位说明。fleet 行的 `sessionId`/`scope` 被 server `stripT` 剥掉不上 wire,别在投影里等。
|
|
54
54
|
*
|
|
55
55
|
* ── 📋 下一批工单(件 4 调研,不在本批实现):BackgroundRow 的 canonical stop 能力判别 ────────
|
|
56
|
-
* 起因(
|
|
56
|
+
* 起因(协作板 [C33]③.4):web 报「`runs.cancel` 的 id 空间是 taskId,而 fleet 顶层行 id 是 runId、
|
|
57
57
|
* 子行是复合 id」⇒ 他们对 fleet 行**不渲 Stop**(没有已挣得的取消路径就不摆按钮 —— 这个处置本身
|
|
58
58
|
* 是对的,server [C34] 也同意)。主会话裁定:**不是「fleet 行没有停止路径」,而是要按行类型分**。
|
|
59
59
|
* 下一批要落的形状(本批只调研落档,不新建 API):
|
package/dist/agentsWireCaps.d.ts
CHANGED
|
@@ -76,8 +76,8 @@ export declare function projectAgentsForWire(defs: readonly AgentDefLike[], deps
|
|
|
76
76
|
* 解析 —— SDK 对这些统一抛错,catch 归一)⇒ 调用层 fail-soft 照发(旧 server 静默剥字段
|
|
77
77
|
* 无害;引擎真死 stream 自己 fail-loud)。
|
|
78
78
|
* 等价性:3s 预算改经 client timeoutMs;maxRetries=0 单发(否则 503 会按 SDK 缺省重试,探测预算
|
|
79
|
-
* 语义变形)
|
|
80
|
-
*
|
|
79
|
+
* 语义变形)。principal 头:SDK 6.11 起值检查删头——缺席不发(与原手抄同义;F-011 停发后
|
|
80
|
+
* 单机形恒缺席,owner-null)。
|
|
81
81
|
*/
|
|
82
82
|
export declare function engineSupportsTaskAgents(baseUrl: string, opts?: EngineProbeOpts): Promise<boolean | undefined>;
|
|
83
83
|
export type WireConfig = {
|
package/dist/agentsWireCaps.js
CHANGED
|
@@ -195,8 +195,8 @@ export function projectAgentsForWire(defs, deps) {
|
|
|
195
195
|
* 解析 —— SDK 对这些统一抛错,catch 归一)⇒ 调用层 fail-soft 照发(旧 server 静默剥字段
|
|
196
196
|
* 无害;引擎真死 stream 自己 fail-loud)。
|
|
197
197
|
* 等价性:3s 预算改经 client timeoutMs;maxRetries=0 单发(否则 503 会按 SDK 缺省重试,探测预算
|
|
198
|
-
* 语义变形)
|
|
199
|
-
*
|
|
198
|
+
* 语义变形)。principal 头:SDK 6.11 起值检查删头——缺席不发(与原手抄同义;F-011 停发后
|
|
199
|
+
* 单机形恒缺席,owner-null)。
|
|
200
200
|
*/
|
|
201
201
|
export async function engineSupportsTaskAgents(baseUrl, opts) {
|
|
202
202
|
const client = makeEngineWireClient({
|
|
@@ -47,11 +47,11 @@
|
|
|
47
47
|
* 语法(逗号分隔,大小写不敏感,允许空白):
|
|
48
48
|
* · `off|0|false|no|none`(整值) ⇒ **真·全关**:literal-true 族一个不发(那一族的 off 就是
|
|
49
49
|
* 删键)+ DEFAULT-ON 两键发 `false`。
|
|
50
|
-
* 🔴
|
|
50
|
+
* 🔴 对抗复审 [medium](2026-08-07)判的真病:这一支此前直接 `return undefined`(不发字段),
|
|
51
51
|
* 而「不发字段」对 DEFAULT-ON 两键的含义**恰恰是保持开着** —— 一个叫 off 的总开关关不掉十件里
|
|
52
52
|
* 的两件,且用户没有任何办法察觉。旧行为在 <1.254 的 server 上与新行为**逐字节等价**(那些
|
|
53
53
|
* server 静默丢 false),在 ≥1.254 上新行为才第一次兑现这个旋钮的字面承诺。
|
|
54
|
-
* ⚠️ **能力边界说清楚**(
|
|
54
|
+
* ⚠️ **能力边界说清楚**(对抗复审二轮):本模块是**纯 env→spec 投影**,手里没有 server
|
|
55
55
|
* 版本/capability 这个量,所以对 <1.254 的部署它兑现不了「全关」—— 那两键仍会默认开着,而
|
|
56
56
|
* 壳侧无从察觉。补这个洞的正位在**请求装配层**(按已探到的 capability 判,与 limitsWire 的
|
|
57
57
|
* 两道地板同族),已记进 docs/refactor/README.md 的宿主/上游工单表。本层只保证两件:
|
|
@@ -47,11 +47,11 @@
|
|
|
47
47
|
* 语法(逗号分隔,大小写不敏感,允许空白):
|
|
48
48
|
* · `off|0|false|no|none`(整值) ⇒ **真·全关**:literal-true 族一个不发(那一族的 off 就是
|
|
49
49
|
* 删键)+ DEFAULT-ON 两键发 `false`。
|
|
50
|
-
* 🔴
|
|
50
|
+
* 🔴 对抗复审 [medium](2026-08-07)判的真病:这一支此前直接 `return undefined`(不发字段),
|
|
51
51
|
* 而「不发字段」对 DEFAULT-ON 两键的含义**恰恰是保持开着** —— 一个叫 off 的总开关关不掉十件里
|
|
52
52
|
* 的两件,且用户没有任何办法察觉。旧行为在 <1.254 的 server 上与新行为**逐字节等价**(那些
|
|
53
53
|
* server 静默丢 false),在 ≥1.254 上新行为才第一次兑现这个旋钮的字面承诺。
|
|
54
|
-
* ⚠️ **能力边界说清楚**(
|
|
54
|
+
* ⚠️ **能力边界说清楚**(对抗复审二轮):本模块是**纯 env→spec 投影**,手里没有 server
|
|
55
55
|
* 版本/capability 这个量,所以对 <1.254 的部署它兑现不了「全关」—— 那两键仍会默认开着,而
|
|
56
56
|
* 壳侧无从察觉。补这个洞的正位在**请求装配层**(按已探到的 capability 判,与 limitsWire 的
|
|
57
57
|
* 两道地板同族),已记进 docs/refactor/README.md 的宿主/上游工单表。本层只保证两件:
|
|
@@ -123,7 +123,7 @@ function refuse(token, why) {
|
|
|
123
123
|
*/
|
|
124
124
|
export function attachmentsForRequest(env = hostEnv()) {
|
|
125
125
|
const raw = (env[ATTACHMENTS_ENV] ?? '').trim().toLowerCase();
|
|
126
|
-
// 总开关 off = 真·全关(见文件头注 §env 的
|
|
126
|
+
// 总开关 off = 真·全关(见文件头注 §env 的 复审 [medium] 登记),不是「不发字段」。
|
|
127
127
|
if (envFlagOff(raw))
|
|
128
128
|
return allDefaultOnOff();
|
|
129
129
|
const tokens = raw.split(',').map(t => t.trim()).filter(t => t.length > 0);
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
* 逐字纪律:CLASSIFIER_DENY_SIGNATURE / NOTICE_REASON_MAX(80)/ 通知行三段格式一字节不改。
|
|
9
9
|
*/
|
|
10
10
|
/**
|
|
11
|
-
* src/sema/classifierVerdictWire.ts — auto-mode 分类器裁决帧的壳侧消费(分类器批3
|
|
11
|
+
* src/sema/classifierVerdictWire.ts — auto-mode 分类器裁决帧的壳侧消费(分类器批3 壳半场,[907])。
|
|
12
12
|
*
|
|
13
13
|
* WIRE 形状(gap-check 2026-07-16 实勘,core 1.279 dist 亲核):
|
|
14
14
|
* 引擎侧分类器 block(core hooks.js runToolGate)→ decision = deny + decisionReason:"classifier",
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
* 逐字纪律:CLASSIFIER_DENY_SIGNATURE / NOTICE_REASON_MAX(80)/ 通知行三段格式一字节不改。
|
|
9
9
|
*/
|
|
10
10
|
/**
|
|
11
|
-
* src/sema/classifierVerdictWire.ts — auto-mode 分类器裁决帧的壳侧消费(分类器批3
|
|
11
|
+
* src/sema/classifierVerdictWire.ts — auto-mode 分类器裁决帧的壳侧消费(分类器批3 壳半场,[907])。
|
|
12
12
|
*
|
|
13
13
|
* WIRE 形状(gap-check 2026-07-16 实勘,core 1.279 dist 亲核):
|
|
14
14
|
* 引擎侧分类器 block(core hooks.js runToolGate)→ decision = deny + decisionReason:"classifier",
|
package/dist/detachWire.d.ts
CHANGED
|
@@ -137,7 +137,9 @@ export interface DetachCancelArm {
|
|
|
137
137
|
authToken: string | {
|
|
138
138
|
mode: 'loopback-unauthed';
|
|
139
139
|
};
|
|
140
|
-
principal
|
|
140
|
+
/** SDK Principal。缺席(undefined)=消费方不发 x-agent-principal 头(owner-null 单机形)——
|
|
141
|
+
* 与 SDK 6.11 Transport 的值检查删头语义一致;绝不在此铸哨兵值。 */
|
|
142
|
+
principal: string | undefined;
|
|
141
143
|
/** Reads the durable taskId early-captured off the X-Task-Id response header; null before capture. */
|
|
142
144
|
getTaskId: () => string | null;
|
|
143
145
|
}
|
package/dist/engineWireSdk.d.ts
CHANGED
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
* fail-closed worker 都是 401,对 owner-gated 路由都是 owner 不匹配,行为面等价。
|
|
18
18
|
*
|
|
19
19
|
* 缺省 maxRetries=0:raw fetch 原语义是单发不重试(探针有自己的预算窗;fire-and-forget 不该静默
|
|
20
|
-
* 翻倍打点)。要 SDK 缺省重试的调用方显式传。principal
|
|
20
|
+
* 翻倍打点)。要 SDK 缺省重试的调用方显式传。principal 缺席=不发头(F-011 停发,replEntry live 车道
|
|
21
21
|
* 同款)——SDK Transport 恒 stamp x-agent-principal(principal-first 宪法);旧 raw fetch 在缺
|
|
22
22
|
* principal 时省略该头,迁移后恒出示,对 requirePrincipal 部署是 fail-open 改善,已记账。
|
|
23
23
|
*/
|
|
@@ -69,8 +69,9 @@ export type EngineWireClientConfig = {
|
|
|
69
69
|
baseUrl: string;
|
|
70
70
|
/** 真 token 串;缺省经 wireAuthTokenFor 三态解析(loopback-unauthed / 'anon')。 */
|
|
71
71
|
token?: string;
|
|
72
|
-
/**
|
|
73
|
-
|
|
72
|
+
/** 缺席/undefined=不发 x-agent-principal 头(owner-null;F-011 停发,replEntry live 车道同闸口
|
|
73
|
+
* 语义;显式 `| undefined` 让 EngineWireTarget.principal 直传合法——exactOptionalPropertyTypes)。 */
|
|
74
|
+
principal?: string | undefined;
|
|
74
75
|
/** 每次请求的超时预算(SDK 缺省 60s)。 */
|
|
75
76
|
timeoutMs?: number;
|
|
76
77
|
/** 缺省 0(raw fetch 单发语义);要 SDK 重试的调用方显式传。 */
|
package/dist/engineWireSdk.js
CHANGED
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
* fail-closed worker 都是 401,对 owner-gated 路由都是 owner 不匹配,行为面等价。
|
|
18
18
|
*
|
|
19
19
|
* 缺省 maxRetries=0:raw fetch 原语义是单发不重试(探针有自己的预算窗;fire-and-forget 不该静默
|
|
20
|
-
* 翻倍打点)。要 SDK 缺省重试的调用方显式传。principal
|
|
20
|
+
* 翻倍打点)。要 SDK 缺省重试的调用方显式传。principal 缺席=不发头(F-011 停发,replEntry live 车道
|
|
21
21
|
* 同款)——SDK Transport 恒 stamp x-agent-principal(principal-first 宪法);旧 raw fetch 在缺
|
|
22
22
|
* principal 时省略该头,迁移后恒出示,对 requirePrincipal 部署是 fail-open 改善,已记账。
|
|
23
23
|
*/
|
|
@@ -75,7 +75,8 @@ export function makeEngineWireClient(cfg) {
|
|
|
75
75
|
return new AgentClient({
|
|
76
76
|
baseUrl: cfg.baseUrl,
|
|
77
77
|
authToken: resolveWireAuth(cfg.baseUrl, cfg.token),
|
|
78
|
-
|
|
78
|
+
// F-011 停发:缺席/空串=不给键(SDK 6.11 缺席=不发 x-agent-principal 头,owner-null)。
|
|
79
|
+
...(cfg.principal !== undefined && cfg.principal !== '' ? { principal: cfg.principal } : {}),
|
|
79
80
|
...(cfg.timeoutMs !== undefined ? { timeoutMs: cfg.timeoutMs } : {}),
|
|
80
81
|
maxRetries: cfg.maxRetries ?? 0,
|
|
81
82
|
...(cfg.fetchImpl ? { fetch: cfg.fetchImpl } : {}),
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
export interface EngineWireTarget {
|
|
2
2
|
baseUrl: string;
|
|
3
3
|
token?: string;
|
|
4
|
-
principal
|
|
4
|
+
/** 缺席=不发 x-agent-principal 头(owner-null,F-011 停发);显式装配/env 值恒赢。 */
|
|
5
|
+
principal?: string;
|
|
5
6
|
}
|
|
6
7
|
/** 装/卸引擎 wire 目标。传 null 卸回 env 派生。返回还原函数。 */
|
|
7
8
|
export declare function installEngineWireTarget(t: EngineWireTarget | null): () => void;
|
package/dist/engineWireTarget.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* ⇄ B6 批搬迁(2026-07-27,设计稿 §3 B6):子代 wire 族里**逐字重复**的 `wireConfig()`
|
|
3
|
-
* (SEMA_LIVE_BASEURL / SEMA_LIVE_TOKEN / SEMA_LIVE_PRINCIPAL
|
|
3
|
+
* (SEMA_LIVE_BASEURL / SEMA_LIVE_TOKEN / SEMA_LIVE_PRINCIPAL 三读;principal 缺席=不发头,F-011 停发)
|
|
4
4
|
* 收成一份。
|
|
5
5
|
*
|
|
6
6
|
* 🔴 收编前的事实(壳 HEAD 2aa1d3e 实测,`grep -rln 'function wireConfig' src/sema/`):
|
|
@@ -56,9 +56,10 @@ export function engineWireTargetFor(sessionKey) {
|
|
|
56
56
|
return {
|
|
57
57
|
baseUrl,
|
|
58
58
|
// principal must match the run's owner (stamped by the live stream) — the owner-gated routes answer
|
|
59
|
-
// 404 for non-owners (no existence oracle)
|
|
59
|
+
// 404 for non-owners (no existence oracle). F-011 停发([3279]):缺席=不发头,owner-null 两侧
|
|
60
|
+
// 对齐(server 7.8.1 读写面窄互认盖存量);显式 SEMA_LIVE_PRINCIPAL 恒赢,绝不铸哨兵值。
|
|
60
61
|
...(env.SEMA_LIVE_TOKEN ? { token: env.SEMA_LIVE_TOKEN } : {}),
|
|
61
|
-
principal: env.SEMA_LIVE_PRINCIPAL
|
|
62
|
+
...(env.SEMA_LIVE_PRINCIPAL ? { principal: env.SEMA_LIVE_PRINCIPAL } : {}),
|
|
62
63
|
};
|
|
63
64
|
}
|
|
64
65
|
/** 诊断开关(壳侧 `process.env.SEMA_DEBUG` 的等价读;本包零 process)。 */
|
package/dist/goalStopHook.d.ts
CHANGED
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
*
|
|
22
22
|
* 🟢 **本 overlay 默认开**(2026-07-26 翻默认;逃生口 `SEMA_GOAL_STOP_HOOK_WIRE=0/false/no/off`)。
|
|
23
23
|
*
|
|
24
|
-
* 修前默认关,理由是两条**前提**——两条都已被 server 侧行为取证**证伪**(
|
|
24
|
+
* 修前默认关,理由是两条**前提**——两条都已被 server 侧行为取证**证伪**([1721],6 条行为
|
|
25
25
|
* 用例已进 server 仓;cli 仓另有 scripts/run-goal-stop-hook-live-test.mjs 的真引擎+真模型复验):
|
|
26
26
|
* ① 旧论断「SDK 类型 DEFERRED ⇒ 服务端会 400」**是把类型面当成了运行时校验面**,对 server
|
|
27
27
|
* 不成立:`parseHooksConfig({Stop:[{hooks:[{type:"prompt",prompt}]}]})` 无 error、真解析;
|
package/dist/goalStopHook.js
CHANGED
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
*
|
|
22
22
|
* 🟢 **本 overlay 默认开**(2026-07-26 翻默认;逃生口 `SEMA_GOAL_STOP_HOOK_WIRE=0/false/no/off`)。
|
|
23
23
|
*
|
|
24
|
-
* 修前默认关,理由是两条**前提**——两条都已被 server 侧行为取证**证伪**(
|
|
24
|
+
* 修前默认关,理由是两条**前提**——两条都已被 server 侧行为取证**证伪**([1721],6 条行为
|
|
25
25
|
* 用例已进 server 仓;cli 仓另有 scripts/run-goal-stop-hook-live-test.mjs 的真引擎+真模型复验):
|
|
26
26
|
* ① 旧论断「SDK 类型 DEFERRED ⇒ 服务端会 400」**是把类型面当成了运行时校验面**,对 server
|
|
27
27
|
* 不成立:`parseHooksConfig({Stop:[{hooks:[{type:"prompt",prompt}]}]})` 无 error、真解析;
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
* · flag 来源:显式表态一律显式 stamp——wire 五词直 stamp,`default` 走 stampDefault 显式垫
|
|
22
22
|
* (旧形 default 不 stamp ⇒ server 侧 `settings.permissions.defaultMode` 恒缺席 ⇒
|
|
23
23
|
* `deriveSettingsPolicy` 早退返回 `{}` ⇒ **按模式派生的那套门一个不铸**,print 车道 ask 门
|
|
24
|
-
* 断链根因。⚠️ 本模块只对**这一个量**负责:body 里有没有 `permissionMode
|
|
24
|
+
* 断链根因。⚠️ 本模块只对**这一个量**负责:body 里有没有 `permissionMode`。[2713] 写的
|
|
25
25
|
* 「applyTaskSettings 整跳」是那条链的简写,它成不成立还要看 body.settings 里有没有别的
|
|
26
26
|
* parsed 字段 —— 那是 server 的控制流,会随 server 改版漂,别在本注释里复述第二遍,要查就去
|
|
27
27
|
* 读 server task-settings.ts);壳内部词(`manual`=CC default 别名、`dontAsk`=壳侧最严
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
* · flag 来源:显式表态一律显式 stamp——wire 五词直 stamp,`default` 走 stampDefault 显式垫
|
|
22
22
|
* (旧形 default 不 stamp ⇒ server 侧 `settings.permissions.defaultMode` 恒缺席 ⇒
|
|
23
23
|
* `deriveSettingsPolicy` 早退返回 `{}` ⇒ **按模式派生的那套门一个不铸**,print 车道 ask 门
|
|
24
|
-
* 断链根因。⚠️ 本模块只对**这一个量**负责:body 里有没有 `permissionMode
|
|
24
|
+
* 断链根因。⚠️ 本模块只对**这一个量**负责:body 里有没有 `permissionMode`。[2713] 写的
|
|
25
25
|
* 「applyTaskSettings 整跳」是那条链的简写,它成不成立还要看 body.settings 里有没有别的
|
|
26
26
|
* parsed 字段 —— 那是 server 的控制流,会随 server 改版漂,别在本注释里复述第二遍,要查就去
|
|
27
27
|
* 读 server task-settings.ts);壳内部词(`manual`=CC default 别名、`dontAsk`=壳侧最严
|
|
@@ -42,7 +42,7 @@
|
|
|
42
42
|
* 落账,守卫 = ①终帧唯一(本 wrapper 首终帧即 return + adapter runStream 首终帧 return + 批 B
|
|
43
43
|
* 双帧守卫「恰一条 result」)②seq 锚(首帧起锁存,attempt 间绝不回放)③gap-check 记账:换道前
|
|
44
44
|
* 已消费的 delta 与账本聚合 text 事件无逐字节对齐关系,真正的精确锚需要 server 给 tasks/stream
|
|
45
|
-
* 帧发 id(
|
|
45
|
+
* 帧发 id(引擎侧诉求,走协作板,非壳侧可解)。
|
|
46
46
|
*
|
|
47
47
|
* ── 账本空(现役 server sync 腿)时的续收降级(R1b)────────────────────────────────────────
|
|
48
48
|
* 同一实证的另一面:detach 后 run 后台跑完,账本无事件行,runs.events 只会心跳保活直到 run row
|
|
@@ -80,7 +80,7 @@ export async function* withHeadlessR1Reconnect(live, deps) {
|
|
|
80
80
|
const probe = deps.probeAlive ?? probeEngineAlive;
|
|
81
81
|
// REF-CC-148(域词表-19):originalTearErr 在环内从不被重写(它是进入本重试环前唯一捕获的
|
|
82
82
|
// 错误对象),所以这个判型是**环不变式**——算一次即可,不必逐轮重算。
|
|
83
|
-
// wave1 回炉复审(
|
|
83
|
+
// wave1 回炉复审(复审 blocker):求值时机必须排在铁律 3(用户中止恒先行)**之后**才对 main
|
|
84
84
|
// 逐字——main 是「每轮入口先查 aborted,再判型」,若把判型提到循环顶(环外、抢在第一轮的
|
|
85
85
|
// aborted 检查之前),当 originalTearErr 是一个 `.name` getter 会抛的畸形错误对象、且入环时
|
|
86
86
|
// signal 已经 aborted 时,新顺序会先让 isSseIdleError 抛出**那个畸形对象的二次异常**,盖过
|
|
@@ -89,7 +89,7 @@ export interface ApprovalsFeedOptions {
|
|
|
89
89
|
/** 降级后多久再试一次 stream;缺省 60_000ms。0 = 不再试(永久轮询)。 */
|
|
90
90
|
streamRetryMs?: number;
|
|
91
91
|
/**
|
|
92
|
-
* [C77]② 轮询条件旋钮(
|
|
92
|
+
* [C77]② 轮询条件旋钮(协作板 desktop 请托:那一端的现行纪律是**仅活跃 run 时轮询**)。
|
|
93
93
|
* 每一拍**触发时**查询一次:`false` ⇒ 跳过本拍取件,但照常排下一拍。缺省(不传)= 恒 true,
|
|
94
94
|
* 行为与加旋钮之前一字不差。
|
|
95
95
|
*
|
package/dist/hitl/frameRouter.js
CHANGED
|
@@ -270,7 +270,7 @@ async function routeToolApprovalFrame(ev, ctx) {
|
|
|
270
270
|
hostLog('debug', `liveHitlAskWire: tool_approval frame ${ev.approvalId} but no respond wire — engine self-settles (TTL deny)`);
|
|
271
271
|
return { kind: 'skip' };
|
|
272
272
|
}
|
|
273
|
-
// 补验批 askq 案定谳(2026-07-23
|
|
273
|
+
// 补验批 askq 案定谳(2026-07-23,[1534],引擎 dist 逐坐标读定):core 的 durable
|
|
274
274
|
// question policy 对 AskUserQuestion 出 action:"ask",本意让 durable gate park(suspended
|
|
275
275
|
// → 下方 bridge 弹卡收答);但 core suspendAsk 的退位条件(safety 缺席 + onAsk 在场)
|
|
276
276
|
// 把问题门也抢进了同步审批帧腿(壳为 fs 写权限三选卡开的 TOOL_APPROVAL_ENABLED)——同步帧
|
|
@@ -46,7 +46,7 @@ export interface GateLedger {
|
|
|
46
46
|
/** 首见 ⇒ true(并记账);durable 重放的已渲 call ⇒ false。 */
|
|
47
47
|
markStarted(callId: string): boolean;
|
|
48
48
|
/** 🔴 存 **tool_start 当拍的 `args` 快照**而非帧引用(与拆分前 `askArgsByCall` 逐字同语义;
|
|
49
|
-
*
|
|
49
|
+
* 对抗复审确证差异 #1 的收货修)——存帧引用意味着「上游在 yield 后改写 `ev.args`」会漂进
|
|
50
50
|
* 审批 payload,且台账持帧延长了整帧生命周期。载荷仍是 UNTRUSTED unknown,台账只搬运不解释。 */
|
|
51
51
|
noteGatedStart(callId: string, ev: AgentEvent): void;
|
|
52
52
|
gatedStartArgs(): ReadonlyMap<string, unknown>;
|
|
@@ -56,7 +56,7 @@ export declare function surfaceRememberNotApplied(): void;
|
|
|
56
56
|
* 「编辑并批准」带了 `updatedInput`,而 ack 回报 `updatedInputForwarded:false`(server 1.241 起
|
|
57
57
|
* 诚实回显)—— 引擎拿到的是**原始**入参。
|
|
58
58
|
*
|
|
59
|
-
* 🔴 这一条比 remember 那条严重一个量级,它是本批
|
|
59
|
+
* 🔴 这一条比 remember 那条严重一个量级,它是本批 对抗复审判的 [high]:用户在卡上把
|
|
60
60
|
* `rm -rf /tmp/x` 改成 `rm -rf /tmp/x/build` 然后按了批准,而真正执行的是他改之前那条。
|
|
61
61
|
* **事后没有 fail-closed 的余地**(allow 已经送达,工具已经在跑),所以唯一诚实的处置就是立刻
|
|
62
62
|
* 响亮地说出来 —— 静默(此前只写 debug 日志)等于让用户以为自己的编辑生效了。
|
|
@@ -130,7 +130,7 @@ export function surfaceRememberNotApplied() {
|
|
|
130
130
|
* 「编辑并批准」带了 `updatedInput`,而 ack 回报 `updatedInputForwarded:false`(server 1.241 起
|
|
131
131
|
* 诚实回显)—— 引擎拿到的是**原始**入参。
|
|
132
132
|
*
|
|
133
|
-
* 🔴 这一条比 remember 那条严重一个量级,它是本批
|
|
133
|
+
* 🔴 这一条比 remember 那条严重一个量级,它是本批 对抗复审判的 [high]:用户在卡上把
|
|
134
134
|
* `rm -rf /tmp/x` 改成 `rm -rf /tmp/x/build` 然后按了批准,而真正执行的是他改之前那条。
|
|
135
135
|
* **事后没有 fail-closed 的余地**(allow 已经送达,工具已经在跑),所以唯一诚实的处置就是立刻
|
|
136
136
|
* 响亮地说出来 —— 静默(此前只写 debug 日志)等于让用户以为自己的编辑生效了。
|
|
@@ -264,7 +264,7 @@ export type RespondToolApprovalFn = (approvalId: string, decision: ToolApprovalR
|
|
|
264
264
|
* 「拿到一个不好用的值」不如「诚实地什么都没有」。两个可选布尔位非布尔时**单独**降缺席
|
|
265
265
|
* (它们直接决定要不要渲「本会话全放行」,透传一个 `'yes'` 字符串会让 `!== false` 这类读法说反话)。
|
|
266
266
|
*
|
|
267
|
-
* 🔴 `decision` 判到 **wire 三词闭集**而不是「是不是串」(
|
|
267
|
+
* 🔴 `decision` 判到 **wire 三词闭集**而不是「是不是串」(对抗复审二轮):ack 上那两个布尔位会
|
|
268
268
|
* 触发**高危安全声明**(「工具正在用原始入参跑」),所以一个 `decision:'garbage'` 的回执绝不许被
|
|
269
269
|
* 当成合规 ack 放行。**相关性**(「这个 ack 是不是**这一次**审批的回执」)不在本函数判 —— 本函数
|
|
270
270
|
* 只认形,对不对得上由 {@link surfaceToolApprovalFrameAndRespond} 拿着 frame 与刚发出的 decision 核。
|
|
@@ -329,7 +329,7 @@ function isToolApprovalDelegation(v) {
|
|
|
329
329
|
if (typeof d.parentToolCallId !== 'string' || d.parentToolCallId.trim().length === 0)
|
|
330
330
|
return false;
|
|
331
331
|
// 深度:上游语义是「宿主直接子代 = 1」⇒ **正安全整数**。0 / 负数 / 小数都不是可渲染的层数,
|
|
332
|
-
// 而 `Number.isFinite` 会把它们全放过(
|
|
332
|
+
// 而 `Number.isFinite` 会把它们全放过(对抗复审命中:`depth: 0` / `-1` / `1.5` 曾一律判真)。
|
|
333
333
|
if (typeof d.depth !== 'number' || !Number.isSafeInteger(d.depth) || d.depth < 1)
|
|
334
334
|
return false;
|
|
335
335
|
return d.agentName === undefined || typeof d.agentName === 'string';
|
|
@@ -354,7 +354,7 @@ function isRespondDecision(v) {
|
|
|
354
354
|
* 「拿到一个不好用的值」不如「诚实地什么都没有」。两个可选布尔位非布尔时**单独**降缺席
|
|
355
355
|
* (它们直接决定要不要渲「本会话全放行」,透传一个 `'yes'` 字符串会让 `!== false` 这类读法说反话)。
|
|
356
356
|
*
|
|
357
|
-
* 🔴 `decision` 判到 **wire 三词闭集**而不是「是不是串」(
|
|
357
|
+
* 🔴 `decision` 判到 **wire 三词闭集**而不是「是不是串」(对抗复审二轮):ack 上那两个布尔位会
|
|
358
358
|
* 触发**高危安全声明**(「工具正在用原始入参跑」),所以一个 `decision:'garbage'` 的回执绝不许被
|
|
359
359
|
* 当成合规 ack 放行。**相关性**(「这个 ack 是不是**这一次**审批的回执」)不在本函数判 —— 本函数
|
|
360
360
|
* 只认形,对不对得上由 {@link surfaceToolApprovalFrameAndRespond} 拿着 frame 与刚发出的 decision 核。
|
|
@@ -469,7 +469,7 @@ export async function surfaceToolApprovalFrameAndRespond(frame, respond, streamA
|
|
|
469
469
|
...(isFromSubagent(frame) ? { workerBadge: subagentBadgeFor(frame) } : {}),
|
|
470
470
|
...(wireNote !== undefined ? { wireNote } : {}),
|
|
471
471
|
...(frame.governanceForced === true ? { governanceForced: true } : {}),
|
|
472
|
-
// 🔴 跨字段不变量(
|
|
472
|
+
// 🔴 跨字段不变量(对抗复审命中):`delegation` 只在**子代 ask** 的门上在场(SDK 头注:
|
|
473
473
|
// "Present on the same door as fromSubagent (child asks only)")。只校对象形不校这一条 ⇒
|
|
474
474
|
// 一个**宿主自己**的破坏性工具审批也能带着 delegation 到卡口,被呈成「某层子代发起的」——
|
|
475
475
|
// 把归属这件安全展示位渲错,正是本键存在的反面。`isToolApprovalFrame` 只验 type/approvalId,
|
|
@@ -488,7 +488,7 @@ export async function surfaceToolApprovalFrameAndRespond(frame, respond, streamA
|
|
|
488
488
|
...(signal && !signal.aborted ? { signal } : {}),
|
|
489
489
|
...(card.kind === 'allow' && card.updatedInput !== undefined ? { updatedInput: card.updatedInput } : {}),
|
|
490
490
|
});
|
|
491
|
-
// 🔴 相关性门(
|
|
491
|
+
// 🔴 相关性门(对抗复审二轮):ack 必须是**这一次**审批的回执 —— id 与决断词都要对上。
|
|
492
492
|
// 对不上的 ack(注入面串了别人的响应 / 坏 mock / raw-fetch 包装器复用了连接)如果照样被
|
|
493
493
|
// 消费,一次普通审批就能弹出「你的编辑没生效、工具正在用原始入参跑」这种强安全声明。
|
|
494
494
|
// 不匹配 ⇒ 整个 ack 丢弃(降成「未知」)+ 响亮留痕,绝不据此触发任何用户告警。
|
package/dist/index.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @sema-agent/client-core — 客户端会话运行时(sema wire → CC 会话词汇表 + 端无关会话逻辑)。
|
|
3
|
-
*
|
|
3
|
+
* 定位公理:[1832](CC 皮肤形状全收本包、wire 保持中性;TUI/web/桌面共用同一个包)。
|
|
4
4
|
* seam 设计对签:[1651]/[1652]/[1653];依赖方向:sdk(wire)+agent-types(词汇表)→ 本包,永不反向。
|
|
5
5
|
* 沿革:@sema-agent/wire-cc-adapter 0.1.0 = seam 类型 + id 确定性派生 + 首批踩坑纯函数;
|
|
6
6
|
* 0.1.2(#52a)= adapt() 管线首批(纯投影臂全落 + 壳态耦合臂投影成 ChromeEvent + 差分守卫);
|
package/dist/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @sema-agent/client-core — 客户端会话运行时(sema wire → CC 会话词汇表 + 端无关会话逻辑)。
|
|
3
|
-
*
|
|
3
|
+
* 定位公理:[1832](CC 皮肤形状全收本包、wire 保持中性;TUI/web/桌面共用同一个包)。
|
|
4
4
|
* seam 设计对签:[1651]/[1652]/[1653];依赖方向:sdk(wire)+agent-types(词汇表)→ 本包,永不反向。
|
|
5
5
|
* 沿革:@sema-agent/wire-cc-adapter 0.1.0 = seam 类型 + id 确定性派生 + 首批踩坑纯函数;
|
|
6
6
|
* 0.1.2(#52a)= adapt() 管线首批(纯投影臂全落 + 壳态耦合臂投影成 ChromeEvent + 差分守卫);
|
|
@@ -38,7 +38,7 @@
|
|
|
38
38
|
* · 旧 server 白名单 fail-soft:server resolveSpec 逐字段白名单拼 TaskSpec,未知 body 字段静默
|
|
39
39
|
* 忽略(limits wire 同款勘察结论)——本字段发了白发不炸。gap-check 实拆 server 1.210.0 dist:
|
|
40
40
|
* resolveSpec(main.js:1233-)【不】读 body.interactiveTools ⇒ 需 server 半场补一行白名单,
|
|
41
|
-
* 壳先备(
|
|
41
|
+
* 壳先备(协作板记账)。
|
|
42
42
|
*/
|
|
43
43
|
import { type EnvLike } from './hostEnv.js';
|
|
44
44
|
/** 部署旋钮 env 键名(settings.json env 块 → 1a-envseed → process.env 同车道)。 */
|
|
@@ -38,7 +38,7 @@
|
|
|
38
38
|
* · 旧 server 白名单 fail-soft:server resolveSpec 逐字段白名单拼 TaskSpec,未知 body 字段静默
|
|
39
39
|
* 忽略(limits wire 同款勘察结论)——本字段发了白发不炸。gap-check 实拆 server 1.210.0 dist:
|
|
40
40
|
* resolveSpec(main.js:1233-)【不】读 body.interactiveTools ⇒ 需 server 半场补一行白名单,
|
|
41
|
-
* 壳先备(
|
|
41
|
+
* 壳先备(协作板记账)。
|
|
42
42
|
*/
|
|
43
43
|
import { hostEnv } from './hostEnv.js';
|
|
44
44
|
import { envFlagOff, envFlagOn } from './envFlag.js';
|
package/dist/limitsWire.d.ts
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* src/limitsWire.ts — headless `-p` run-limits wire: expose the engine's TASK-LEVEL budget face on
|
|
3
3
|
* the headless `-p` path via `TaskRequest.limits`.
|
|
4
4
|
*
|
|
5
|
-
* ── core 5.8.0 词表迁移(
|
|
5
|
+
* ── core 5.8.0 词表迁移([2489],2026-08-04)────────────────────────────────────────────
|
|
6
6
|
* `limits` 是**唯一预算面,默认全空 = 无限制**。本模块拼的三个键都骑 5.8.0 的新词表:
|
|
7
7
|
* · `maxWalltimeMs`(**毫秒**;5.7 的 `limits.timeoutSec` 已删,单位一并变)
|
|
8
8
|
* · `maxTurns`
|
package/dist/limitsWire.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* src/limitsWire.ts — headless `-p` run-limits wire: expose the engine's TASK-LEVEL budget face on
|
|
3
3
|
* the headless `-p` path via `TaskRequest.limits`.
|
|
4
4
|
*
|
|
5
|
-
* ── core 5.8.0 词表迁移(
|
|
5
|
+
* ── core 5.8.0 词表迁移([2489],2026-08-04)────────────────────────────────────────────
|
|
6
6
|
* `limits` 是**唯一预算面,默认全空 = 无限制**。本模块拼的三个键都骑 5.8.0 的新词表:
|
|
7
7
|
* · `maxWalltimeMs`(**毫秒**;5.7 的 `limits.timeoutSec` 已删,单位一并变)
|
|
8
8
|
* · `maxTurns`
|
|
@@ -78,7 +78,7 @@ export declare function _resetLiveInitToolFaceForTest(): void;
|
|
|
78
78
|
* 同 wire 同 encodeURIComponent)→ { tools(场景附加段), toolset }。fail-soft:任何失败(网络/404/
|
|
79
79
|
* 形状不符/超时)返回 null,调用层回退缺省词表。等价性记账:超时经 client timeoutMs(缺省 2s 同预算,
|
|
80
80
|
* maxRetries=0 单发同原语义);ScenarioDetail 类型面之外仍保留逐字段运行时校验(引擎回什么不轻信)。
|
|
81
|
-
*
|
|
81
|
+
* principal 头:SDK 6.11 起值检查删头(缺席不发;F-011 停发后单机形恒缺席)——原手抄在无 principal
|
|
82
82
|
* 时省略该头;principal-first 宪法姿势,对 requirePrincipal 部署是 fail-open 改善。 */
|
|
83
83
|
export declare function probeScenarioTools(baseUrl: string, scenario: string, opts?: EngineProbeOpts): Promise<{
|
|
84
84
|
tools: string[];
|
package/dist/liveInitToolFace.js
CHANGED
|
@@ -126,7 +126,7 @@ export function _resetLiveInitToolFaceForTest() {
|
|
|
126
126
|
* 同 wire 同 encodeURIComponent)→ { tools(场景附加段), toolset }。fail-soft:任何失败(网络/404/
|
|
127
127
|
* 形状不符/超时)返回 null,调用层回退缺省词表。等价性记账:超时经 client timeoutMs(缺省 2s 同预算,
|
|
128
128
|
* maxRetries=0 单发同原语义);ScenarioDetail 类型面之外仍保留逐字段运行时校验(引擎回什么不轻信)。
|
|
129
|
-
*
|
|
129
|
+
* principal 头:SDK 6.11 起值检查删头(缺席不发;F-011 停发后单机形恒缺席)——原手抄在无 principal
|
|
130
130
|
* 时省略该头;principal-first 宪法姿势,对 requirePrincipal 部署是 fail-open 改善。 */
|
|
131
131
|
export async function probeScenarioTools(baseUrl, scenario, opts) {
|
|
132
132
|
const client = makeEngineWireClient({
|
package/dist/notifications.d.ts
CHANGED
|
@@ -40,7 +40,7 @@ export declare function deriveNotificationResidualLines(n: Record<string, unknow
|
|
|
40
40
|
* 字段名映射按 wire 真形:task_id/output_file/task_type/source 是 snake/wire 名,其余同名。
|
|
41
41
|
*/
|
|
42
42
|
export declare function normalizeTaskNotification(n: Record<string, unknown>): TaskNotificationFields | null;
|
|
43
|
-
/** 通知去重键——cli engineTaskNotificationDedupKey **逐字等价**(
|
|
43
|
+
/** 通知去重键——cli engineTaskNotificationDedupKey **逐字等价**(对抗复审抓的
|
|
44
44
|
* 等价性破坏,0.1.1 修):无 seq 不追加段(与 seq:1 是不同键);仅 external 用
|
|
45
45
|
* `external:` 前缀;seq 收 number|string。格式:`[external:]taskId:status[:seq]`。 */
|
|
46
46
|
export declare function taskNotificationDedupKey(n: {
|
|
@@ -54,7 +54,7 @@ export declare function taskNotificationDedupKey(n: {
|
|
|
54
54
|
* 的等价物(入参是引擎 `task_notification` 帧的原始 payload:snake_case `task_id` / `task_type`)。
|
|
55
55
|
*
|
|
56
56
|
* 🔴 **不是第二份算法**:字段归一之后直接委托给上面那一个 `taskNotificationDedupKey`。
|
|
57
|
-
* 两份手写算法正是这条键在 0.1.1 被
|
|
57
|
+
* 两份手写算法正是这条键在 0.1.1 被 对抗复审抓到过的形(无 seq 追不追段的差异会让
|
|
58
58
|
* 「重放去重」整条失效而两边代码看着都对);pure 门 B7 段对两个入口做**同键对拍**。
|
|
59
59
|
*
|
|
60
60
|
* 键形:`[external:]taskId:status[:seq]`。缺 `task_id` ⇒ 空 taskId 段(与 cli 逐字一致 ——
|
package/dist/notifications.js
CHANGED
|
@@ -92,7 +92,7 @@ export function normalizeTaskNotification(n) {
|
|
|
92
92
|
...(typeof n.source === 'string' && n.source.length > 0 ? { externalSource: n.source } : {}),
|
|
93
93
|
};
|
|
94
94
|
}
|
|
95
|
-
/** 通知去重键——cli engineTaskNotificationDedupKey **逐字等价**(
|
|
95
|
+
/** 通知去重键——cli engineTaskNotificationDedupKey **逐字等价**(对抗复审抓的
|
|
96
96
|
* 等价性破坏,0.1.1 修):无 seq 不追加段(与 seq:1 是不同键);仅 external 用
|
|
97
97
|
* `external:` 前缀;seq 收 number|string。格式:`[external:]taskId:status[:seq]`。 */
|
|
98
98
|
export function taskNotificationDedupKey(n) {
|
|
@@ -105,7 +105,7 @@ export function taskNotificationDedupKey(n) {
|
|
|
105
105
|
* 的等价物(入参是引擎 `task_notification` 帧的原始 payload:snake_case `task_id` / `task_type`)。
|
|
106
106
|
*
|
|
107
107
|
* 🔴 **不是第二份算法**:字段归一之后直接委托给上面那一个 `taskNotificationDedupKey`。
|
|
108
|
-
* 两份手写算法正是这条键在 0.1.1 被
|
|
108
|
+
* 两份手写算法正是这条键在 0.1.1 被 对抗复审抓到过的形(无 seq 追不追段的差异会让
|
|
109
109
|
* 「重放去重」整条失效而两边代码看着都对);pure 门 B7 段对两个入口做**同键对拍**。
|
|
110
110
|
*
|
|
111
111
|
* 键形:`[external:]taskId:status[:seq]`。缺 `task_id` ⇒ 空 taskId 段(与 cli 逐字一致 ——
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
* acceptEdits/bypassPermissions ⇒ loosening, coerced to default engine-side, enforced client-side). This keeps the
|
|
13
13
|
* shell a thin per-turn intent projector that's identical across TOC-local / TOB-cloud / centralized-session axes.
|
|
14
14
|
*
|
|
15
|
-
* `auto`(分类器批3
|
|
15
|
+
* `auto`(分类器批3,[907] server 五模式表):server ≥1.209 coercePermissionMode 认 "auto"
|
|
16
16
|
* (解释 = default 同款 fs 写 ask 门;存活 ask 由引擎侧 auto-mode 分类器先行裁决——武装 AND 门
|
|
17
17
|
* RuntimeCaps.autoMode ∧ RunnerDeps.autoMode,缺一静默回 ask,fail-closed)。壳只透传意图,分类器
|
|
18
18
|
* 规则/权益都在装配面,非 TaskSpec 字段。版本安全:老 server coerce 未知非空词 → "default"
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
* acceptEdits/bypassPermissions ⇒ loosening, coerced to default engine-side, enforced client-side). This keeps the
|
|
13
13
|
* shell a thin per-turn intent projector that's identical across TOC-local / TOB-cloud / centralized-session axes.
|
|
14
14
|
*
|
|
15
|
-
* `auto`(分类器批3
|
|
15
|
+
* `auto`(分类器批3,[907] server 五模式表):server ≥1.209 coercePermissionMode 认 "auto"
|
|
16
16
|
* (解释 = default 同款 fs 写 ask 门;存活 ask 由引擎侧 auto-mode 分类器先行裁决——武装 AND 门
|
|
17
17
|
* RuntimeCaps.autoMode ∧ RunnerDeps.autoMode,缺一静默回 ask,fail-closed)。壳只透传意图,分类器
|
|
18
18
|
* 规则/权益都在装配面,非 TaskSpec 字段。版本安全:老 server coerce 未知非空词 → "default"
|
package/dist/retryStatus.d.ts
CHANGED
|
@@ -24,7 +24,7 @@
|
|
|
24
24
|
export type RetryStatus =
|
|
25
25
|
/** 等 API 响应(`reconnecting`)。**计数两位在场**:实装 core 的 reconnecting 帧与 retrying/
|
|
26
26
|
* rate_limited 同形,六字段全发(`stream-engine.js` 三处 `sleepAnnouncingRetry` 逐处实测)——
|
|
27
|
-
* 丢掉它们正好是在「用户最需要看重连进度」的那一刻把进度藏起来(2026-08-08
|
|
27
|
+
* 丢掉它们正好是在「用户最需要看重连进度」的那一刻把进度藏起来(2026-08-08 对抗复审命中)。 */
|
|
28
28
|
{
|
|
29
29
|
kind: 'stalled';
|
|
30
30
|
deadline: number;
|
|
@@ -36,7 +36,7 @@ export type RetryStatus =
|
|
|
36
36
|
attempt?: number;
|
|
37
37
|
maxRetries?: number;
|
|
38
38
|
/**
|
|
39
|
-
* 🔴 **终态位**(2026-08-08
|
|
39
|
+
* 🔴 **终态位**(2026-08-08 对抗复审命中):`true` ⇔ 引擎**不会再重试了**(`gave_up` 相)。
|
|
40
40
|
* 缺席 = 仍在重试循环里(retrying / rate_limited / circuit_open)。
|
|
41
41
|
*
|
|
42
42
|
* 为什么必须有这一位:`deadline` 的语义是「距下次重试」,而 gave_up 根本没有下次 —— 实装 core
|
package/dist/seam.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* client-core seam types —
|
|
2
|
+
* client-core seam types — [1651] 设计稿 v1.1 已对签形([1652] core 签/[1653] 钉版)。
|
|
3
3
|
*
|
|
4
4
|
* 平面判据(成文,[1652]):「重启后还该看得见的进 transcript,纯瞬态进 chrome。」
|
|
5
5
|
* transcript id 纪律([1653] v1 定案,后改=BREAKING):优先从 wire 稳定键确定性派生
|
|
@@ -377,7 +377,7 @@ export type ChromeEvent = {
|
|
|
377
377
|
result: unknown;
|
|
378
378
|
}
|
|
379
379
|
/**
|
|
380
|
-
* FIX⑦(2026-08-07
|
|
380
|
+
* FIX⑦(2026-08-07,[3017]/[3020];core 5.14.0 design/171 新 `TaskEvent` 臂,server 7.4.0
|
|
381
381
|
* 起真上 SSE)——「**谁把什么喂进了这条 run**」的生命周期账本帧:objective / 实时 steer /
|
|
382
382
|
* nextTurn / parked-steer 续跑 / wake 五个载体共用一个投影点。
|
|
383
383
|
*
|
package/dist/skillsWireCaps.d.ts
CHANGED
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
* content ≤1MB — a violation is a 400, so we truncate/limit HERE to make each FIELD well-formed
|
|
13
13
|
* by construction.
|
|
14
14
|
*
|
|
15
|
-
* 🔴 措辞收窄(2026-08-08
|
|
15
|
+
* 🔴 措辞收窄(2026-08-08 对抗复审命中):原文写「make the live request well-formed by construction」——
|
|
16
16
|
* 那是**过头的承诺**,本模块只管每个字段的**逐字段**帽,管不到整请求。server 那边 10 项 × 1MB 与
|
|
17
17
|
* 它自己 8MB 的 `MAX_BODY` 是两个互不知情的帽,所以极端技能集仍可能整请求 400/413。本层不加
|
|
18
18
|
* 「按剩余预算偷偷多截一点」的聚合补偿:那恰好把一个响亮的 400 换回一次静默截断(= 本次修掉的病)。
|
|
@@ -11,7 +11,7 @@ export declare function engineTaskHandlesCapable(): boolean;
|
|
|
11
11
|
*
|
|
12
12
|
* true ⇒ 行的执行者是引擎,端写 `killed` 是一句它没证实过的断言 —— 必须 `POST …/stop` 拿到 200
|
|
13
13
|
* 才翻;409 `stop.not_landed` / `stop.not_local` / `stop.parked` 一律保持原状(引擎里
|
|
14
|
-
* 可能还在跑),下一拍由行帧/`stopped-by` 归因 settle(
|
|
14
|
+
* 可能还在跑),下一拍由行帧/`stopped-by` 归因 settle([1754]③)。
|
|
15
15
|
* false ⇒ 行跑在本进程(CC 逐字形态),`abortController.abort()` 就是执行本身,端写 `killed`
|
|
16
16
|
* 按构造恒真 ⇒ 同步翻,与 CC 2.1.220 `UPd`(pretty220.js:507299)一字不差。
|
|
17
17
|
*/
|
|
@@ -45,7 +45,7 @@ export function engineTaskHandlesCapable() {
|
|
|
45
45
|
*
|
|
46
46
|
* true ⇒ 行的执行者是引擎,端写 `killed` 是一句它没证实过的断言 —— 必须 `POST …/stop` 拿到 200
|
|
47
47
|
* 才翻;409 `stop.not_landed` / `stop.not_local` / `stop.parked` 一律保持原状(引擎里
|
|
48
|
-
* 可能还在跑),下一拍由行帧/`stopped-by` 归因 settle(
|
|
48
|
+
* 可能还在跑),下一拍由行帧/`stopped-by` 归因 settle([1754]③)。
|
|
49
49
|
* false ⇒ 行跑在本进程(CC 逐字形态),`abortController.abort()` 就是执行本身,端写 `killed`
|
|
50
50
|
* 按构造恒真 ⇒ 同步翻,与 CC 2.1.220 `UPd`(pretty220.js:507299)一字不差。
|
|
51
51
|
*/
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
*
|
|
22
22
|
* 读面游标语义([1501]§一 + [1505] must-fix 修正,UI 必须按此做):是否「读即消费」取决于句柄
|
|
23
23
|
* 形态——spooled 腿全量可重读、GET 幂等;cursor-only 腿每次 GET 只出新字节、读走就没了。
|
|
24
|
-
* 两形判别用 **wire 契约自带标记**(server [1505] 钉版承诺稳定,变更走 CHANGELOG
|
|
24
|
+
* 两形判别用 **wire 契约自带标记**(server [1505] 钉版承诺稳定,变更走 CHANGELOG+协作板;core
|
|
25
25
|
* CC-verbatim 固定形):content 含 `--- stdout (full, re-readable) ---` = spool 全量形 → 整体
|
|
26
26
|
* 替换;含 `--- new stdout ---` = cursor 增量形 → append。初版的「前缀延展」启发式被 [1505]
|
|
27
27
|
* 否决——spool content 首行 `status: <displayStatus>` 在任务完成时刻从 running 翻 exited,
|
package/dist/toolResult.d.ts
CHANGED
|
@@ -44,7 +44,7 @@ export declare const PROTOCOL_MARKERS: {
|
|
|
44
44
|
* [1505] spool 标记判别(REF-CC-域词表-06 提单源):判「读游标该整体替换还是追加」这一件事,
|
|
45
45
|
* 唯一真源在此——`engineTaskHandleWire.ts` 的 `mergeTaskOutput` 消费它,此前是各写一份
|
|
46
46
|
* `.includes()` 的独立判读,现在改成两处调用同一个函数,不再靠两份手抄字面量碰巧对齐。
|
|
47
|
-
* ⚠️ 措辞收窄(opus
|
|
47
|
+
* ⚠️ 措辞收窄(opus/对抗复审,回炉车):本函数**不**是"表里任何 stdout/stderr 分隔行判读的
|
|
48
48
|
* 单源"——`parseModelFacingTaskOutput` 里的 `taskOutputStdoutLine` 是解**另一件事**(T13
|
|
49
49
|
* TaskOutput 模型面正文里 stdout 段的边界在哪),两者字面量近似但语义不同、输入来源也不同
|
|
50
50
|
* (读游标累积 vs 单次模型面文本反解),存在能让两者给出不同答案的输入(如带前导垃圾字节的
|
|
@@ -69,12 +69,12 @@ export declare function stripUntrustedFence(text: string): {
|
|
|
69
69
|
/**
|
|
70
70
|
* T13 回落解析结果(REF-CC-TYPESHAPE-14:命名 discriminated union —— 此前是 4 成员内联匿名形,
|
|
71
71
|
* 三个构造点各自手写、`'unknown'` 分支「没有 output」原来只是注释里的一句话,现在类型强制)。
|
|
72
|
-
* 🔴 抽 DU **不改运行时形**(
|
|
72
|
+
* 🔴 抽 DU **不改运行时形**(二次回炉,复审 #4):`taskId`/`status` 缺值时**键照样在、值是
|
|
73
73
|
* `undefined`**(与 main 逐字节一致)——本函数是 npm 公面导出,`Object.keys()` / `'taskId' in r` /
|
|
74
74
|
* JSON 序列化都是下游看得见的契约,类型重构无权改它。eopt 收官(E-seat 卡裁定):「公面键恒在」
|
|
75
75
|
* 形不许被本批翻回条件展开——三键改 `| undefined` 显式并集,继续如实描述「键恒在、值可能 undefined」
|
|
76
76
|
* 这个已裁定的公面契约(不是收窄成条件展开,那会静默改变 `Object.keys()` 的下游可见形)。
|
|
77
|
-
* 常驻钉见 `run-client-core-pure-test.mjs` ⑪ 段「公面形(
|
|
77
|
+
* 常驻钉见 `run-client-core-pure-test.mjs` ⑪ 段「公面形(复审 #4 回卷钉)」三条。
|
|
78
78
|
*/
|
|
79
79
|
export type ModelFacingTaskOutput = {
|
|
80
80
|
kind: 'bash';
|
package/dist/toolResult.js
CHANGED
|
@@ -170,7 +170,7 @@ export const PROTOCOL_MARKERS = {
|
|
|
170
170
|
* [1505] spool 标记判别(REF-CC-域词表-06 提单源):判「读游标该整体替换还是追加」这一件事,
|
|
171
171
|
* 唯一真源在此——`engineTaskHandleWire.ts` 的 `mergeTaskOutput` 消费它,此前是各写一份
|
|
172
172
|
* `.includes()` 的独立判读,现在改成两处调用同一个函数,不再靠两份手抄字面量碰巧对齐。
|
|
173
|
-
* ⚠️ 措辞收窄(opus
|
|
173
|
+
* ⚠️ 措辞收窄(opus/对抗复审,回炉车):本函数**不**是"表里任何 stdout/stderr 分隔行判读的
|
|
174
174
|
* 单源"——`parseModelFacingTaskOutput` 里的 `taskOutputStdoutLine` 是解**另一件事**(T13
|
|
175
175
|
* TaskOutput 模型面正文里 stdout 段的边界在哪),两者字面量近似但语义不同、输入来源也不同
|
|
176
176
|
* (读游标累积 vs 单次模型面文本反解),存在能让两者给出不同答案的输入(如带前导垃圾字节的
|
package/dist/workflow.d.ts
CHANGED
|
@@ -24,9 +24,9 @@
|
|
|
24
24
|
export declare function rowIdTail(id: string): string;
|
|
25
25
|
/** core 1.356 BCE 合成 workflow-agent id 形:wa+16hex(判据①)。
|
|
26
26
|
* 真实 fleet 子行 id 是 `${runId} ${engineTaskId}` 复合形——必须取空白分隔尾段再匹配
|
|
27
|
-
* (cli footerRowBelt
|
|
27
|
+
* (cli footerRowBelt 原版语义;对抗复审抓的等价性破坏,0.1.1 修)。
|
|
28
28
|
* upstreamBridge 的 task_progress 前台 lane 门在 wire 无 workflowRunId 时(server <a76bd77,
|
|
29
|
-
*
|
|
29
|
+
* [1619]:1.272.0 投影白名单仍剥该键)以此为次级判别——与 belt 双判据同模板。 */
|
|
30
30
|
export declare function isWorkflowAgentTaskId(taskId: string): boolean;
|
|
31
31
|
export declare function recordWorkflowAgentTaskId(taskId: string): void;
|
|
32
32
|
export declare function isKnownWorkflowAgentTaskId(taskId: string): boolean;
|
package/dist/workflow.js
CHANGED
|
@@ -26,9 +26,9 @@ export function rowIdTail(id) {
|
|
|
26
26
|
}
|
|
27
27
|
/** core 1.356 BCE 合成 workflow-agent id 形:wa+16hex(判据①)。
|
|
28
28
|
* 真实 fleet 子行 id 是 `${runId} ${engineTaskId}` 复合形——必须取空白分隔尾段再匹配
|
|
29
|
-
* (cli footerRowBelt
|
|
29
|
+
* (cli footerRowBelt 原版语义;对抗复审抓的等价性破坏,0.1.1 修)。
|
|
30
30
|
* upstreamBridge 的 task_progress 前台 lane 门在 wire 无 workflowRunId 时(server <a76bd77,
|
|
31
|
-
*
|
|
31
|
+
* [1619]:1.272.0 投影白名单仍剥该键)以此为次级判别——与 belt 双判据同模板。 */
|
|
32
32
|
export function isWorkflowAgentTaskId(taskId) {
|
|
33
33
|
return /^wa[0-9a-f]{16}$/.test(rowIdTail(taskId));
|
|
34
34
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@sema-agent/client-core",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.24.0",
|
|
4
4
|
"description": "Client-side session runtime shared by every sema human client (TUI / web / desktop): sema wire frames (AgentEvent) -> CC session vocabulary (SDKMessage) with dual-plane output (transcript/chrome), deterministic transcript ids, lane discipline as a type, and the notification/dedup ledgers. Every CC-skin shape is collected here so the wire itself stays neutral. Blackboard [1832] design axioms; [1651]/[1652]/[1653] signed seam design. Renamed from @sema-agent/wire-cc-adapter (0.1.x).",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
@@ -28,12 +28,12 @@
|
|
|
28
28
|
},
|
|
29
29
|
"peerDependencies": {
|
|
30
30
|
"@sema-agent/agent-types": ">=0.2.0",
|
|
31
|
-
"@sema-agent/sdk": ">=6.
|
|
31
|
+
"@sema-agent/sdk": ">=6.11.0"
|
|
32
32
|
},
|
|
33
33
|
"devDependencies": {
|
|
34
34
|
"@sema-agent/agent-types": "^0.2.0",
|
|
35
35
|
"@sema-agent/core": "^5.20.0",
|
|
36
|
-
"@sema-agent/sdk": "^6.
|
|
36
|
+
"@sema-agent/sdk": "^6.11.0",
|
|
37
37
|
"esbuild": "^0.27.4",
|
|
38
38
|
"typescript": "^6.0.2"
|
|
39
39
|
}
|