@inferencesh/sdk 0.22.0 → 0.23.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/CHANGELOG.md +28 -0
- package/dist/agent/actions.d.ts +2 -2
- package/dist/agent/actions.js +93 -21
- package/dist/agent/api.d.ts +3 -3
- package/dist/agent/api.js +9 -7
- package/dist/agent/context.d.ts +1 -1
- package/dist/agent/hooks.d.ts +2 -2
- package/dist/agent/hooks.js +1 -1
- package/dist/agent/index.d.ts +6 -6
- package/dist/agent/index.js +5 -5
- package/dist/agent/mcp-input.d.ts +1 -1
- package/dist/agent/provider.d.ts +1 -1
- package/dist/agent/provider.js +5 -5
- package/dist/agent/reducer.d.ts +1 -1
- package/dist/agent/reducer.js +2 -2
- package/dist/agent/types.d.ts +5 -5
- package/dist/api/agents.d.ts +8 -10
- package/dist/api/agents.js +45 -34
- package/dist/api/api-keys.d.ts +3 -3
- package/dist/api/apps.d.ts +4 -4
- package/dist/api/artifacts.d.ts +3 -3
- package/dist/api/chats.d.ts +4 -4
- package/dist/api/credentials.d.ts +3 -3
- package/dist/api/engines.d.ts +4 -4
- package/dist/api/files.d.ts +3 -3
- package/dist/api/flow-runs.d.ts +3 -3
- package/dist/api/flows.d.ts +4 -4
- package/dist/api/index.d.ts +4 -4
- package/dist/api/index.js +4 -4
- package/dist/api/knowledge.d.ts +4 -4
- package/dist/api/mcp-servers.d.ts +4 -4
- package/dist/api/projects.d.ts +4 -4
- package/dist/api/search.d.ts +3 -3
- package/dist/api/secrets.d.ts +3 -3
- package/dist/api/sessions.d.ts +3 -3
- package/dist/api/sockets.d.ts +6 -6
- package/dist/api/sockets.js +2 -2
- package/dist/api/tasks.d.ts +3 -3
- package/dist/api/tasks.js +4 -4
- package/dist/api/teams.d.ts +4 -4
- package/dist/api/write-bodies.d.ts +1 -1
- package/dist/delta.d.ts +1 -1
- package/dist/delta.js +1 -1
- package/dist/hook-builder.d.ts +1 -1
- package/dist/hook-builder.js +1 -1
- package/dist/http/client.d.ts +2 -2
- package/dist/http/client.js +2 -2
- package/dist/http/errors.d.ts +1 -1
- package/dist/http/index.d.ts +4 -4
- package/dist/http/index.js +4 -4
- package/dist/http/response.d.ts +1 -1
- package/dist/http/stream-until-terminal.d.ts +22 -8
- package/dist/http/stream-until-terminal.js +17 -9
- package/dist/http/streamable.d.ts +63 -7
- package/dist/http/streamable.js +277 -119
- package/dist/index.d.ts +65 -65
- package/dist/index.js +53 -53
- package/dist/live/schema.js +1 -1
- package/dist/live/session.d.ts +3 -3
- package/dist/live/session.js +2 -2
- package/dist/proxy/express.d.ts +1 -1
- package/dist/proxy/express.js +1 -1
- package/dist/proxy/hono.d.ts +1 -1
- package/dist/proxy/hono.js +1 -1
- package/dist/proxy/index.js +0 -2
- package/dist/proxy/nextjs.d.ts +3 -3
- package/dist/proxy/nextjs.js +2 -2
- package/dist/proxy/remix.d.ts +1 -1
- package/dist/proxy/remix.js +1 -1
- package/dist/proxy/svelte.d.ts +1 -1
- package/dist/proxy/svelte.js +1 -1
- package/dist/tool-builder.d.ts +1 -1
- package/dist/tool-builder.js +1 -1
- package/dist/types.d.ts +164 -40
- package/dist/types.js +33 -9
- package/dist/utils.d.ts +2 -2
- package/dist/utils.js +2 -2
- package/package.json +2 -1
package/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,34 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
## [0.23.0] - 2026-10-11
|
|
11
|
+
|
|
12
|
+
### Changed
|
|
13
|
+
|
|
14
|
+
- Generated types follow the API: `MessageInput` (what an agent run takes), `ContextField.in_prompt`, `ApiAgentRunRequest` takes `agent_id`/`agent_version_id` and no `channel_context`; `CreateAgentMessageRequest` is gone. Per-function `credentials` and annotations on `AppFunction`, and `DeployWarning` on `AppVersionDTO` (INF-1053). `ScopesResponse.account_groups`. Agent events for subagent ids, context, limits and account.
|
|
15
|
+
- Dev dependency lockfile refreshed for security advisories (handlebars, devalue, sharp). Nothing shipped in the package changes.
|
|
16
|
+
|
|
17
|
+
### Deprecated
|
|
18
|
+
|
|
19
|
+
- `SendMessageOptions.channel_context`. The API no longer reads a channel context from an agent run request; a chat's routing comes from the server's own channel receivers. The option is still accepted and is not sent. Chats still return `channel_context`.
|
|
20
|
+
|
|
21
|
+
### Added
|
|
22
|
+
|
|
23
|
+
- `StreamableManager` reconnects on opt-in: `reconnect: true | { maxAttempts, baseDelayMs, maxDelayMs, idleTimeoutMs }` (defaults 10, 1000, 30000, 30000). A failed stream is retried with jittered exponential backoff; any line received, heartbeats included, resets the failure count; a stream silent for `idleTimeoutMs` is reconnected; in a browser, `online` or the tab becoming visible retries at once. A 4xx other than 408/429 is not retried. `onRetry(error, attempt, delayMs)` reports each scheduled retry; `onReconnect(attempt)` runs after a retry connects and before the new stream is read, so the caller can fetch what it missed. With `reconnect`, `onError` fires only when the manager gives up. `StreamReconnectOptions` is exported. Without the option nothing changes.
|
|
24
|
+
|
|
25
|
+
### Fixed
|
|
26
|
+
|
|
27
|
+
- The React chat (`AgentChatProvider`) no longer stays busy after a network blip mid-turn (Chromium `ERR_NETWORK_CHANGED`, "Stream error: TypeError: network error"). The chat stream reconnects; each reconnect refetches the chat and its messages, so a turn that finished while disconnected ends and `onTurnEnd` fires. `connectionStatus` is `'connecting'` while it waits to retry and `'error'` (with `error` set) once it gives up. Whenever the stream ends on its own and the chat is still busy, the chat is polled until idle. A stop, reset or chat switch during a pending retry leaves the new state alone.
|
|
28
|
+
- `Agent.sendMessage`/`startStreaming` and `tasks.run`/`watch` in streaming mode survive a network error: the stream reconnects and refetches the chat (with its messages) or the task, so the wait settles when it finished meanwhile. A 4xx refusal still rejects at once; other errors reject once the stream stops retrying.
|
|
29
|
+
|
|
30
|
+
- The package loads in plain Node (no bundler). 0.22.1's dist used extensionless relative imports, so `import("@inferencesh/sdk")` and every subpath except `proxy` and `internal/upload` failed with ERR_MODULE_NOT_FOUND. The build now uses NodeNext resolution with `.js` import specifiers, and `@inferencesh/sdk/proxy/nextjs` imports `next/server.js`. `require()` of every subpath works on Node >=22.12. CI and publish load each export of the packed tarball (`pnpm run check:exports`).
|
|
31
|
+
|
|
32
|
+
## [0.22.1] - 2026-10-10
|
|
33
|
+
|
|
34
|
+
### Fixed
|
|
35
|
+
|
|
36
|
+
- `sendMessage` sends its attachments: it posted only the text after uploading the files, so attachments never reached the agent. It now posts the file refs as `attachments` on POST /chats/{id}/messages. Needs api-v1227+; an older API ignores the field.
|
|
37
|
+
|
|
10
38
|
## [0.22.0] - 2026-10-10
|
|
11
39
|
|
|
12
40
|
Breaking: the server proxy forwards only app runs and agent chats and refuses every other API call with 403 (see Security); `update()` on projects, knowledge, skills, chats, engines and teams sends PATCH and needs an API that answers PATCH (see Changed); the Next.js proxy handler has no `PUT`.
|
package/dist/agent/actions.d.ts
CHANGED
|
@@ -4,6 +4,6 @@
|
|
|
4
4
|
* Action creators that handle side effects (API calls, streaming).
|
|
5
5
|
* These are created once per provider instance with access to dispatch.
|
|
6
6
|
*/
|
|
7
|
-
import type { ActionsContext, ActionsResult } from './types';
|
|
7
|
+
import type { ActionsContext, ActionsResult } from './types.js';
|
|
8
8
|
export declare function createActions(ctx: ActionsContext): ActionsResult;
|
|
9
|
-
export declare function getClientToolHandlers(config: import('./types').AgentOptions | null): Map<string, import('./types').ClientToolHandlerFn>;
|
|
9
|
+
export declare function getClientToolHandlers(config: import('./types.js').AgentOptions | null): Map<string, import('./types.js').ClientToolHandlerFn>;
|
package/dist/agent/actions.js
CHANGED
|
@@ -4,15 +4,15 @@
|
|
|
4
4
|
* Action creators that handle side effects (API calls, streaming).
|
|
5
5
|
* These are created once per provider instance with access to dispatch.
|
|
6
6
|
*/
|
|
7
|
-
import { ToolInvocationStatusAwaitingInput, ToolInvocationStatusInProgress, ToolTypeClient, } from '../types';
|
|
8
|
-
import { isChatBusy, isMessageTerminal, isRunInterrupted, isRunWorking } from '../utils';
|
|
9
|
-
import { StreamableManager } from '../http/streamable';
|
|
10
|
-
import { PollManager } from '../http/poll';
|
|
11
|
-
import { createLLMDeltaAccumulator } from '../delta';
|
|
12
|
-
import { isAdHocConfig, extractClientToolHandlers } from './types';
|
|
13
|
-
import * as api from './api';
|
|
14
|
-
import { buildMCPInputResult } from './mcp-input';
|
|
15
|
-
import { isInferenceError } from '../http/errors';
|
|
7
|
+
import { ToolInvocationStatusAwaitingInput, ToolInvocationStatusInProgress, ToolTypeClient, } from '../types.js';
|
|
8
|
+
import { isChatBusy, isMessageTerminal, isRunInterrupted, isRunWorking } from '../utils.js';
|
|
9
|
+
import { StreamableManager } from '../http/streamable.js';
|
|
10
|
+
import { PollManager } from '../http/poll.js';
|
|
11
|
+
import { createLLMDeltaAccumulator } from '../delta.js';
|
|
12
|
+
import { isAdHocConfig, extractClientToolHandlers } from './types.js';
|
|
13
|
+
import * as api from './api.js';
|
|
14
|
+
import { buildMCPInputResult } from './mcp-input.js';
|
|
15
|
+
import { isInferenceError } from '../http/errors.js';
|
|
16
16
|
// =============================================================================
|
|
17
17
|
// Action Creators
|
|
18
18
|
// =============================================================================
|
|
@@ -20,6 +20,10 @@ export function createActions(ctx) {
|
|
|
20
20
|
const dispatchedToolInvocations = new Set();
|
|
21
21
|
const { client, dispatch, getState, getConfig, getChatId, getClientToolHandlers, getStreamManager, setStreamManager, getStreamEnabled, getPollIntervalMs, callbacks } = ctx;
|
|
22
22
|
let prevChatWasBusy = false;
|
|
23
|
+
// Bumped by every streamChat() and stopStream(). A stream whose generation
|
|
24
|
+
// is no longer current (stopped, reset, switched to another chat) leaves
|
|
25
|
+
// state alone, including work it started before that.
|
|
26
|
+
let streamGeneration = 0;
|
|
23
27
|
const checkTurnEnd = (chat) => {
|
|
24
28
|
const busy = isChatBusy(chat);
|
|
25
29
|
if (prevChatWasBusy && !busy) {
|
|
@@ -83,6 +87,7 @@ export function createActions(ctx) {
|
|
|
83
87
|
}
|
|
84
88
|
};
|
|
85
89
|
const streamChat = async (id) => {
|
|
90
|
+
const generation = ++streamGeneration;
|
|
86
91
|
const existingManager = getStreamManager();
|
|
87
92
|
if (existingManager) {
|
|
88
93
|
existingManager.stop();
|
|
@@ -93,6 +98,9 @@ export function createActions(ctx) {
|
|
|
93
98
|
try {
|
|
94
99
|
// Fetch initial chat (fetchChat loads messages separately since Chat.Get no longer preloads them)
|
|
95
100
|
const chat = await api.fetchChat(client, id);
|
|
101
|
+
// Stopped or switched to another chat while fetching.
|
|
102
|
+
if (generation !== streamGeneration)
|
|
103
|
+
return;
|
|
96
104
|
if (chat) {
|
|
97
105
|
setChat(chat);
|
|
98
106
|
}
|
|
@@ -108,11 +116,53 @@ export function createActions(ctx) {
|
|
|
108
116
|
pollChat(id);
|
|
109
117
|
return;
|
|
110
118
|
}
|
|
119
|
+
// Token-by-token streaming state, one accumulator per message being
|
|
120
|
+
// streamed. Deltas name their message (DeltaEvent.resource_id), so state
|
|
121
|
+
// never leaks between messages the way a single shared accumulator allowed.
|
|
122
|
+
const deltaAccums = new Map();
|
|
123
|
+
const isCurrent = () => generation === streamGeneration;
|
|
124
|
+
let failed = false;
|
|
125
|
+
// The API does not replay what the stream missed: the chat as fetched is
|
|
126
|
+
// the source of truth. Messages are merged, so older pages stay loaded.
|
|
127
|
+
const resync = async () => {
|
|
128
|
+
const chat = await api.fetchChat(client, id);
|
|
129
|
+
if (!chat || !isCurrent())
|
|
130
|
+
return null;
|
|
131
|
+
for (const message of chat.chat_messages ?? []) {
|
|
132
|
+
updateMessage(message);
|
|
133
|
+
}
|
|
134
|
+
dispatch({ type: 'UPDATE_CHAT', payload: chat });
|
|
135
|
+
callbacks.onStatusChange?.(isChatBusy(chat) ? 'streaming' : 'idle');
|
|
136
|
+
checkTurnEnd(chat);
|
|
137
|
+
return chat;
|
|
138
|
+
};
|
|
111
139
|
// Single unified stream with TypedEvents (both Chat and ChatMessage events)
|
|
112
140
|
const manager = new StreamableManager({
|
|
113
141
|
request: api.chatStreamRequest(client, id),
|
|
142
|
+
reconnect: true,
|
|
143
|
+
onRetry: (error, attempt, delayMs) => {
|
|
144
|
+
console.warn(`[AgentSDK] Stream error, reconnecting in ${delayMs}ms (attempt ${attempt}):`, error);
|
|
145
|
+
if (!isCurrent())
|
|
146
|
+
return;
|
|
147
|
+
dispatch({ type: 'SET_CONNECTION_STATUS', payload: 'connecting' });
|
|
148
|
+
callbacks.onStatusChange?.('connecting');
|
|
149
|
+
},
|
|
150
|
+
onReconnect: async () => {
|
|
151
|
+
// Partial text from before the drop is replaced by the fetched messages.
|
|
152
|
+
deltaAccums.clear();
|
|
153
|
+
if (!isCurrent())
|
|
154
|
+
return;
|
|
155
|
+
dispatch({ type: 'SET_CONNECTION_STATUS', payload: 'streaming' });
|
|
156
|
+
await resync();
|
|
157
|
+
},
|
|
114
158
|
onError: (error) => {
|
|
159
|
+
// The manager gave up: a refusal, or every retry failed.
|
|
115
160
|
console.warn('[AgentSDK] Stream error:', error);
|
|
161
|
+
if (!isCurrent())
|
|
162
|
+
return;
|
|
163
|
+
failed = true;
|
|
164
|
+
dispatch({ type: 'SET_CONNECTION_STATUS', payload: 'error' });
|
|
165
|
+
dispatch({ type: 'SET_ERROR', payload: error.message });
|
|
116
166
|
callbacks.onError?.(error);
|
|
117
167
|
},
|
|
118
168
|
onStart: () => {
|
|
@@ -120,14 +170,28 @@ export function createActions(ctx) {
|
|
|
120
170
|
callbacks.onStatusChange?.('streaming');
|
|
121
171
|
},
|
|
122
172
|
onEnd: () => {
|
|
123
|
-
//
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
173
|
+
// An intentional stop or a newer stream skips all of this.
|
|
174
|
+
if (!isCurrent() || getStreamManager() !== manager)
|
|
175
|
+
return;
|
|
176
|
+
// The stream ended cleanly or gave up. Release the ref now, so a
|
|
177
|
+
// sendMessage meanwhile opens a new stream (and makes this one stale).
|
|
178
|
+
setStreamManager(undefined);
|
|
179
|
+
// A turn still running would leave the UI busy with nothing to end
|
|
180
|
+
// it: read the chat, and poll it until idle if it is still busy.
|
|
181
|
+
resync()
|
|
182
|
+
.catch(() => null)
|
|
183
|
+
.then((chat) => {
|
|
184
|
+
if (!isCurrent() || getStreamManager())
|
|
185
|
+
return;
|
|
186
|
+
if (chat ? isChatBusy(chat) : isChatBusy(getState().chat)) {
|
|
187
|
+
pollChat(id, { untilIdle: true });
|
|
188
|
+
return;
|
|
189
|
+
}
|
|
190
|
+
if (failed)
|
|
191
|
+
return; // keep the 'error' status
|
|
128
192
|
dispatch({ type: 'SET_CONNECTION_STATUS', payload: 'idle' });
|
|
129
193
|
callbacks.onStatusChange?.('idle');
|
|
130
|
-
}
|
|
194
|
+
});
|
|
131
195
|
},
|
|
132
196
|
});
|
|
133
197
|
// Listen for Chat object updates (status changes only — don't replace messages)
|
|
@@ -138,10 +202,6 @@ export function createActions(ctx) {
|
|
|
138
202
|
checkTurnEnd(chatData);
|
|
139
203
|
}
|
|
140
204
|
});
|
|
141
|
-
// Token-by-token streaming state, one accumulator per message being
|
|
142
|
-
// streamed. Deltas name their message (DeltaEvent.resource_id), so state
|
|
143
|
-
// never leaks between messages the way a single shared accumulator allowed.
|
|
144
|
-
const deltaAccums = new Map();
|
|
145
205
|
// Listen for ChatMessage updates
|
|
146
206
|
manager.addEventListener('chat_messages', (message, fields) => {
|
|
147
207
|
// A message that has reached a terminal state will receive no further
|
|
@@ -182,8 +242,12 @@ export function createActions(ctx) {
|
|
|
182
242
|
setStreamManager(manager);
|
|
183
243
|
manager.start();
|
|
184
244
|
};
|
|
185
|
-
/**
|
|
186
|
-
|
|
245
|
+
/**
|
|
246
|
+
* Poll-based alternative to streaming for restricted environments. With
|
|
247
|
+
* `untilIdle` (the fallback when a stream gave up mid-turn) polling stops
|
|
248
|
+
* once the chat is idle; the next sendMessage streams again.
|
|
249
|
+
*/
|
|
250
|
+
const pollChat = (id, { untilIdle = false } = {}) => {
|
|
187
251
|
let prevStatus = null;
|
|
188
252
|
const manager = new PollManager({
|
|
189
253
|
pollFunction: async () => {
|
|
@@ -205,6 +269,13 @@ export function createActions(ctx) {
|
|
|
205
269
|
updateMessage(message);
|
|
206
270
|
}
|
|
207
271
|
}
|
|
272
|
+
if (untilIdle && !isChatBusy(chat) && getStreamManager() === manager) {
|
|
273
|
+
// Clear the ref first so onStop is a no-op.
|
|
274
|
+
setStreamManager(undefined);
|
|
275
|
+
manager.stop();
|
|
276
|
+
dispatch({ type: 'SET_CONNECTION_STATUS', payload: 'idle' });
|
|
277
|
+
callbacks.onStatusChange?.('idle');
|
|
278
|
+
}
|
|
208
279
|
}
|
|
209
280
|
}
|
|
210
281
|
catch (err) {
|
|
@@ -232,6 +303,7 @@ export function createActions(ctx) {
|
|
|
232
303
|
manager.start();
|
|
233
304
|
};
|
|
234
305
|
const stopStream = () => {
|
|
306
|
+
streamGeneration++;
|
|
235
307
|
const manager = getStreamManager();
|
|
236
308
|
// Clear ref first so onStop callback (from manager.stop) is a no-op
|
|
237
309
|
setStreamManager(undefined);
|
package/dist/agent/api.d.ts
CHANGED
|
@@ -7,9 +7,9 @@
|
|
|
7
7
|
*
|
|
8
8
|
* /agents/run stays for A2A/programmatic use.
|
|
9
9
|
*/
|
|
10
|
-
import type { AlwaysAllowOptionsDTO, AlwaysAllowResultDTO, ChatAgentDTO, ChatDTO, ChatMessageDTO, ChatSettingsDTO, ChatSettingsRequest, InterruptDTO, ToolExplanationDTO } from '../types';
|
|
11
|
-
import type { AgentOptions, AgentClient, AgentInfo, FileRef } from './types';
|
|
12
|
-
import type { StreamRequest } from '../http/streamable';
|
|
10
|
+
import type { AlwaysAllowOptionsDTO, AlwaysAllowResultDTO, ChatAgentDTO, ChatDTO, ChatMessageDTO, ChatSettingsDTO, ChatSettingsRequest, InterruptDTO, ToolExplanationDTO } from '../types.js';
|
|
11
|
+
import type { AgentOptions, AgentClient, AgentInfo, FileRef } from './types.js';
|
|
12
|
+
import type { StreamRequest } from '../http/streamable.js';
|
|
13
13
|
export interface SendResult {
|
|
14
14
|
chatId: string;
|
|
15
15
|
userMessage: ChatMessageDTO;
|
package/dist/agent/api.js
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*
|
|
8
8
|
* /agents/run stays for A2A/programmatic use.
|
|
9
9
|
*/
|
|
10
|
-
import { isAdHocConfig } from './types';
|
|
10
|
+
import { isAdHocConfig } from './types.js';
|
|
11
11
|
function isFileRef(input) {
|
|
12
12
|
return 'uri' in input && typeof input.uri === 'string';
|
|
13
13
|
}
|
|
@@ -21,7 +21,9 @@ async function processFiles(client, files) {
|
|
|
21
21
|
if (isFileRef(file))
|
|
22
22
|
return file;
|
|
23
23
|
try {
|
|
24
|
-
|
|
24
|
+
// The upload answers with the whole file record; the message takes a ref.
|
|
25
|
+
const { id, uri, filename, content_type, size } = await client.files.upload(file);
|
|
26
|
+
return { id, uri, filename, content_type, size };
|
|
25
27
|
}
|
|
26
28
|
catch (error) {
|
|
27
29
|
console.error('[AgentSDK] Failed to upload file:', error);
|
|
@@ -45,9 +47,9 @@ async function createChat(client, config) {
|
|
|
45
47
|
/**
|
|
46
48
|
* Send a message in a chat — POST /chats/{id}/messages
|
|
47
49
|
*/
|
|
48
|
-
async function sendChatMessage(client, chatId, text) {
|
|
50
|
+
async function sendChatMessage(client, chatId, text, attachments) {
|
|
49
51
|
const resp = await client.http.request('post', `/chats/${chatId}/messages`, {
|
|
50
|
-
data: { message: text },
|
|
52
|
+
data: attachments ? { message: text, attachments } : { message: text },
|
|
51
53
|
});
|
|
52
54
|
return {
|
|
53
55
|
chatId,
|
|
@@ -58,14 +60,14 @@ async function sendChatMessage(client, chatId, text) {
|
|
|
58
60
|
* Send a message — creates chat if needed, then sends message
|
|
59
61
|
*/
|
|
60
62
|
export async function sendMessage(client, config, chatId, text, files) {
|
|
61
|
-
await processFiles(client, files);
|
|
63
|
+
const attachments = await processFiles(client, files);
|
|
62
64
|
// Existing chat — just send the message
|
|
63
65
|
if (chatId) {
|
|
64
|
-
return sendChatMessage(client, chatId, text);
|
|
66
|
+
return sendChatMessage(client, chatId, text, attachments);
|
|
65
67
|
}
|
|
66
68
|
// New chat — create it, then send the first message
|
|
67
69
|
const chat = await createChat(client, config);
|
|
68
|
-
return sendChatMessage(client, chat.id, text);
|
|
70
|
+
return sendChatMessage(client, chat.id, text, attachments);
|
|
69
71
|
}
|
|
70
72
|
// =========================================================================
|
|
71
73
|
// Agent info
|
package/dist/agent/context.d.ts
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
*
|
|
4
4
|
* React Context for sharing chat state and actions.
|
|
5
5
|
*/
|
|
6
|
-
import type { AgentChatState, AgentChatActions, AgentClient } from './types';
|
|
6
|
+
import type { AgentChatState, AgentChatActions, AgentClient } from './types.js';
|
|
7
7
|
/**
|
|
8
8
|
* Context value combining state, actions, and client
|
|
9
9
|
*/
|
package/dist/agent/hooks.d.ts
CHANGED
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
*
|
|
4
4
|
* React hooks for accessing chat state and actions.
|
|
5
5
|
*/
|
|
6
|
-
import type { AgentChatState, AgentChatActions, AgentClient } from './types';
|
|
7
|
-
import type { ChatMessageDTO } from '../types';
|
|
6
|
+
import type { AgentChatState, AgentChatActions, AgentClient } from './types.js';
|
|
7
|
+
import type { ChatMessageDTO } from '../types.js';
|
|
8
8
|
/**
|
|
9
9
|
* Hook to access chat state
|
|
10
10
|
*
|
package/dist/agent/hooks.js
CHANGED
package/dist/agent/index.d.ts
CHANGED
|
@@ -43,9 +43,9 @@
|
|
|
43
43
|
* }
|
|
44
44
|
* ```
|
|
45
45
|
*/
|
|
46
|
-
export { AgentChatProvider } from './provider';
|
|
47
|
-
export { useAgentChat, useAgentActions, useAgentClient, useAgentChatContext, useMessage, } from './hooks';
|
|
48
|
-
export { AgentChatContext, type AgentChatContextValue } from './context';
|
|
49
|
-
export type { AgentClient, FileRef, AdHocAgentConfig, TemplateAgentConfig, AgentOptions, AgentChatState, AgentChatActions, AlwaysAllowChoice, ChatStatus, AgentChatProviderProps, ClientTool, ClientToolHandlerFn, } from './types';
|
|
50
|
-
export { isAdHocConfig, isTemplateConfig, isClientTool, extractToolSchemas, extractClientToolHandlers, } from './types';
|
|
51
|
-
export { MCPMethodElicitationCreate, parseMCPInputState, elicitParams, isURLElicitation, buildMCPInputResult, type MCPInputState, type ElicitRequestParams, type ElicitRequestedSchema, type ElicitPropertySchema, } from './mcp-input';
|
|
46
|
+
export { AgentChatProvider } from './provider.js';
|
|
47
|
+
export { useAgentChat, useAgentActions, useAgentClient, useAgentChatContext, useMessage, } from './hooks.js';
|
|
48
|
+
export { AgentChatContext, type AgentChatContextValue } from './context.js';
|
|
49
|
+
export type { AgentClient, FileRef, AdHocAgentConfig, TemplateAgentConfig, AgentOptions, AgentChatState, AgentChatActions, AlwaysAllowChoice, ChatStatus, AgentChatProviderProps, ClientTool, ClientToolHandlerFn, } from './types.js';
|
|
50
|
+
export { isAdHocConfig, isTemplateConfig, isClientTool, extractToolSchemas, extractClientToolHandlers, } from './types.js';
|
|
51
|
+
export { MCPMethodElicitationCreate, parseMCPInputState, elicitParams, isURLElicitation, buildMCPInputResult, type MCPInputState, type ElicitRequestParams, type ElicitRequestedSchema, type ElicitPropertySchema, } from './mcp-input.js';
|
package/dist/agent/index.js
CHANGED
|
@@ -44,12 +44,12 @@
|
|
|
44
44
|
* ```
|
|
45
45
|
*/
|
|
46
46
|
// Provider
|
|
47
|
-
export { AgentChatProvider } from './provider';
|
|
47
|
+
export { AgentChatProvider } from './provider.js';
|
|
48
48
|
// Hooks
|
|
49
|
-
export { useAgentChat, useAgentActions, useAgentClient, useAgentChatContext, useMessage, } from './hooks';
|
|
49
|
+
export { useAgentChat, useAgentActions, useAgentClient, useAgentChatContext, useMessage, } from './hooks.js';
|
|
50
50
|
// Context (for advanced use cases)
|
|
51
|
-
export { AgentChatContext } from './context';
|
|
51
|
+
export { AgentChatContext } from './context.js';
|
|
52
52
|
// Type guards and helpers
|
|
53
|
-
export { isAdHocConfig, isTemplateConfig, isClientTool, extractToolSchemas, extractClientToolHandlers, } from './types';
|
|
53
|
+
export { isAdHocConfig, isTemplateConfig, isClientTool, extractToolSchemas, extractClientToolHandlers, } from './types.js';
|
|
54
54
|
// MCP input requests
|
|
55
|
-
export { MCPMethodElicitationCreate, parseMCPInputState, elicitParams, isURLElicitation, buildMCPInputResult, } from './mcp-input';
|
|
55
|
+
export { MCPMethodElicitationCreate, parseMCPInputState, elicitParams, isURLElicitation, buildMCPInputResult, } from './mcp-input.js';
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
* key, and submits them with `submitMCPInput`; the runtime then re-sends the
|
|
8
8
|
* tool call with those responses.
|
|
9
9
|
*/
|
|
10
|
-
import type { ElicitResult, InputRequest } from '../types';
|
|
10
|
+
import type { ElicitResult, InputRequest } from '../types.js';
|
|
11
11
|
export declare const MCPMethodElicitationCreate = "elicitation/create";
|
|
12
12
|
/** Stored in ToolInvocationDTO.data while an MCP tool call waits for the user. */
|
|
13
13
|
export interface MCPInputState {
|
package/dist/agent/provider.d.ts
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
* Uses React useReducer + Context pattern.
|
|
6
6
|
*/
|
|
7
7
|
import React from 'react';
|
|
8
|
-
import type { AgentChatProviderProps } from './types';
|
|
8
|
+
import type { AgentChatProviderProps } from './types.js';
|
|
9
9
|
/**
|
|
10
10
|
* AgentChatProvider - Provides chat state and actions to children
|
|
11
11
|
*
|
package/dist/agent/provider.js
CHANGED
|
@@ -6,11 +6,11 @@ import { jsx as _jsx } from "react/jsx-runtime";
|
|
|
6
6
|
* Uses React useReducer + Context pattern.
|
|
7
7
|
*/
|
|
8
8
|
import { useReducer, useRef, useEffect, useMemo } from 'react';
|
|
9
|
-
import { AgentChatContext } from './context';
|
|
10
|
-
import { chatReducer, initialState } from './reducer';
|
|
11
|
-
import { createActions, getClientToolHandlers } from './actions';
|
|
12
|
-
import { fetchAgentInfo } from './api';
|
|
13
|
-
import { isTemplateConfig } from './types';
|
|
9
|
+
import { AgentChatContext } from './context.js';
|
|
10
|
+
import { chatReducer, initialState } from './reducer.js';
|
|
11
|
+
import { createActions, getClientToolHandlers } from './actions.js';
|
|
12
|
+
import { fetchAgentInfo } from './api.js';
|
|
13
|
+
import { isTemplateConfig } from './types.js';
|
|
14
14
|
function mergeHandlers(base, extra) {
|
|
15
15
|
if (!extra || extra.size === 0)
|
|
16
16
|
return base;
|
package/dist/agent/reducer.d.ts
CHANGED
|
@@ -3,6 +3,6 @@
|
|
|
3
3
|
*
|
|
4
4
|
* Pure reducer for managing agent chat state.
|
|
5
5
|
*/
|
|
6
|
-
import type { AgentChatState, ChatAction } from './types';
|
|
6
|
+
import type { AgentChatState, ChatAction } from './types.js';
|
|
7
7
|
export declare const initialState: AgentChatState;
|
|
8
8
|
export declare function chatReducer(state: AgentChatState, action: ChatAction): AgentChatState;
|
package/dist/agent/reducer.js
CHANGED
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
*
|
|
4
4
|
* Pure reducer for managing agent chat state.
|
|
5
5
|
*/
|
|
6
|
-
import { ChatStatusBusy, ChatStatusAwaitingInput, ChatStatusIdle } from '../types';
|
|
7
|
-
import { isRunInterrupted, isRunWorking } from '../utils';
|
|
6
|
+
import { ChatStatusBusy, ChatStatusAwaitingInput, ChatStatusIdle } from '../types.js';
|
|
7
|
+
import { isRunInterrupted, isRunWorking } from '../utils.js';
|
|
8
8
|
function deriveChatStatus(run) {
|
|
9
9
|
if (!run)
|
|
10
10
|
return ChatStatusIdle;
|
package/dist/agent/types.d.ts
CHANGED
|
@@ -4,11 +4,11 @@
|
|
|
4
4
|
* Public types for the Agent chat module.
|
|
5
5
|
*/
|
|
6
6
|
import type { Dispatch } from 'react';
|
|
7
|
-
import type { AgentRunDTO, AgentVersionDTO, AlwaysAllowOptionsDTO, AlwaysAllowResultDTO, ToolExplanationDTO, ChatAgentDTO, ChatDTO, ChatMessageDTO, ChatSettingsDTO, ChatSettingsRequest, AgentTool, AgentConfigInput as GeneratedAgentConfig, CoreAppConfigInput as CoreAppConfig, FileRef, ElicitResult } from '../types';
|
|
8
|
-
import type { HttpClient } from '../http/client';
|
|
9
|
-
import type { StreamableManager } from '../http/streamable';
|
|
10
|
-
import type { PollManager } from '../http/poll';
|
|
11
|
-
export type { FileRef } from '../types';
|
|
7
|
+
import type { AgentRunDTO, AgentVersionDTO, AlwaysAllowOptionsDTO, AlwaysAllowResultDTO, ToolExplanationDTO, ChatAgentDTO, ChatDTO, ChatMessageDTO, ChatSettingsDTO, ChatSettingsRequest, AgentTool, AgentConfigInput as GeneratedAgentConfig, CoreAppConfigInput as CoreAppConfig, FileRef, ElicitResult } from '../types.js';
|
|
8
|
+
import type { HttpClient } from '../http/client.js';
|
|
9
|
+
import type { StreamableManager } from '../http/streamable.js';
|
|
10
|
+
import type { PollManager } from '../http/poll.js';
|
|
11
|
+
export type { FileRef } from '../types.js';
|
|
12
12
|
/** The "always allow" option to save: a key from getAlwaysAllowOptions. */
|
|
13
13
|
export interface AlwaysAllowChoice {
|
|
14
14
|
option?: string;
|
package/dist/api/agents.d.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { HttpClient } from '../http/client';
|
|
2
|
-
import type { Response } from '../http/response';
|
|
3
|
-
import type { AgentUpdateBody } from './write-bodies';
|
|
4
|
-
import { FilesAPI } from './files';
|
|
5
|
-
import { ChatDTO, ChatMessageDTO,
|
|
1
|
+
import { HttpClient } from '../http/client.js';
|
|
2
|
+
import type { Response } from '../http/response.js';
|
|
3
|
+
import type { AgentUpdateBody } from './write-bodies.js';
|
|
4
|
+
import { FilesAPI } from './files.js';
|
|
5
|
+
import { ChannelContext, ChatDTO, ChatMessageDTO, LLMDelta, LLMOutput, AgentConfigInput as AgentConfig, AgentDTO, AgentVersionDTO, CreateAgentRequest, FileDTO as File, InterruptDTO, CursorListRequest, CursorListResponse } from '../types.js';
|
|
6
6
|
/** Internal tool definition returned by getInternalTools */
|
|
7
7
|
export interface InternalToolDefinition {
|
|
8
8
|
id: string;
|
|
@@ -67,11 +67,9 @@ export interface SendMessageOptions {
|
|
|
67
67
|
*/
|
|
68
68
|
signal?: AbortSignal;
|
|
69
69
|
/**
|
|
70
|
-
* The
|
|
71
|
-
*
|
|
72
|
-
*
|
|
73
|
-
* message; the API records it on the chat the first time it sees it, so
|
|
74
|
-
* later turns in that chat inherit the routing.
|
|
70
|
+
* @deprecated The API no longer reads a channel context from an agent run;
|
|
71
|
+
* a chat's routing comes from the server's own channel receivers. Accepted
|
|
72
|
+
* for compatibility and not sent.
|
|
75
73
|
*/
|
|
76
74
|
channel_context?: ChannelContext;
|
|
77
75
|
}
|
package/dist/api/agents.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { streamUntilTerminal } from '../http/stream-until-terminal';
|
|
2
|
-
import { PollManager } from '../http/poll';
|
|
3
|
-
import { createLLMDeltaAccumulator } from '../delta';
|
|
4
|
-
import { ToolTypeClient, ToolInvocationStatusAwaitingInput, ToolInvocationStatusInProgress, } from '../types';
|
|
5
|
-
import { isChatBusy, isMessageTerminal } from '../utils';
|
|
1
|
+
import { streamUntilTerminal } from '../http/stream-until-terminal.js';
|
|
2
|
+
import { PollManager } from '../http/poll.js';
|
|
3
|
+
import { createLLMDeltaAccumulator } from '../delta.js';
|
|
4
|
+
import { ToolTypeClient, ToolInvocationStatusAwaitingInput, ToolInvocationStatusInProgress, } from '../types.js';
|
|
5
|
+
import { isChatBusy, isMessageTerminal } from '../utils.js';
|
|
6
6
|
/**
|
|
7
7
|
* Decides when one sendMessage() turn is over.
|
|
8
8
|
*
|
|
@@ -90,7 +90,6 @@ export class Agent {
|
|
|
90
90
|
chat_id: this.chatId ?? undefined,
|
|
91
91
|
context: this.context,
|
|
92
92
|
input,
|
|
93
|
-
channel_context: options.channel_context,
|
|
94
93
|
...(isTemplate
|
|
95
94
|
? { agent: this.config }
|
|
96
95
|
: {
|
|
@@ -243,6 +242,43 @@ export class Agent {
|
|
|
243
242
|
// the delta names, so a tool-call-only turn never shows the previous
|
|
244
243
|
// message's text. Same attribution rule as the React hooks.
|
|
245
244
|
const deltaAccums = new Map();
|
|
245
|
+
const observeMessage = (message) => {
|
|
246
|
+
// A terminal message receives no further deltas.
|
|
247
|
+
if (isMessageTerminal(message.status))
|
|
248
|
+
deltaAccums.delete(message.id);
|
|
249
|
+
gate.observeMessage(message);
|
|
250
|
+
options.onMessage?.(message);
|
|
251
|
+
if (idlePending && gate.settled)
|
|
252
|
+
settle.resolve();
|
|
253
|
+
if (message.tool_invocations && options.onToolCall) {
|
|
254
|
+
for (const inv of message.tool_invocations) {
|
|
255
|
+
if (this.dispatchedToolCalls.has(inv.id))
|
|
256
|
+
continue;
|
|
257
|
+
if (inv.type === ToolTypeClient && (inv.status === ToolInvocationStatusInProgress || inv.status === ToolInvocationStatusAwaitingInput)) {
|
|
258
|
+
this.dispatchedToolCalls.add(inv.id);
|
|
259
|
+
options.onToolCall({
|
|
260
|
+
id: inv.id,
|
|
261
|
+
name: inv.function?.name || '',
|
|
262
|
+
args: inv.function?.arguments || {},
|
|
263
|
+
});
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
};
|
|
268
|
+
// The chat and its latest messages as the API has them now: what a
|
|
269
|
+
// dropped stream missed, or whether a closed stream's turn is over.
|
|
270
|
+
// Messages first, so this turn's terminal message can gate the idle chat.
|
|
271
|
+
const resync = async () => {
|
|
272
|
+
// Deltas sent while disconnected are gone; the messages replace them.
|
|
273
|
+
deltaAccums.clear();
|
|
274
|
+
const [{ data: chat }, { data: page }] = await Promise.all([
|
|
275
|
+
this.http.request('get', `/chats/${chatId}`),
|
|
276
|
+
this.http.request('get', `/chats/${chatId}/messages`),
|
|
277
|
+
]);
|
|
278
|
+
for (const message of page?.items ?? [])
|
|
279
|
+
observeMessage(message);
|
|
280
|
+
observeChat(chat);
|
|
281
|
+
};
|
|
246
282
|
return {
|
|
247
283
|
request: (init) => this.http.fetch(`/chats/${chatId}/stream`, init),
|
|
248
284
|
events: {
|
|
@@ -264,36 +300,11 @@ export class Agent {
|
|
|
264
300
|
seq: evt.seq,
|
|
265
301
|
});
|
|
266
302
|
},
|
|
267
|
-
chat_messages: (message) =>
|
|
268
|
-
// A terminal message receives no further deltas.
|
|
269
|
-
if (isMessageTerminal(message.status))
|
|
270
|
-
deltaAccums.delete(message.id);
|
|
271
|
-
gate.observeMessage(message);
|
|
272
|
-
options.onMessage?.(message);
|
|
273
|
-
if (idlePending && gate.settled)
|
|
274
|
-
settle.resolve();
|
|
275
|
-
if (message.tool_invocations && options.onToolCall) {
|
|
276
|
-
for (const inv of message.tool_invocations) {
|
|
277
|
-
if (this.dispatchedToolCalls.has(inv.id))
|
|
278
|
-
continue;
|
|
279
|
-
if (inv.type === ToolTypeClient && (inv.status === ToolInvocationStatusInProgress || inv.status === ToolInvocationStatusAwaitingInput)) {
|
|
280
|
-
this.dispatchedToolCalls.add(inv.id);
|
|
281
|
-
options.onToolCall({
|
|
282
|
-
id: inv.id,
|
|
283
|
-
name: inv.function?.name || '',
|
|
284
|
-
args: inv.function?.arguments || {},
|
|
285
|
-
});
|
|
286
|
-
}
|
|
287
|
-
}
|
|
288
|
-
}
|
|
289
|
-
},
|
|
303
|
+
chat_messages: (message) => observeMessage(message),
|
|
290
304
|
},
|
|
291
305
|
// The stream closed before the chat was seen idle: the chat itself
|
|
292
|
-
// says whether the turn is over.
|
|
293
|
-
reconcile:
|
|
294
|
-
const { data: chat } = await this.http.request('get', `/chats/${chatId}`);
|
|
295
|
-
observeChat(chat);
|
|
296
|
-
},
|
|
306
|
+
// says whether the turn is over. A reconnect resyncs the same way.
|
|
307
|
+
reconcile: resync,
|
|
297
308
|
closedMessage: 'Chat stream closed before the chat became idle',
|
|
298
309
|
// Stopped by disconnect()/abort or replaced by a newer stream: the
|
|
299
310
|
// caller stopped waiting on purpose.
|
package/dist/api/api-keys.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { HttpClient } from '../http/client';
|
|
2
|
-
import type { Response } from '../http/response';
|
|
3
|
-
import { ApiKeyDTO, CreateApiKeyRequest, CursorListRequest, CursorListResponse } from '../types';
|
|
1
|
+
import { HttpClient } from '../http/client.js';
|
|
2
|
+
import type { Response } from '../http/response.js';
|
|
3
|
+
import { ApiKeyDTO, CreateApiKeyRequest, CursorListRequest, CursorListResponse } from '../types.js';
|
|
4
4
|
/**
|
|
5
5
|
* API Keys API
|
|
6
6
|
*/
|
package/dist/api/apps.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { HttpClient } from '../http/client';
|
|
2
|
-
import type { Response } from '../http/response';
|
|
3
|
-
import type { AppPatchBody, AppUpdateBody } from './write-bodies';
|
|
4
|
-
import { AppDTO as App, AppVersionDTO, CursorListRequest, CursorListResponse, LicenseRecordDTO } from '../types';
|
|
1
|
+
import { HttpClient } from '../http/client.js';
|
|
2
|
+
import type { Response } from '../http/response.js';
|
|
3
|
+
import type { AppPatchBody, AppUpdateBody } from './write-bodies.js';
|
|
4
|
+
import { AppDTO as App, AppVersionDTO, CursorListRequest, CursorListResponse, LicenseRecordDTO } from '../types.js';
|
|
5
5
|
/**
|
|
6
6
|
* Apps API
|
|
7
7
|
*/
|
package/dist/api/artifacts.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { HttpClient } from '../http/client';
|
|
2
|
-
import type { Response } from '../http/response';
|
|
3
|
-
import { ArtifactDTO, ArtifactVersionDTO, ArtifactCreateRequest, ArtifactUpdateRequest, ArtifactPublishRequest, ArtifactContentResponse, CursorListRequest, CursorListResponse } from '../types';
|
|
1
|
+
import { HttpClient } from '../http/client.js';
|
|
2
|
+
import type { Response } from '../http/response.js';
|
|
3
|
+
import { ArtifactDTO, ArtifactVersionDTO, ArtifactCreateRequest, ArtifactUpdateRequest, ArtifactPublishRequest, ArtifactContentResponse, CursorListRequest, CursorListResponse } from '../types.js';
|
|
4
4
|
/**
|
|
5
5
|
* Artifacts API — small self-contained HTML/Markdown pages published to a
|
|
6
6
|
* URL, versioned, permissioned, and shareable.
|
package/dist/api/chats.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { HttpClient } from '../http/client';
|
|
2
|
-
import type { Response } from '../http/response';
|
|
3
|
-
import type { ChatUpdateBody } from './write-bodies';
|
|
4
|
-
import { ChatDTO as Chat, ChatMessageDTO, ChatSettingsDTO, ChatSettingsRequest, ChatTraceDTO, CursorListRequest, CursorListResponse } from '../types';
|
|
1
|
+
import { HttpClient } from '../http/client.js';
|
|
2
|
+
import type { Response } from '../http/response.js';
|
|
3
|
+
import type { ChatUpdateBody } from './write-bodies.js';
|
|
4
|
+
import { ChatDTO as Chat, ChatMessageDTO, ChatSettingsDTO, ChatSettingsRequest, ChatTraceDTO, CursorListRequest, CursorListResponse } from '../types.js';
|
|
5
5
|
/**
|
|
6
6
|
* Chats API
|
|
7
7
|
*/
|