@acontext/acontext 0.1.5 → 0.1.7
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/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/integrations/claude-agent.d.ts +124 -0
- package/dist/integrations/claude-agent.js +371 -0
- package/dist/integrations/index.d.ts +4 -0
- package/dist/integrations/index.js +20 -0
- package/dist/resources/sessions.d.ts +69 -0
- package/dist/resources/sessions.js +84 -0
- package/dist/types/session.d.ts +7 -0
- package/dist/types/session.js +12 -0
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -33,3 +33,4 @@ Object.defineProperty(exports, "AcontextError", { enumerable: true, get: functio
|
|
|
33
33
|
__exportStar(require("./types"), exports);
|
|
34
34
|
__exportStar(require("./resources"), exports);
|
|
35
35
|
__exportStar(require("./agent"), exports);
|
|
36
|
+
__exportStar(require("./integrations"), exports);
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Claude Agent SDK integration for Acontext.
|
|
3
|
+
*
|
|
4
|
+
* Provides {@link ClaudeAgentStorage} that accepts messages produced by the
|
|
5
|
+
* Claude Agent SDK `query()` async iterable and persists **only** user and
|
|
6
|
+
* assistant messages to Acontext in Anthropic format via
|
|
7
|
+
* `client.sessions.storeMessage(...)`.
|
|
8
|
+
*
|
|
9
|
+
* Other message types (system, result, stream_event, etc.) are used only for
|
|
10
|
+
* session-id resolution and are **never** stored.
|
|
11
|
+
*
|
|
12
|
+
* Usage:
|
|
13
|
+
* ```typescript
|
|
14
|
+
* import { AcontextClient, ClaudeAgentStorage } from '@acontext/acontext';
|
|
15
|
+
* import { query } from '@anthropic-ai/claude-agent-sdk';
|
|
16
|
+
*
|
|
17
|
+
* const client = new AcontextClient({ apiKey: 'sk-ac-your-api-key' });
|
|
18
|
+
* const storage = new ClaudeAgentStorage({ client });
|
|
19
|
+
*
|
|
20
|
+
* for await (const message of query({ prompt: 'Hello' })) {
|
|
21
|
+
* await storage.saveMessage(message);
|
|
22
|
+
* }
|
|
23
|
+
* ```
|
|
24
|
+
*/
|
|
25
|
+
/**
|
|
26
|
+
* Minimal duck-typed interface for the Acontext client.
|
|
27
|
+
* Both `AcontextClient` and `MockAcontextClient` satisfy this interface.
|
|
28
|
+
*/
|
|
29
|
+
export interface AcontextClientLike {
|
|
30
|
+
sessions: {
|
|
31
|
+
create(options?: {
|
|
32
|
+
useUuid?: string | null;
|
|
33
|
+
user?: string | null;
|
|
34
|
+
}): Promise<{
|
|
35
|
+
id: string;
|
|
36
|
+
}>;
|
|
37
|
+
storeMessage(sessionId: string, blob: Record<string, unknown>, options?: {
|
|
38
|
+
format?: string;
|
|
39
|
+
meta?: Record<string, unknown> | null;
|
|
40
|
+
}): Promise<unknown>;
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Options for constructing a {@link ClaudeAgentStorage} instance.
|
|
45
|
+
*/
|
|
46
|
+
export interface ClaudeAgentStorageOptions {
|
|
47
|
+
/** An Acontext client instance (or any object satisfying `AcontextClientLike`). */
|
|
48
|
+
client: AcontextClientLike;
|
|
49
|
+
/** Acontext session UUID. If omitted, discovered from the Claude stream or auto-created. */
|
|
50
|
+
sessionId?: string;
|
|
51
|
+
/** Optional user identifier passed to `sessions.create()`. */
|
|
52
|
+
user?: string;
|
|
53
|
+
/** Whether to store ThinkingBlock content as text blocks. Default: false. */
|
|
54
|
+
includeThinking?: boolean;
|
|
55
|
+
/**
|
|
56
|
+
* Optional error callback invoked when `storeMessage` raises.
|
|
57
|
+
* Receives `(error, blob)` where `blob` is the **converted** Anthropic blob.
|
|
58
|
+
* If not provided, errors are logged via `console.warn`.
|
|
59
|
+
*/
|
|
60
|
+
onError?: (error: Error, blob: Record<string, unknown>) => void;
|
|
61
|
+
}
|
|
62
|
+
/**
|
|
63
|
+
* Try to extract a Claude session id from a non-storable message.
|
|
64
|
+
*
|
|
65
|
+
* In the TS Claude Agent SDK, `session_id` is a flat field on system,
|
|
66
|
+
* result, stream_event, and other non-storable message types.
|
|
67
|
+
*
|
|
68
|
+
* Returns `null` when the message does not carry a session id.
|
|
69
|
+
*/
|
|
70
|
+
export declare function getSessionIdFromMessage(msg: Record<string, unknown>): string | null;
|
|
71
|
+
/**
|
|
72
|
+
* Convert a Claude Agent SDK user message to an Anthropic blob.
|
|
73
|
+
*
|
|
74
|
+
* TS reads `msg.message?.content ?? ""` (nested under API message object).
|
|
75
|
+
*
|
|
76
|
+
* Returns `null` when the resulting content would be empty (no storable blocks).
|
|
77
|
+
*/
|
|
78
|
+
export declare function claudeUserMessageToAnthropicBlob(msg: Record<string, unknown>): Record<string, unknown> | null;
|
|
79
|
+
/**
|
|
80
|
+
* Convert a Claude Agent SDK assistant message to an Anthropic blob.
|
|
81
|
+
*
|
|
82
|
+
* TS reads `msg.message?.content ?? []` (nested under API message object).
|
|
83
|
+
*
|
|
84
|
+
* Returns `{ blob: ... | null, hasThinking: boolean }`.
|
|
85
|
+
*/
|
|
86
|
+
export declare function claudeAssistantMessageToAnthropicBlob(msg: Record<string, unknown>, includeThinking?: boolean): {
|
|
87
|
+
blob: Record<string, unknown> | null;
|
|
88
|
+
hasThinking: boolean;
|
|
89
|
+
};
|
|
90
|
+
/**
|
|
91
|
+
* Storage adapter for the Claude Agent SDK (TypeScript).
|
|
92
|
+
*
|
|
93
|
+
* Accepts messages from the `query()` async iterable and persists **only**
|
|
94
|
+
* user and assistant messages to Acontext in Anthropic format.
|
|
95
|
+
*/
|
|
96
|
+
export declare class ClaudeAgentStorage {
|
|
97
|
+
private _client;
|
|
98
|
+
private _sessionId;
|
|
99
|
+
private _user;
|
|
100
|
+
private _includeThinking;
|
|
101
|
+
private _onError;
|
|
102
|
+
private _sessionEnsured;
|
|
103
|
+
constructor(options: ClaudeAgentStorageOptions);
|
|
104
|
+
/**
|
|
105
|
+
* The current Acontext session id (may be `null` until resolved).
|
|
106
|
+
*/
|
|
107
|
+
get sessionId(): string | null;
|
|
108
|
+
/**
|
|
109
|
+
* Persist a single Claude Agent SDK message to Acontext.
|
|
110
|
+
*
|
|
111
|
+
* - User and assistant messages are stored.
|
|
112
|
+
* - All other message types (system, result, stream_event, etc.) are used
|
|
113
|
+
* only for session-id resolution and are **not** stored.
|
|
114
|
+
* - Replay messages (`isReplay: true`) are skipped to prevent duplicates.
|
|
115
|
+
* - API errors are caught and either forwarded to `onError` or logged,
|
|
116
|
+
* so the caller's `for await` loop is never interrupted.
|
|
117
|
+
*/
|
|
118
|
+
saveMessage(msg: Record<string, unknown>): Promise<void>;
|
|
119
|
+
private _tryUpdateSessionId;
|
|
120
|
+
private _storeUser;
|
|
121
|
+
private _storeAssistant;
|
|
122
|
+
private _ensureSession;
|
|
123
|
+
private _callStore;
|
|
124
|
+
}
|
|
@@ -0,0 +1,371 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Claude Agent SDK integration for Acontext.
|
|
4
|
+
*
|
|
5
|
+
* Provides {@link ClaudeAgentStorage} that accepts messages produced by the
|
|
6
|
+
* Claude Agent SDK `query()` async iterable and persists **only** user and
|
|
7
|
+
* assistant messages to Acontext in Anthropic format via
|
|
8
|
+
* `client.sessions.storeMessage(...)`.
|
|
9
|
+
*
|
|
10
|
+
* Other message types (system, result, stream_event, etc.) are used only for
|
|
11
|
+
* session-id resolution and are **never** stored.
|
|
12
|
+
*
|
|
13
|
+
* Usage:
|
|
14
|
+
* ```typescript
|
|
15
|
+
* import { AcontextClient, ClaudeAgentStorage } from '@acontext/acontext';
|
|
16
|
+
* import { query } from '@anthropic-ai/claude-agent-sdk';
|
|
17
|
+
*
|
|
18
|
+
* const client = new AcontextClient({ apiKey: 'sk-ac-your-api-key' });
|
|
19
|
+
* const storage = new ClaudeAgentStorage({ client });
|
|
20
|
+
*
|
|
21
|
+
* for await (const message of query({ prompt: 'Hello' })) {
|
|
22
|
+
* await storage.saveMessage(message);
|
|
23
|
+
* }
|
|
24
|
+
* ```
|
|
25
|
+
*/
|
|
26
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
27
|
+
exports.ClaudeAgentStorage = void 0;
|
|
28
|
+
exports.getSessionIdFromMessage = getSessionIdFromMessage;
|
|
29
|
+
exports.claudeUserMessageToAnthropicBlob = claudeUserMessageToAnthropicBlob;
|
|
30
|
+
exports.claudeAssistantMessageToAnthropicBlob = claudeAssistantMessageToAnthropicBlob;
|
|
31
|
+
const errors_1 = require("../errors");
|
|
32
|
+
// ---------------------------------------------------------------------------
|
|
33
|
+
// Helpers – message type detection (TS Claude Agent SDK uses `type` field)
|
|
34
|
+
// ---------------------------------------------------------------------------
|
|
35
|
+
/**
|
|
36
|
+
* Check if a message is a storable user message.
|
|
37
|
+
* Skips replay messages (`isReplay === true`) which are TS-only.
|
|
38
|
+
*/
|
|
39
|
+
function isUserMessage(msg) {
|
|
40
|
+
return msg.type === 'user' && !msg.isReplay;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Check if a message is a storable assistant message.
|
|
44
|
+
*/
|
|
45
|
+
function isAssistantMessage(msg) {
|
|
46
|
+
return msg.type === 'assistant';
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Check if a message is a replay user message (TS-only).
|
|
50
|
+
*/
|
|
51
|
+
function isReplayMessage(msg) {
|
|
52
|
+
return msg.type === 'user' && msg.isReplay === true;
|
|
53
|
+
}
|
|
54
|
+
// ---------------------------------------------------------------------------
|
|
55
|
+
// Helpers – session id extraction
|
|
56
|
+
// ---------------------------------------------------------------------------
|
|
57
|
+
/**
|
|
58
|
+
* Try to extract a Claude session id from a non-storable message.
|
|
59
|
+
*
|
|
60
|
+
* In the TS Claude Agent SDK, `session_id` is a flat field on system,
|
|
61
|
+
* result, stream_event, and other non-storable message types.
|
|
62
|
+
*
|
|
63
|
+
* Returns `null` when the message does not carry a session id.
|
|
64
|
+
*/
|
|
65
|
+
function getSessionIdFromMessage(msg) {
|
|
66
|
+
// Only extract from non-storable messages
|
|
67
|
+
if (msg.type === 'user' || msg.type === 'assistant') {
|
|
68
|
+
return null;
|
|
69
|
+
}
|
|
70
|
+
const sid = msg.session_id;
|
|
71
|
+
return typeof sid === 'string' ? sid : null;
|
|
72
|
+
}
|
|
73
|
+
// ---------------------------------------------------------------------------
|
|
74
|
+
// Helpers – block conversion (Claude SDK → Anthropic blob)
|
|
75
|
+
// ---------------------------------------------------------------------------
|
|
76
|
+
/**
|
|
77
|
+
* Normalize `ToolResultBlock.content` to a shape accepted by the API.
|
|
78
|
+
*
|
|
79
|
+
* - `null`/`undefined` → `""`
|
|
80
|
+
* - `string` → as-is
|
|
81
|
+
* - `array` → `[{ type: "text", text: item.text ?? "" }]`
|
|
82
|
+
* - other → `String(content)`
|
|
83
|
+
*/
|
|
84
|
+
function normalizeToolResultContent(content) {
|
|
85
|
+
if (content === null || content === undefined) {
|
|
86
|
+
return '';
|
|
87
|
+
}
|
|
88
|
+
if (typeof content === 'string') {
|
|
89
|
+
return content;
|
|
90
|
+
}
|
|
91
|
+
if (Array.isArray(content)) {
|
|
92
|
+
return content.map((item) => ({
|
|
93
|
+
type: 'text',
|
|
94
|
+
text: item?.text ?? '',
|
|
95
|
+
}));
|
|
96
|
+
}
|
|
97
|
+
return String(content);
|
|
98
|
+
}
|
|
99
|
+
/**
|
|
100
|
+
* Convert a single Claude SDK content block to an Anthropic content block.
|
|
101
|
+
*
|
|
102
|
+
* Returns `null` when the block should be skipped.
|
|
103
|
+
*/
|
|
104
|
+
function convertBlock(block, role, includeThinking) {
|
|
105
|
+
const blockType = block.type;
|
|
106
|
+
switch (blockType) {
|
|
107
|
+
case 'thinking': {
|
|
108
|
+
if (!includeThinking) {
|
|
109
|
+
return null;
|
|
110
|
+
}
|
|
111
|
+
const thinkingText = block.thinking;
|
|
112
|
+
if (!thinkingText) {
|
|
113
|
+
return null; // empty thinking text
|
|
114
|
+
}
|
|
115
|
+
return { type: 'text', text: thinkingText };
|
|
116
|
+
}
|
|
117
|
+
case 'tool_use': {
|
|
118
|
+
if (role !== 'assistant') {
|
|
119
|
+
return null; // tool_use only valid in assistant messages
|
|
120
|
+
}
|
|
121
|
+
let inputVal = block.input;
|
|
122
|
+
if (typeof inputVal === 'string') {
|
|
123
|
+
try {
|
|
124
|
+
inputVal = JSON.parse(inputVal);
|
|
125
|
+
}
|
|
126
|
+
catch {
|
|
127
|
+
inputVal = { raw: inputVal };
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
return {
|
|
131
|
+
type: 'tool_use',
|
|
132
|
+
id: block.id,
|
|
133
|
+
name: block.name,
|
|
134
|
+
input: inputVal,
|
|
135
|
+
};
|
|
136
|
+
}
|
|
137
|
+
case 'tool_result': {
|
|
138
|
+
if (role !== 'user') {
|
|
139
|
+
return null; // tool_result only valid in user messages
|
|
140
|
+
}
|
|
141
|
+
const result = {
|
|
142
|
+
type: 'tool_result',
|
|
143
|
+
tool_use_id: block.tool_use_id,
|
|
144
|
+
content: normalizeToolResultContent(block.content),
|
|
145
|
+
};
|
|
146
|
+
if (block.is_error) {
|
|
147
|
+
result.is_error = true;
|
|
148
|
+
}
|
|
149
|
+
return result;
|
|
150
|
+
}
|
|
151
|
+
case 'text': {
|
|
152
|
+
const text = block.text;
|
|
153
|
+
if (!text) {
|
|
154
|
+
return null; // empty text
|
|
155
|
+
}
|
|
156
|
+
return { type: 'text', text };
|
|
157
|
+
}
|
|
158
|
+
default:
|
|
159
|
+
// Unknown block type – skip silently
|
|
160
|
+
return null;
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* Convert Claude SDK content to Anthropic content block array.
|
|
165
|
+
*
|
|
166
|
+
* Returns `[blocks, hasThinking]` where `hasThinking` is `true` when at
|
|
167
|
+
* least one thinking block was successfully included in the output.
|
|
168
|
+
*/
|
|
169
|
+
function convertContentBlocks(content, role, includeThinking) {
|
|
170
|
+
let hasThinking = false;
|
|
171
|
+
if (typeof content === 'string') {
|
|
172
|
+
if (!content) {
|
|
173
|
+
return [[], false];
|
|
174
|
+
}
|
|
175
|
+
return [[{ type: 'text', text: content }], false];
|
|
176
|
+
}
|
|
177
|
+
if (!Array.isArray(content)) {
|
|
178
|
+
return [[], false];
|
|
179
|
+
}
|
|
180
|
+
const blocks = [];
|
|
181
|
+
for (const block of content) {
|
|
182
|
+
if (typeof block !== 'object' || block === null) {
|
|
183
|
+
continue; // skip non-object items (matching Python's `if not isinstance(block, dict)`)
|
|
184
|
+
}
|
|
185
|
+
const converted = convertBlock(block, role, includeThinking);
|
|
186
|
+
if (converted !== null) {
|
|
187
|
+
blocks.push(converted);
|
|
188
|
+
// Track whether a thinking block was successfully included
|
|
189
|
+
if (block.type === 'thinking' &&
|
|
190
|
+
includeThinking) {
|
|
191
|
+
hasThinking = true;
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
return [blocks, hasThinking];
|
|
196
|
+
}
|
|
197
|
+
// ---------------------------------------------------------------------------
|
|
198
|
+
// Public conversion helpers
|
|
199
|
+
// ---------------------------------------------------------------------------
|
|
200
|
+
/**
|
|
201
|
+
* Convert a Claude Agent SDK user message to an Anthropic blob.
|
|
202
|
+
*
|
|
203
|
+
* TS reads `msg.message?.content ?? ""` (nested under API message object).
|
|
204
|
+
*
|
|
205
|
+
* Returns `null` when the resulting content would be empty (no storable blocks).
|
|
206
|
+
*/
|
|
207
|
+
function claudeUserMessageToAnthropicBlob(msg) {
|
|
208
|
+
const message = msg.message;
|
|
209
|
+
const content = message?.content ?? '';
|
|
210
|
+
const [blocks] = convertContentBlocks(content, 'user', false);
|
|
211
|
+
if (blocks.length === 0) {
|
|
212
|
+
return null;
|
|
213
|
+
}
|
|
214
|
+
return { role: 'user', content: blocks };
|
|
215
|
+
}
|
|
216
|
+
/**
|
|
217
|
+
* Convert a Claude Agent SDK assistant message to an Anthropic blob.
|
|
218
|
+
*
|
|
219
|
+
* TS reads `msg.message?.content ?? []` (nested under API message object).
|
|
220
|
+
*
|
|
221
|
+
* Returns `{ blob: ... | null, hasThinking: boolean }`.
|
|
222
|
+
*/
|
|
223
|
+
function claudeAssistantMessageToAnthropicBlob(msg, includeThinking = false) {
|
|
224
|
+
const message = msg.message;
|
|
225
|
+
const content = message?.content ?? [];
|
|
226
|
+
const [blocks, hasThinking] = convertContentBlocks(content, 'assistant', includeThinking);
|
|
227
|
+
if (blocks.length === 0) {
|
|
228
|
+
return { blob: null, hasThinking };
|
|
229
|
+
}
|
|
230
|
+
return {
|
|
231
|
+
blob: { role: 'assistant', content: blocks },
|
|
232
|
+
hasThinking,
|
|
233
|
+
};
|
|
234
|
+
}
|
|
235
|
+
// ---------------------------------------------------------------------------
|
|
236
|
+
// ClaudeAgentStorage
|
|
237
|
+
// ---------------------------------------------------------------------------
|
|
238
|
+
/**
|
|
239
|
+
* Storage adapter for the Claude Agent SDK (TypeScript).
|
|
240
|
+
*
|
|
241
|
+
* Accepts messages from the `query()` async iterable and persists **only**
|
|
242
|
+
* user and assistant messages to Acontext in Anthropic format.
|
|
243
|
+
*/
|
|
244
|
+
class ClaudeAgentStorage {
|
|
245
|
+
constructor(options) {
|
|
246
|
+
this._sessionEnsured = false;
|
|
247
|
+
this._client = options.client;
|
|
248
|
+
this._sessionId = options.sessionId ?? null;
|
|
249
|
+
this._user = options.user ?? null;
|
|
250
|
+
this._includeThinking = options.includeThinking ?? false;
|
|
251
|
+
this._onError = options.onError ?? null;
|
|
252
|
+
}
|
|
253
|
+
// -- properties ----------------------------------------------------------
|
|
254
|
+
/**
|
|
255
|
+
* The current Acontext session id (may be `null` until resolved).
|
|
256
|
+
*/
|
|
257
|
+
get sessionId() {
|
|
258
|
+
return this._sessionId;
|
|
259
|
+
}
|
|
260
|
+
// -- public API ----------------------------------------------------------
|
|
261
|
+
/**
|
|
262
|
+
* Persist a single Claude Agent SDK message to Acontext.
|
|
263
|
+
*
|
|
264
|
+
* - User and assistant messages are stored.
|
|
265
|
+
* - All other message types (system, result, stream_event, etc.) are used
|
|
266
|
+
* only for session-id resolution and are **not** stored.
|
|
267
|
+
* - Replay messages (`isReplay: true`) are skipped to prevent duplicates.
|
|
268
|
+
* - API errors are caught and either forwarded to `onError` or logged,
|
|
269
|
+
* so the caller's `for await` loop is never interrupted.
|
|
270
|
+
*/
|
|
271
|
+
async saveMessage(msg) {
|
|
272
|
+
// -- non-storable message types: update session_id only ----------------
|
|
273
|
+
if (msg.type !== 'user' && msg.type !== 'assistant') {
|
|
274
|
+
this._tryUpdateSessionId(msg);
|
|
275
|
+
return;
|
|
276
|
+
}
|
|
277
|
+
// -- replay user message: skip (TS-only) -------------------------------
|
|
278
|
+
if (isReplayMessage(msg)) {
|
|
279
|
+
return;
|
|
280
|
+
}
|
|
281
|
+
// -- storable: assistant or user ---------------------------------------
|
|
282
|
+
if (isAssistantMessage(msg)) {
|
|
283
|
+
return this._storeAssistant(msg);
|
|
284
|
+
}
|
|
285
|
+
if (isUserMessage(msg)) {
|
|
286
|
+
return this._storeUser(msg);
|
|
287
|
+
}
|
|
288
|
+
// Unknown — ignore
|
|
289
|
+
}
|
|
290
|
+
// -- internal helpers ----------------------------------------------------
|
|
291
|
+
_tryUpdateSessionId(msg) {
|
|
292
|
+
if (this._sessionId !== null) {
|
|
293
|
+
return;
|
|
294
|
+
}
|
|
295
|
+
const sid = getSessionIdFromMessage(msg);
|
|
296
|
+
if (sid) {
|
|
297
|
+
this._sessionId = sid;
|
|
298
|
+
console.debug(`Resolved session_id=${sid} from message`);
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
// -- private store methods -----------------------------------------------
|
|
302
|
+
async _storeUser(msg) {
|
|
303
|
+
const blob = claudeUserMessageToAnthropicBlob(msg);
|
|
304
|
+
if (blob === null) {
|
|
305
|
+
console.debug('UserMessage produced empty content after conversion – skipping.');
|
|
306
|
+
return;
|
|
307
|
+
}
|
|
308
|
+
await this._callStore(blob, null);
|
|
309
|
+
}
|
|
310
|
+
async _storeAssistant(msg) {
|
|
311
|
+
const { blob, hasThinking } = claudeAssistantMessageToAnthropicBlob(msg, this._includeThinking);
|
|
312
|
+
if (blob === null) {
|
|
313
|
+
console.debug('AssistantMessage produced empty content after conversion – skipping.');
|
|
314
|
+
return;
|
|
315
|
+
}
|
|
316
|
+
const meta = {};
|
|
317
|
+
const message = msg.message;
|
|
318
|
+
const model = message?.model;
|
|
319
|
+
if (model) {
|
|
320
|
+
meta.model = model;
|
|
321
|
+
}
|
|
322
|
+
if (hasThinking) {
|
|
323
|
+
meta.has_thinking = true;
|
|
324
|
+
}
|
|
325
|
+
const error = msg.error;
|
|
326
|
+
if (error) {
|
|
327
|
+
meta.error = error;
|
|
328
|
+
}
|
|
329
|
+
await this._callStore(blob, Object.keys(meta).length > 0 ? meta : null);
|
|
330
|
+
}
|
|
331
|
+
async _ensureSession() {
|
|
332
|
+
if (this._sessionEnsured) {
|
|
333
|
+
return;
|
|
334
|
+
}
|
|
335
|
+
try {
|
|
336
|
+
const session = await this._client.sessions.create({
|
|
337
|
+
useUuid: this._sessionId ? this._sessionId : null,
|
|
338
|
+
user: this._user,
|
|
339
|
+
});
|
|
340
|
+
this._sessionId = session.id;
|
|
341
|
+
console.debug(`Created Acontext session ${this._sessionId}`);
|
|
342
|
+
}
|
|
343
|
+
catch (err) {
|
|
344
|
+
if (err instanceof errors_1.APIError && err.statusCode === 409) {
|
|
345
|
+
console.debug(`Session ${this._sessionId} already exists (409) – continuing.`);
|
|
346
|
+
}
|
|
347
|
+
else {
|
|
348
|
+
throw err;
|
|
349
|
+
}
|
|
350
|
+
}
|
|
351
|
+
this._sessionEnsured = true;
|
|
352
|
+
}
|
|
353
|
+
async _callStore(blob, meta) {
|
|
354
|
+
try {
|
|
355
|
+
await this._ensureSession();
|
|
356
|
+
await this._client.sessions.storeMessage(this._sessionId, blob, {
|
|
357
|
+
format: 'anthropic',
|
|
358
|
+
meta,
|
|
359
|
+
});
|
|
360
|
+
}
|
|
361
|
+
catch (err) {
|
|
362
|
+
if (this._onError) {
|
|
363
|
+
this._onError(err, blob);
|
|
364
|
+
}
|
|
365
|
+
else {
|
|
366
|
+
console.warn(`Failed to store message (session=${this._sessionId}):`, err);
|
|
367
|
+
}
|
|
368
|
+
}
|
|
369
|
+
}
|
|
370
|
+
}
|
|
371
|
+
exports.ClaudeAgentStorage = ClaudeAgentStorage;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Integration modules for the Acontext TypeScript SDK.
|
|
4
|
+
*/
|
|
5
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
6
|
+
if (k2 === undefined) k2 = k;
|
|
7
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
8
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
9
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
10
|
+
}
|
|
11
|
+
Object.defineProperty(o, k2, desc);
|
|
12
|
+
}) : (function(o, m, k, k2) {
|
|
13
|
+
if (k2 === undefined) k2 = k;
|
|
14
|
+
o[k2] = m[k];
|
|
15
|
+
}));
|
|
16
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
17
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
18
|
+
};
|
|
19
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
20
|
+
__exportStar(require("./claude-agent"), exports);
|
|
@@ -68,8 +68,23 @@ export declare class SessionsAPI {
|
|
|
68
68
|
getSessionSummary(sessionId: string, options?: {
|
|
69
69
|
limit?: number | null;
|
|
70
70
|
}): Promise<string>;
|
|
71
|
+
/**
|
|
72
|
+
* Store a message to a session.
|
|
73
|
+
*
|
|
74
|
+
* @param sessionId - The UUID of the session.
|
|
75
|
+
* @param blob - The message blob in Acontext, OpenAI, Anthropic, or Gemini format.
|
|
76
|
+
* @param options - Options for storing the message.
|
|
77
|
+
* @param options.format - The format of the message blob ('acontext', 'openai', 'anthropic', or 'gemini').
|
|
78
|
+
* @param options.meta - Optional user-provided metadata for the message. This metadata is stored
|
|
79
|
+
* separately from the message content and can be retrieved via getMessages().metas
|
|
80
|
+
* or updated via patchMessageMeta(). Works with all formats.
|
|
81
|
+
* @param options.fileField - The field name for file upload. Only used when format is 'acontext'.
|
|
82
|
+
* @param options.file - Optional file upload. Only used when format is 'acontext'.
|
|
83
|
+
* @returns The created Message object. The msg.meta field contains only user-provided metadata.
|
|
84
|
+
*/
|
|
71
85
|
storeMessage(sessionId: string, blob: MessageBlob, options?: {
|
|
72
86
|
format?: 'acontext' | 'openai' | 'anthropic' | 'gemini';
|
|
87
|
+
meta?: Record<string, unknown> | null;
|
|
73
88
|
fileField?: string | null;
|
|
74
89
|
file?: FileUpload | null;
|
|
75
90
|
}): Promise<Message>;
|
|
@@ -86,8 +101,11 @@ export declare class SessionsAPI {
|
|
|
86
101
|
* @param options.editStrategies - Optional list of edit strategies to apply before format conversion.
|
|
87
102
|
* Examples:
|
|
88
103
|
* - Remove tool results: [{ type: 'remove_tool_result', params: { keep_recent_n_tool_results: 3 } }]
|
|
104
|
+
* - Remove large tool results: [{ type: 'remove_tool_result', params: { gt_token: 100 } }]
|
|
105
|
+
* - Remove large tool call params: [{ type: 'remove_tool_call_params', params: { gt_token: 100 } }]
|
|
89
106
|
* - Middle out: [{ type: 'middle_out', params: { token_reduce_to: 5000 } }]
|
|
90
107
|
* - Token limit: [{ type: 'token_limit', params: { limit_tokens: 20000 } }]
|
|
108
|
+
* Throws if editStrategies fail schema validation.
|
|
91
109
|
* @param options.pinEditingStrategiesAtMessage - Message ID to pin editing strategies at.
|
|
92
110
|
* When provided, strategies are only applied to messages up to and including this message ID,
|
|
93
111
|
* keeping subsequent messages unchanged. This helps maintain prompt cache stability by
|
|
@@ -126,4 +144,55 @@ export declare class SessionsAPI {
|
|
|
126
144
|
* pending counts and updated_at timestamp.
|
|
127
145
|
*/
|
|
128
146
|
messagesObservingStatus(sessionId: string): Promise<MessageObservingStatus>;
|
|
147
|
+
/**
|
|
148
|
+
* Update message metadata using patch semantics.
|
|
149
|
+
*
|
|
150
|
+
* Only updates keys present in the meta object. Existing keys not in the request
|
|
151
|
+
* are preserved. To delete a key, pass null as its value.
|
|
152
|
+
*
|
|
153
|
+
* @param sessionId - The UUID of the session.
|
|
154
|
+
* @param messageId - The UUID of the message.
|
|
155
|
+
* @param meta - Object of metadata keys to add, update, or delete. Pass null as a value to delete that key.
|
|
156
|
+
* @returns The complete user metadata after the patch operation.
|
|
157
|
+
*
|
|
158
|
+
* @example
|
|
159
|
+
* // Add/update keys
|
|
160
|
+
* const updated = await client.sessions.patchMessageMeta(
|
|
161
|
+
* sessionId, messageId,
|
|
162
|
+
* { status: 'processed', score: 0.95 }
|
|
163
|
+
* );
|
|
164
|
+
*
|
|
165
|
+
* @example
|
|
166
|
+
* // Delete a key
|
|
167
|
+
* const updated = await client.sessions.patchMessageMeta(
|
|
168
|
+
* sessionId, messageId,
|
|
169
|
+
* { old_key: null } // Deletes "old_key"
|
|
170
|
+
* );
|
|
171
|
+
*/
|
|
172
|
+
patchMessageMeta(sessionId: string, messageId: string, meta: Record<string, unknown>): Promise<Record<string, unknown>>;
|
|
173
|
+
/**
|
|
174
|
+
* Update session configs using patch semantics.
|
|
175
|
+
*
|
|
176
|
+
* Only updates keys present in the configs object. Existing keys not in the request
|
|
177
|
+
* are preserved. To delete a key, pass null as its value.
|
|
178
|
+
*
|
|
179
|
+
* @param sessionId - The UUID of the session.
|
|
180
|
+
* @param configs - Object of config keys to add, update, or delete. Pass null as a value to delete that key.
|
|
181
|
+
* @returns The complete configs after the patch operation.
|
|
182
|
+
*
|
|
183
|
+
* @example
|
|
184
|
+
* // Add/update keys
|
|
185
|
+
* const updated = await client.sessions.patchConfigs(
|
|
186
|
+
* sessionId,
|
|
187
|
+
* { agent: 'bot2', temperature: 0.8 }
|
|
188
|
+
* );
|
|
189
|
+
*
|
|
190
|
+
* @example
|
|
191
|
+
* // Delete a key
|
|
192
|
+
* const updated = await client.sessions.patchConfigs(
|
|
193
|
+
* sessionId,
|
|
194
|
+
* { old_key: null } // Deletes "old_key"
|
|
195
|
+
* );
|
|
196
|
+
*/
|
|
197
|
+
patchConfigs(sessionId: string, configs: Record<string, unknown>): Promise<Record<string, unknown>>;
|
|
129
198
|
}
|
|
@@ -139,6 +139,20 @@ class SessionsAPI {
|
|
|
139
139
|
}
|
|
140
140
|
return parts.join('\n');
|
|
141
141
|
}
|
|
142
|
+
/**
|
|
143
|
+
* Store a message to a session.
|
|
144
|
+
*
|
|
145
|
+
* @param sessionId - The UUID of the session.
|
|
146
|
+
* @param blob - The message blob in Acontext, OpenAI, Anthropic, or Gemini format.
|
|
147
|
+
* @param options - Options for storing the message.
|
|
148
|
+
* @param options.format - The format of the message blob ('acontext', 'openai', 'anthropic', or 'gemini').
|
|
149
|
+
* @param options.meta - Optional user-provided metadata for the message. This metadata is stored
|
|
150
|
+
* separately from the message content and can be retrieved via getMessages().metas
|
|
151
|
+
* or updated via patchMessageMeta(). Works with all formats.
|
|
152
|
+
* @param options.fileField - The field name for file upload. Only used when format is 'acontext'.
|
|
153
|
+
* @param options.file - Optional file upload. Only used when format is 'acontext'.
|
|
154
|
+
* @returns The created Message object. The msg.meta field contains only user-provided metadata.
|
|
155
|
+
*/
|
|
142
156
|
async storeMessage(sessionId, blob, options) {
|
|
143
157
|
const format = options?.format ?? 'openai';
|
|
144
158
|
if (!['acontext', 'openai', 'anthropic', 'gemini'].includes(format)) {
|
|
@@ -150,6 +164,9 @@ class SessionsAPI {
|
|
|
150
164
|
const payload = {
|
|
151
165
|
format,
|
|
152
166
|
};
|
|
167
|
+
if (options?.meta !== undefined && options?.meta !== null) {
|
|
168
|
+
payload.meta = options.meta;
|
|
169
|
+
}
|
|
153
170
|
if (format === 'acontext') {
|
|
154
171
|
if (blob instanceof messages_1.AcontextMessage) {
|
|
155
172
|
payload.blob = blob.toJSON();
|
|
@@ -197,8 +214,11 @@ class SessionsAPI {
|
|
|
197
214
|
* @param options.editStrategies - Optional list of edit strategies to apply before format conversion.
|
|
198
215
|
* Examples:
|
|
199
216
|
* - Remove tool results: [{ type: 'remove_tool_result', params: { keep_recent_n_tool_results: 3 } }]
|
|
217
|
+
* - Remove large tool results: [{ type: 'remove_tool_result', params: { gt_token: 100 } }]
|
|
218
|
+
* - Remove large tool call params: [{ type: 'remove_tool_call_params', params: { gt_token: 100 } }]
|
|
200
219
|
* - Middle out: [{ type: 'middle_out', params: { token_reduce_to: 5000 } }]
|
|
201
220
|
* - Token limit: [{ type: 'token_limit', params: { limit_tokens: 20000 } }]
|
|
221
|
+
* Throws if editStrategies fail schema validation.
|
|
202
222
|
* @param options.pinEditingStrategiesAtMessage - Message ID to pin editing strategies at.
|
|
203
223
|
* When provided, strategies are only applied to messages up to and including this message ID,
|
|
204
224
|
* keeping subsequent messages unchanged. This helps maintain prompt cache stability by
|
|
@@ -218,6 +238,7 @@ class SessionsAPI {
|
|
|
218
238
|
time_desc: options?.timeDesc ?? true, // Default to true
|
|
219
239
|
}));
|
|
220
240
|
if (options?.editStrategies !== undefined && options?.editStrategies !== null) {
|
|
241
|
+
types_1.EditStrategySchema.array().parse(options.editStrategies);
|
|
221
242
|
params.edit_strategies = JSON.stringify(options.editStrategies);
|
|
222
243
|
}
|
|
223
244
|
if (options?.pinEditingStrategiesAtMessage !== undefined && options?.pinEditingStrategiesAtMessage !== null) {
|
|
@@ -256,5 +277,68 @@ class SessionsAPI {
|
|
|
256
277
|
const data = await this.requester.request('GET', `/session/${sessionId}/observing_status`);
|
|
257
278
|
return types_1.MessageObservingStatusSchema.parse(data);
|
|
258
279
|
}
|
|
280
|
+
/**
|
|
281
|
+
* Update message metadata using patch semantics.
|
|
282
|
+
*
|
|
283
|
+
* Only updates keys present in the meta object. Existing keys not in the request
|
|
284
|
+
* are preserved. To delete a key, pass null as its value.
|
|
285
|
+
*
|
|
286
|
+
* @param sessionId - The UUID of the session.
|
|
287
|
+
* @param messageId - The UUID of the message.
|
|
288
|
+
* @param meta - Object of metadata keys to add, update, or delete. Pass null as a value to delete that key.
|
|
289
|
+
* @returns The complete user metadata after the patch operation.
|
|
290
|
+
*
|
|
291
|
+
* @example
|
|
292
|
+
* // Add/update keys
|
|
293
|
+
* const updated = await client.sessions.patchMessageMeta(
|
|
294
|
+
* sessionId, messageId,
|
|
295
|
+
* { status: 'processed', score: 0.95 }
|
|
296
|
+
* );
|
|
297
|
+
*
|
|
298
|
+
* @example
|
|
299
|
+
* // Delete a key
|
|
300
|
+
* const updated = await client.sessions.patchMessageMeta(
|
|
301
|
+
* sessionId, messageId,
|
|
302
|
+
* { old_key: null } // Deletes "old_key"
|
|
303
|
+
* );
|
|
304
|
+
*/
|
|
305
|
+
async patchMessageMeta(sessionId, messageId, meta) {
|
|
306
|
+
const payload = { meta };
|
|
307
|
+
const data = await this.requester.request('PATCH', `/session/${sessionId}/messages/${messageId}/meta`, {
|
|
308
|
+
jsonData: payload,
|
|
309
|
+
});
|
|
310
|
+
return data.meta ?? {};
|
|
311
|
+
}
|
|
312
|
+
/**
|
|
313
|
+
* Update session configs using patch semantics.
|
|
314
|
+
*
|
|
315
|
+
* Only updates keys present in the configs object. Existing keys not in the request
|
|
316
|
+
* are preserved. To delete a key, pass null as its value.
|
|
317
|
+
*
|
|
318
|
+
* @param sessionId - The UUID of the session.
|
|
319
|
+
* @param configs - Object of config keys to add, update, or delete. Pass null as a value to delete that key.
|
|
320
|
+
* @returns The complete configs after the patch operation.
|
|
321
|
+
*
|
|
322
|
+
* @example
|
|
323
|
+
* // Add/update keys
|
|
324
|
+
* const updated = await client.sessions.patchConfigs(
|
|
325
|
+
* sessionId,
|
|
326
|
+
* { agent: 'bot2', temperature: 0.8 }
|
|
327
|
+
* );
|
|
328
|
+
*
|
|
329
|
+
* @example
|
|
330
|
+
* // Delete a key
|
|
331
|
+
* const updated = await client.sessions.patchConfigs(
|
|
332
|
+
* sessionId,
|
|
333
|
+
* { old_key: null } // Deletes "old_key"
|
|
334
|
+
* );
|
|
335
|
+
*/
|
|
336
|
+
async patchConfigs(sessionId, configs) {
|
|
337
|
+
const payload = { configs };
|
|
338
|
+
const data = await this.requester.request('PATCH', `/session/${sessionId}/configs`, {
|
|
339
|
+
jsonData: payload,
|
|
340
|
+
});
|
|
341
|
+
return data.configs ?? {};
|
|
342
|
+
}
|
|
259
343
|
}
|
|
260
344
|
exports.SessionsAPI = SessionsAPI;
|
package/dist/types/session.d.ts
CHANGED
|
@@ -111,6 +111,7 @@ export type PublicURL = z.infer<typeof PublicURLSchema>;
|
|
|
111
111
|
export declare const GetMessagesOutputSchema: z.ZodObject<{
|
|
112
112
|
items: z.ZodArray<z.ZodUnknown>;
|
|
113
113
|
ids: z.ZodArray<z.ZodString>;
|
|
114
|
+
metas: z.ZodDefault<z.ZodArray<z.ZodRecord<z.ZodString, z.ZodUnknown>>>;
|
|
114
115
|
next_cursor: z.ZodOptional<z.ZodNullable<z.ZodString>>;
|
|
115
116
|
has_more: z.ZodBoolean;
|
|
116
117
|
this_time_tokens: z.ZodNumber;
|
|
@@ -159,6 +160,7 @@ export declare const RemoveToolResultParamsSchema: z.ZodObject<{
|
|
|
159
160
|
keep_recent_n_tool_results: z.ZodOptional<z.ZodNumber>;
|
|
160
161
|
tool_result_placeholder: z.ZodOptional<z.ZodString>;
|
|
161
162
|
keep_tools: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
163
|
+
gt_token: z.ZodOptional<z.ZodNumber>;
|
|
162
164
|
}, z.core.$strip>;
|
|
163
165
|
export type RemoveToolResultParams = z.infer<typeof RemoveToolResultParamsSchema>;
|
|
164
166
|
/**
|
|
@@ -167,6 +169,7 @@ export type RemoveToolResultParams = z.infer<typeof RemoveToolResultParamsSchema
|
|
|
167
169
|
export declare const RemoveToolCallParamsParamsSchema: z.ZodObject<{
|
|
168
170
|
keep_recent_n_tool_calls: z.ZodOptional<z.ZodNumber>;
|
|
169
171
|
keep_tools: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
172
|
+
gt_token: z.ZodOptional<z.ZodNumber>;
|
|
170
173
|
}, z.core.$strip>;
|
|
171
174
|
export type RemoveToolCallParamsParams = z.infer<typeof RemoveToolCallParamsParamsSchema>;
|
|
172
175
|
/**
|
|
@@ -183,6 +186,7 @@ export declare const RemoveToolCallParamsStrategySchema: z.ZodObject<{
|
|
|
183
186
|
params: z.ZodObject<{
|
|
184
187
|
keep_recent_n_tool_calls: z.ZodOptional<z.ZodNumber>;
|
|
185
188
|
keep_tools: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
189
|
+
gt_token: z.ZodOptional<z.ZodNumber>;
|
|
186
190
|
}, z.core.$strip>;
|
|
187
191
|
}, z.core.$strip>;
|
|
188
192
|
export type RemoveToolCallParamsStrategy = z.infer<typeof RemoveToolCallParamsStrategySchema>;
|
|
@@ -197,6 +201,7 @@ export declare const RemoveToolResultStrategySchema: z.ZodObject<{
|
|
|
197
201
|
keep_recent_n_tool_results: z.ZodOptional<z.ZodNumber>;
|
|
198
202
|
tool_result_placeholder: z.ZodOptional<z.ZodString>;
|
|
199
203
|
keep_tools: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
204
|
+
gt_token: z.ZodOptional<z.ZodNumber>;
|
|
200
205
|
}, z.core.$strip>;
|
|
201
206
|
}, z.core.$strip>;
|
|
202
207
|
export type RemoveToolResultStrategy = z.infer<typeof RemoveToolResultStrategySchema>;
|
|
@@ -252,12 +257,14 @@ export declare const EditStrategySchema: z.ZodUnion<readonly [z.ZodObject<{
|
|
|
252
257
|
keep_recent_n_tool_results: z.ZodOptional<z.ZodNumber>;
|
|
253
258
|
tool_result_placeholder: z.ZodOptional<z.ZodString>;
|
|
254
259
|
keep_tools: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
260
|
+
gt_token: z.ZodOptional<z.ZodNumber>;
|
|
255
261
|
}, z.core.$strip>;
|
|
256
262
|
}, z.core.$strip>, z.ZodObject<{
|
|
257
263
|
type: z.ZodLiteral<"remove_tool_call_params">;
|
|
258
264
|
params: z.ZodObject<{
|
|
259
265
|
keep_recent_n_tool_calls: z.ZodOptional<z.ZodNumber>;
|
|
260
266
|
keep_tools: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
267
|
+
gt_token: z.ZodOptional<z.ZodNumber>;
|
|
261
268
|
}, z.core.$strip>;
|
|
262
269
|
}, z.core.$strip>, z.ZodObject<{
|
|
263
270
|
type: z.ZodLiteral<"token_limit">;
|
package/dist/types/session.js
CHANGED
|
@@ -74,6 +74,8 @@ exports.PublicURLSchema = zod_1.z.object({
|
|
|
74
74
|
exports.GetMessagesOutputSchema = zod_1.z.object({
|
|
75
75
|
items: zod_1.z.array(zod_1.z.unknown()),
|
|
76
76
|
ids: zod_1.z.array(zod_1.z.string()),
|
|
77
|
+
/** User-provided metadata for each message (same order as items/ids) */
|
|
78
|
+
metas: zod_1.z.array(zod_1.z.record(zod_1.z.string(), zod_1.z.unknown())).default([]),
|
|
77
79
|
next_cursor: zod_1.z.string().nullable().optional(),
|
|
78
80
|
has_more: zod_1.z.boolean(),
|
|
79
81
|
/** Total token count of the returned messages */
|
|
@@ -121,6 +123,11 @@ exports.RemoveToolResultParamsSchema = zod_1.z.object({
|
|
|
121
123
|
* Tool results from these tools are always kept regardless of keep_recent_n_tool_results.
|
|
122
124
|
*/
|
|
123
125
|
keep_tools: zod_1.z.array(zod_1.z.string()).optional(),
|
|
126
|
+
/**
|
|
127
|
+
* Only remove tool results whose text has more than this many tokens.
|
|
128
|
+
* If omitted, all tool results are eligible for removal.
|
|
129
|
+
*/
|
|
130
|
+
gt_token: zod_1.z.number().int().min(1).optional(),
|
|
124
131
|
});
|
|
125
132
|
/**
|
|
126
133
|
* Parameters for the remove_tool_call_params edit strategy.
|
|
@@ -136,6 +143,11 @@ exports.RemoveToolCallParamsParamsSchema = zod_1.z.object({
|
|
|
136
143
|
* Tool calls for these tools always keep their full parameters regardless of keep_recent_n_tool_calls.
|
|
137
144
|
*/
|
|
138
145
|
keep_tools: zod_1.z.array(zod_1.z.string()).optional(),
|
|
146
|
+
/**
|
|
147
|
+
* Only remove tool call params whose arguments have more than this many tokens.
|
|
148
|
+
* If omitted, all tool calls are eligible for removal.
|
|
149
|
+
*/
|
|
150
|
+
gt_token: zod_1.z.number().int().min(1).optional(),
|
|
139
151
|
});
|
|
140
152
|
/**
|
|
141
153
|
* Edit strategy to remove parameters from old tool-call parts.
|