claude-code-acp-ts 0.99.2 → 0.99.3
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/dist/context-compaction.d.ts +6 -4
- package/dist/context-compaction.d.ts.map +1 -1
- package/dist/context-compaction.js +22 -11
- package/dist/tool-calls/reporters/compaction.d.ts +10 -0
- package/dist/tool-calls/reporters/compaction.d.ts.map +1 -1
- package/dist/tool-calls/reporters/compaction.js +52 -0
- package/package.json +1 -1
|
@@ -70,10 +70,12 @@ export declare class ContextCompactionLifecycle {
|
|
|
70
70
|
*
|
|
71
71
|
* A `compaction_update` entity still `in_progress` here never received its
|
|
72
72
|
* terminal signal from the runtime and gets its one terminal status,
|
|
73
|
-
* `cancelled`. The legacy tool call
|
|
74
|
-
*
|
|
75
|
-
*
|
|
76
|
-
*
|
|
73
|
+
* `cancelled`. The legacy tool call has no `cancelled` status in ACP v1, so
|
|
74
|
+
* it is settled as `completed` with the outcome in `content` instead of
|
|
75
|
+
* being left `in_progress`: a client that counts unclosed tool calls would
|
|
76
|
+
* otherwise resend it after the turn, out of its original position. Never
|
|
77
|
+
* throws — a failed send is logged, so callers can settle the turn
|
|
78
|
+
* unconditionally.
|
|
77
79
|
*/
|
|
78
80
|
reset(): Promise<void>;
|
|
79
81
|
/** Abandon the current work before settling its prompt or tearing down the
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context-compaction.d.ts","sourceRoot":"","sources":["../src/context-compaction.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,kBAAkB,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AAC5F,OAAO,EACL,yBAAyB,EAE1B,MAAM,8BAA8B,CAAC;AAGtC,KAAK,gBAAgB,GAAG,WAAW,GAAG,QAAQ,CAAC;AAG/C;;;;;;;;GAQG;AACH,MAAM,MAAM,sBAAsB,GAAG,WAAW,GAAG,mBAAmB,CAAC;AAevE,KAAK,UAAU,GAAG,CAAC,YAAY,EAAE,mBAAmB,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;AAEvE,MAAM,MAAM,iCAAiC,GAAG;IAC9C,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,CAAC,EAAE,sBAAsB,CAAC;IACtC;gCAC4B;IAC5B,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,KAAK,IAAI,CAAC;IACrD,0FAA0F;IAC1F,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB,CAAC;AAEF,wBAAgB,+BAA+B,CAAC,YAAY,CAAC,EAAE,kBAAkB,GAAG,IAAI,GAAG,OAAO,CAGjG;AAyBD;;;;;;;;;GASG;AACH,wBAAgB,qBAAqB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAkBrE;AAoBD;6EAC6E;AAC7E,wBAAgB,uBAAuB,CAAC,OAAO,EAAE,OAAO,GAAG,OAAO,CAOjE;AAED;;;;;;;GAOG;AACH,qBAAa,0BAA0B;IAoBnC,OAAO,CAAC,QAAQ,CAAC,UAAU;IAnB7B,OAAO,CAAC,gBAAgB,CAA8B;IACtD,OAAO,CAAC,eAAe,CAAS;IAChC,OAAO,CAAC,oBAAoB,CAAqB;IACjD;;iEAE6D;IAC7D,OAAO,CAAC,WAAW,CAAS;IAC5B;;;;kDAI8C;IAC9C,OAAO,CAAC,cAAc,CAAqB;IAC3C,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;IACnC,QAAQ,CAAC,YAAY,EAAE,sBAAsB,CAAC;IAC9C,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAA4C;IACrE,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAU;gBAGjB,UAAU,EAAE,UAAU,EACvC,OAAO,EAAE,iCAAiC;IAQ5C,IAAI,kBAAkB,IAAI,OAAO,CAEhC;IAED
|
|
1
|
+
{"version":3,"file":"context-compaction.d.ts","sourceRoot":"","sources":["../src/context-compaction.ts"],"names":[],"mappings":"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"}
|
|
@@ -123,24 +123,30 @@ export class ContextCompactionLifecycle {
|
|
|
123
123
|
*
|
|
124
124
|
* A `compaction_update` entity still `in_progress` here never received its
|
|
125
125
|
* terminal signal from the runtime and gets its one terminal status,
|
|
126
|
-
* `cancelled`. The legacy tool call
|
|
127
|
-
*
|
|
128
|
-
*
|
|
129
|
-
*
|
|
126
|
+
* `cancelled`. The legacy tool call has no `cancelled` status in ACP v1, so
|
|
127
|
+
* it is settled as `completed` with the outcome in `content` instead of
|
|
128
|
+
* being left `in_progress`: a client that counts unclosed tool calls would
|
|
129
|
+
* otherwise resend it after the turn, out of its original position. Never
|
|
130
|
+
* throws — a failed send is logged, so callers can settle the turn
|
|
131
|
+
* unconditionally.
|
|
130
132
|
*/
|
|
131
133
|
async reset() {
|
|
132
134
|
const state = this.activeCompaction;
|
|
133
135
|
this.activeCompaction = undefined;
|
|
134
136
|
this.outputDelivered = false;
|
|
135
137
|
this.duplicateErrorOutput = undefined;
|
|
136
|
-
if (!state || state.terminalStatus
|
|
138
|
+
if (!state || state.terminalStatus)
|
|
137
139
|
return;
|
|
138
140
|
state.terminalStatus = "cancelled";
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
141
|
+
if (this.presentation === "compaction_update") {
|
|
142
|
+
await this.sendQuietly({
|
|
143
|
+
sessionUpdate: "compaction_update",
|
|
144
|
+
compactionId: state.compactionId,
|
|
145
|
+
status: "cancelled",
|
|
146
|
+
}, "cancelled compaction");
|
|
147
|
+
return;
|
|
148
|
+
}
|
|
149
|
+
await this.sendQuietly(compactionToolCall.settled(state.compactionId, undefined, this.airClient), "settled compaction");
|
|
144
150
|
}
|
|
145
151
|
/** Abandon the current work before settling its prompt or tearing down the
|
|
146
152
|
* stream. Unlike a normal result boundary, its pending hooks are not safe
|
|
@@ -296,7 +302,12 @@ export class ContextCompactionLifecycle {
|
|
|
296
302
|
});
|
|
297
303
|
return;
|
|
298
304
|
}
|
|
299
|
-
await this.send(compactionToolCall.finished(state.compactionId,
|
|
305
|
+
await this.send(compactionToolCall.finished(state.compactionId,
|
|
306
|
+
// A status-less update is a patch for clients that merge, but a client
|
|
307
|
+
// that replaces the whole call reads it as "no longer terminal" and
|
|
308
|
+
// leaves the call running. Repeating the terminal status on the
|
|
309
|
+
// enriching update is idempotent for both.
|
|
310
|
+
opened || firstTerminal || enrichTerminal ? status : undefined, metadata, opened, this.airClient));
|
|
300
311
|
}
|
|
301
312
|
/** Make `compactionId` the active entity, moving a pending hook summary onto
|
|
302
313
|
* it, and mark compaction output as delivered for the owning turn. */
|
|
@@ -17,6 +17,16 @@ type ToolCallUpdate = SessionNotification["update"];
|
|
|
17
17
|
export declare const compactionToolCall: {
|
|
18
18
|
started(compactionId: string, airClient?: boolean): ToolCallUpdate;
|
|
19
19
|
inProgress(compactionId: string, airClient?: boolean): ToolCallUpdate;
|
|
20
|
+
/**
|
|
21
|
+
* Settle a compaction that was abandoned at a turn boundary, so the call
|
|
22
|
+
* does not stay `in_progress` forever.
|
|
23
|
+
*
|
|
24
|
+
* ACP v1's `ToolCallStatus` has no `cancelled` value, so this closes as
|
|
25
|
+
* `completed` and says what actually happened in `content`. Clients that
|
|
26
|
+
* treat a call without a terminal status as unclosed would otherwise resend
|
|
27
|
+
* it later, out of order.
|
|
28
|
+
*/
|
|
29
|
+
settled(compactionId: string, note?: string, airClient?: boolean): ToolCallUpdate;
|
|
20
30
|
/** The terminal report. A missed opening makes it the first report, a `tool_call`. */
|
|
21
31
|
finished(compactionId: string, status: "completed" | "failed" | undefined, facts: CompactionFacts, first: boolean, airClient?: boolean): ToolCallUpdate;
|
|
22
32
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"compaction.d.ts","sourceRoot":"","sources":["../../../src/tool-calls/reporters/compaction.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AAC7E,OAAO,EACL,KAAK,yBAAyB,EAE/B,MAAM,kCAAkC,CAAC;AAG1C,KAAK,eAAe,GAAG,IAAI,CAAC,yBAAyB,EAAE,SAAS,CAAC,CAAC;AAClE,KAAK,cAAc,GAAG,mBAAmB,CAAC,QAAQ,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"compaction.d.ts","sourceRoot":"","sources":["../../../src/tool-calls/reporters/compaction.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AAC7E,OAAO,EACL,KAAK,yBAAyB,EAE/B,MAAM,kCAAkC,CAAC;AAG1C,KAAK,eAAe,GAAG,IAAI,CAAC,yBAAyB,EAAE,SAAS,CAAC,CAAC;AAClE,KAAK,cAAc,GAAG,mBAAmB,CAAC,QAAQ,CAAC,CAAC;AAgCpD;;;;;;;;;;;GAWG;AACH,eAAO,MAAM,kBAAkB;0BACP,MAAM,wBAAsB,cAAc;6BAWvC,MAAM,wBAAsB,cAAc;IASnE;;;;;;;;OAQG;0BACmB,MAAM,uCAA2C,cAAc;IAUrF,sFAAsF;2BAEtE,MAAM,UACZ,WAAW,GAAG,QAAQ,GAAG,SAAS,SACnC,eAAe,SACf,OAAO,wBAEb,cAAc;CAqClB,CAAC"}
|
|
@@ -1,6 +1,31 @@
|
|
|
1
1
|
import { createContextCompactionMeta, } from "../../context-compaction-meta.js";
|
|
2
2
|
import { textContent } from "../content.js";
|
|
3
3
|
const TITLE = "Compact conversation";
|
|
4
|
+
/** The note a settled (never finished) compaction carries as its result. */
|
|
5
|
+
const SETTLED_NOTE = "Context compaction was cancelled before it finished; the conversation was not summarized.";
|
|
6
|
+
/** The human-readable result of a compaction, for clients that show `content`. */
|
|
7
|
+
function factsText(facts) {
|
|
8
|
+
// Widened to `string`: upstream added the `idle` trigger after this release,
|
|
9
|
+
// and a comparison against it must not be a type error here or after the
|
|
10
|
+
// next rebase.
|
|
11
|
+
const trigger = facts.trigger;
|
|
12
|
+
const what = trigger === "idle"
|
|
13
|
+
? "Context compacted while idle"
|
|
14
|
+
: trigger === "manual"
|
|
15
|
+
? "Context compacted on request"
|
|
16
|
+
: "Context compacted";
|
|
17
|
+
const details = [];
|
|
18
|
+
if (typeof facts.preTokens === "number" && typeof facts.postTokens === "number") {
|
|
19
|
+
details.push(`${facts.preTokens} -> ${facts.postTokens} tokens`);
|
|
20
|
+
}
|
|
21
|
+
else if (typeof facts.postTokens === "number") {
|
|
22
|
+
details.push(`${facts.postTokens} tokens after compaction`);
|
|
23
|
+
}
|
|
24
|
+
if (typeof facts.durationMs === "number") {
|
|
25
|
+
details.push(`${(facts.durationMs / 1000).toFixed(1)}s`);
|
|
26
|
+
}
|
|
27
|
+
return details.length > 0 ? `${what}: ${details.join(", ")}` : what;
|
|
28
|
+
}
|
|
4
29
|
/**
|
|
5
30
|
* The synthetic "Compact conversation" tool call, for a client without the
|
|
6
31
|
* ACP compaction updates.
|
|
@@ -32,11 +57,36 @@ export const compactionToolCall = {
|
|
|
32
57
|
_meta: meta({}, airClient),
|
|
33
58
|
};
|
|
34
59
|
},
|
|
60
|
+
/**
|
|
61
|
+
* Settle a compaction that was abandoned at a turn boundary, so the call
|
|
62
|
+
* does not stay `in_progress` forever.
|
|
63
|
+
*
|
|
64
|
+
* ACP v1's `ToolCallStatus` has no `cancelled` value, so this closes as
|
|
65
|
+
* `completed` and says what actually happened in `content`. Clients that
|
|
66
|
+
* treat a call without a terminal status as unclosed would otherwise resend
|
|
67
|
+
* it later, out of order.
|
|
68
|
+
*/
|
|
69
|
+
settled(compactionId, note = SETTLED_NOTE, airClient = false) {
|
|
70
|
+
return {
|
|
71
|
+
sessionUpdate: "tool_call_update",
|
|
72
|
+
toolCallId: compactionId,
|
|
73
|
+
status: "completed",
|
|
74
|
+
content: [textContent(note)],
|
|
75
|
+
_meta: meta({}, airClient),
|
|
76
|
+
};
|
|
77
|
+
},
|
|
35
78
|
/** The terminal report. A missed opening makes it the first report, a `tool_call`. */
|
|
36
79
|
finished(compactionId, status, facts, first, airClient = false) {
|
|
37
80
|
const errorContent = status === "failed" && facts.error
|
|
38
81
|
? { content: [textContent(`Compaction failed: ${facts.error}`)] }
|
|
39
82
|
: {};
|
|
83
|
+
// A client that renders `content` needs something to expand; `rawOutput`
|
|
84
|
+
// alone is opaque. The error, when there is one, is the result instead.
|
|
85
|
+
// AIR reads every fact from `_meta.jetbrains.air.contextCompaction`, so it
|
|
86
|
+
// gets no `content`: the docs ask for each fact once.
|
|
87
|
+
const factsContent = airClient || "content" in errorContent || Object.keys(facts).length === 0
|
|
88
|
+
? {}
|
|
89
|
+
: { content: [textContent(factsText(facts))] };
|
|
40
90
|
const rawOutput = !airClient && Object.keys(facts).length > 0 ? { rawOutput: facts } : {};
|
|
41
91
|
if (first) {
|
|
42
92
|
return {
|
|
@@ -46,6 +96,7 @@ export const compactionToolCall = {
|
|
|
46
96
|
kind: "think",
|
|
47
97
|
status: status ?? "completed",
|
|
48
98
|
...errorContent,
|
|
99
|
+
...factsContent,
|
|
49
100
|
...rawOutput,
|
|
50
101
|
_meta: meta(facts, airClient),
|
|
51
102
|
};
|
|
@@ -55,6 +106,7 @@ export const compactionToolCall = {
|
|
|
55
106
|
toolCallId: compactionId,
|
|
56
107
|
...(status ? { status } : {}),
|
|
57
108
|
...errorContent,
|
|
109
|
+
...factsContent,
|
|
58
110
|
...rawOutput,
|
|
59
111
|
_meta: meta(facts, airClient),
|
|
60
112
|
};
|
package/package.json
CHANGED