@downcity/agent 1.1.64 → 1.1.69
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/bin/agent/Agent.d.ts.map +1 -1
- package/bin/agent/Agent.js +1 -0
- package/bin/agent/Agent.js.map +1 -1
- package/bin/agent/RemoteAgent.d.ts +8 -0
- package/bin/agent/RemoteAgent.d.ts.map +1 -1
- package/bin/agent/RemoteAgent.js +45 -14
- package/bin/agent/RemoteAgent.js.map +1 -1
- package/bin/model/CityModelAdapter.d.ts +4 -3
- package/bin/model/CityModelAdapter.d.ts.map +1 -1
- package/bin/model/CityModelAdapter.js +24 -410
- package/bin/model/CityModelAdapter.js.map +1 -1
- package/bin/rpc/Client.d.ts +49 -0
- package/bin/rpc/Client.d.ts.map +1 -1
- package/bin/rpc/Client.js +77 -0
- package/bin/rpc/Client.js.map +1 -1
- package/bin/rpc/Server.d.ts +3 -0
- package/bin/rpc/Server.d.ts.map +1 -1
- package/bin/rpc/Server.js +82 -0
- package/bin/rpc/Server.js.map +1 -1
- package/bin/session/SessionTitle.d.ts +2 -6
- package/bin/session/SessionTitle.d.ts.map +1 -1
- package/bin/session/SessionTitle.js +5 -27
- package/bin/session/SessionTitle.js.map +1 -1
- package/bin/session/browse/Browse.d.ts +1 -5
- package/bin/session/browse/Browse.d.ts.map +1 -1
- package/bin/session/browse/Browse.js +2 -8
- package/bin/session/browse/Browse.js.map +1 -1
- package/bin/session/index.d.ts +2 -2
- package/bin/session/index.d.ts.map +1 -1
- package/bin/session/index.js +2 -2
- package/bin/session/index.js.map +1 -1
- package/bin/types/agent/AgentTypes.d.ts +8 -0
- package/bin/types/agent/AgentTypes.d.ts.map +1 -1
- package/package.json +3 -2
- package/scripts/city-model-tool-loop.test.mjs +154 -44
- package/scripts/session-title-event.test.mjs +74 -7
- package/src/agent/Agent.ts +1 -0
- package/src/agent/RemoteAgent.ts +55 -12
- package/src/model/CityModelAdapter.ts +26 -501
- package/src/rpc/Client.ts +162 -0
- package/src/rpc/Server.ts +139 -0
- package/src/session/SessionTitle.ts +5 -34
- package/src/session/browse/Browse.ts +1 -9
- package/src/session/index.ts +0 -2
- package/src/types/agent/AgentTypes.ts +9 -0
- package/tsconfig.tsbuildinfo +1 -1
package/src/rpc/Client.ts
CHANGED
|
@@ -17,6 +17,16 @@ import type {
|
|
|
17
17
|
AgentSessionSummaryPage,
|
|
18
18
|
AgentSessionSystemSnapshot,
|
|
19
19
|
} from "@/types/agent/AgentTypes.js";
|
|
20
|
+
import type { JsonValue } from "@/types/common/Json.js";
|
|
21
|
+
import type {
|
|
22
|
+
PluginActionResult,
|
|
23
|
+
PluginAvailability,
|
|
24
|
+
PluginCommandResult,
|
|
25
|
+
PluginStateControlAction,
|
|
26
|
+
PluginStateControlResult,
|
|
27
|
+
PluginStateSnapshot,
|
|
28
|
+
PluginView,
|
|
29
|
+
} from "@/plugin/types/Plugin.js";
|
|
20
30
|
import type { AgentSessionEvent } from "@/types/sdk/AgentSessionEvent.js";
|
|
21
31
|
import type { AgentSessionPromptInput } from "@/types/sdk/AgentSessionPrompt.js";
|
|
22
32
|
|
|
@@ -82,6 +92,52 @@ type RpcClientRequest =
|
|
|
82
92
|
params: {
|
|
83
93
|
subscriptionId: string;
|
|
84
94
|
};
|
|
95
|
+
}
|
|
96
|
+
| {
|
|
97
|
+
id: string;
|
|
98
|
+
method: "internal.status.get";
|
|
99
|
+
}
|
|
100
|
+
| {
|
|
101
|
+
id: string;
|
|
102
|
+
method: "internal.plugins.catalog";
|
|
103
|
+
}
|
|
104
|
+
| {
|
|
105
|
+
id: string;
|
|
106
|
+
method: "internal.plugins.list";
|
|
107
|
+
}
|
|
108
|
+
| {
|
|
109
|
+
id: string;
|
|
110
|
+
method: "internal.plugins.control";
|
|
111
|
+
params: {
|
|
112
|
+
pluginName: string;
|
|
113
|
+
action: PluginStateControlAction;
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
| {
|
|
117
|
+
id: string;
|
|
118
|
+
method: "internal.plugins.command";
|
|
119
|
+
params: {
|
|
120
|
+
pluginName: string;
|
|
121
|
+
command: string;
|
|
122
|
+
payload?: JsonValue;
|
|
123
|
+
schedule?: JsonValue;
|
|
124
|
+
};
|
|
125
|
+
}
|
|
126
|
+
| {
|
|
127
|
+
id: string;
|
|
128
|
+
method: "internal.plugins.availability";
|
|
129
|
+
params: {
|
|
130
|
+
pluginName: string;
|
|
131
|
+
};
|
|
132
|
+
}
|
|
133
|
+
| {
|
|
134
|
+
id: string;
|
|
135
|
+
method: "internal.plugins.action";
|
|
136
|
+
params: {
|
|
137
|
+
pluginName: string;
|
|
138
|
+
actionName: string;
|
|
139
|
+
payload?: JsonValue;
|
|
140
|
+
};
|
|
85
141
|
};
|
|
86
142
|
|
|
87
143
|
type RpcResponseFrame = {
|
|
@@ -288,6 +344,112 @@ export class RpcClient {
|
|
|
288
344
|
};
|
|
289
345
|
}
|
|
290
346
|
|
|
347
|
+
/**
|
|
348
|
+
* 读取 Agent 内部状态。
|
|
349
|
+
*/
|
|
350
|
+
async get_internal_status(): Promise<{ status: string }> {
|
|
351
|
+
return await this.request<{ status: string }>({
|
|
352
|
+
method: "internal.status.get",
|
|
353
|
+
});
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
/**
|
|
357
|
+
* 列出 Agent runtime 注册的 plugin catalog。
|
|
358
|
+
*/
|
|
359
|
+
async list_internal_plugin_catalog(): Promise<PluginView[]> {
|
|
360
|
+
const data = await this.request<{ plugins: PluginView[] }>({
|
|
361
|
+
method: "internal.plugins.catalog",
|
|
362
|
+
});
|
|
363
|
+
return Array.isArray(data.plugins) ? data.plugins : [];
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
/**
|
|
367
|
+
* 列出 Agent runtime 内 plugin 状态。
|
|
368
|
+
*/
|
|
369
|
+
async list_internal_plugin_states(): Promise<PluginStateSnapshot[]> {
|
|
370
|
+
const data = await this.request<{ plugins: PluginStateSnapshot[] }>({
|
|
371
|
+
method: "internal.plugins.list",
|
|
372
|
+
});
|
|
373
|
+
return Array.isArray(data.plugins) ? data.plugins : [];
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
/**
|
|
377
|
+
* 控制 Agent runtime 内 plugin 生命周期。
|
|
378
|
+
*/
|
|
379
|
+
async control_internal_plugin(params: {
|
|
380
|
+
plugin_name: string;
|
|
381
|
+
action: PluginStateControlAction;
|
|
382
|
+
}): Promise<PluginStateControlResult> {
|
|
383
|
+
return await this.request<PluginStateControlResult>({
|
|
384
|
+
method: "internal.plugins.control",
|
|
385
|
+
params: {
|
|
386
|
+
pluginName: params.plugin_name,
|
|
387
|
+
action: params.action,
|
|
388
|
+
},
|
|
389
|
+
});
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
/**
|
|
393
|
+
* 执行 Agent runtime 内 plugin command。
|
|
394
|
+
*/
|
|
395
|
+
async run_internal_plugin_command(params: {
|
|
396
|
+
plugin_name: string;
|
|
397
|
+
command: string;
|
|
398
|
+
payload?: JsonValue;
|
|
399
|
+
schedule?: JsonValue;
|
|
400
|
+
}): Promise<PluginCommandResult & { plugin?: PluginStateSnapshot }> {
|
|
401
|
+
return await this.request<PluginCommandResult & { plugin?: PluginStateSnapshot }>({
|
|
402
|
+
method: "internal.plugins.command",
|
|
403
|
+
params: {
|
|
404
|
+
pluginName: params.plugin_name,
|
|
405
|
+
command: params.command,
|
|
406
|
+
...(params.payload !== undefined ? { payload: params.payload } : {}),
|
|
407
|
+
...(params.schedule !== undefined ? { schedule: params.schedule } : {}),
|
|
408
|
+
},
|
|
409
|
+
});
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
/**
|
|
413
|
+
* 检查 Agent runtime 内 plugin 可用性。
|
|
414
|
+
*/
|
|
415
|
+
async get_internal_plugin_availability(
|
|
416
|
+
plugin_name: string,
|
|
417
|
+
): Promise<PluginAvailability> {
|
|
418
|
+
const data = await this.request<{
|
|
419
|
+
availability: PluginAvailability;
|
|
420
|
+
}>({
|
|
421
|
+
method: "internal.plugins.availability",
|
|
422
|
+
params: {
|
|
423
|
+
pluginName: plugin_name,
|
|
424
|
+
},
|
|
425
|
+
});
|
|
426
|
+
return data.availability;
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
/**
|
|
430
|
+
* 执行 Agent runtime 内 plugin action。
|
|
431
|
+
*/
|
|
432
|
+
async run_internal_plugin_action(params: {
|
|
433
|
+
plugin_name: string;
|
|
434
|
+
action_name: string;
|
|
435
|
+
payload?: JsonValue;
|
|
436
|
+
}): Promise<PluginActionResult<JsonValue> & {
|
|
437
|
+
pluginName?: string;
|
|
438
|
+
actionName?: string;
|
|
439
|
+
}> {
|
|
440
|
+
return await this.request<PluginActionResult<JsonValue> & {
|
|
441
|
+
pluginName?: string;
|
|
442
|
+
actionName?: string;
|
|
443
|
+
}>({
|
|
444
|
+
method: "internal.plugins.action",
|
|
445
|
+
params: {
|
|
446
|
+
pluginName: params.plugin_name,
|
|
447
|
+
actionName: params.action_name,
|
|
448
|
+
...(params.payload !== undefined ? { payload: params.payload } : {}),
|
|
449
|
+
},
|
|
450
|
+
});
|
|
451
|
+
}
|
|
452
|
+
|
|
291
453
|
/**
|
|
292
454
|
* 关闭底层连接。
|
|
293
455
|
*/
|
package/src/rpc/Server.ts
CHANGED
|
@@ -14,6 +14,15 @@ import type {
|
|
|
14
14
|
} from "@/types/agent/AgentTypes.js";
|
|
15
15
|
import type { AgentSessionPromptInput } from "@/types/sdk/AgentSessionPrompt.js";
|
|
16
16
|
import type { AgentSessionEvent } from "@/types/sdk/AgentSessionEvent.js";
|
|
17
|
+
import type { AgentContext } from "@/types/runtime/agent/AgentContext.js";
|
|
18
|
+
import type { JsonValue } from "@/types/common/Json.js";
|
|
19
|
+
import type { PluginStateControlAction } from "@/plugin/types/Plugin.js";
|
|
20
|
+
import {
|
|
21
|
+
controlPluginState,
|
|
22
|
+
listPluginStates,
|
|
23
|
+
} from "@/plugin/core/PluginStateController.js";
|
|
24
|
+
import { parsePluginCommandRequestBody } from "@/plugin/core/PluginCommandRequest.js";
|
|
25
|
+
import { runPluginCommand } from "@/plugin/core/PluginActionRunner.js";
|
|
17
26
|
|
|
18
27
|
type RpcSessionRequest =
|
|
19
28
|
| {
|
|
@@ -84,6 +93,52 @@ type RpcSessionRequest =
|
|
|
84
93
|
params: {
|
|
85
94
|
subscriptionId: string;
|
|
86
95
|
};
|
|
96
|
+
}
|
|
97
|
+
| {
|
|
98
|
+
id: string;
|
|
99
|
+
method: "internal.status.get";
|
|
100
|
+
}
|
|
101
|
+
| {
|
|
102
|
+
id: string;
|
|
103
|
+
method: "internal.plugins.catalog";
|
|
104
|
+
}
|
|
105
|
+
| {
|
|
106
|
+
id: string;
|
|
107
|
+
method: "internal.plugins.list";
|
|
108
|
+
}
|
|
109
|
+
| {
|
|
110
|
+
id: string;
|
|
111
|
+
method: "internal.plugins.control";
|
|
112
|
+
params: {
|
|
113
|
+
pluginName: string;
|
|
114
|
+
action: PluginStateControlAction;
|
|
115
|
+
};
|
|
116
|
+
}
|
|
117
|
+
| {
|
|
118
|
+
id: string;
|
|
119
|
+
method: "internal.plugins.command";
|
|
120
|
+
params: {
|
|
121
|
+
pluginName: string;
|
|
122
|
+
command: string;
|
|
123
|
+
payload?: JsonValue;
|
|
124
|
+
schedule?: JsonValue;
|
|
125
|
+
};
|
|
126
|
+
}
|
|
127
|
+
| {
|
|
128
|
+
id: string;
|
|
129
|
+
method: "internal.plugins.availability";
|
|
130
|
+
params: {
|
|
131
|
+
pluginName: string;
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
| {
|
|
135
|
+
id: string;
|
|
136
|
+
method: "internal.plugins.action";
|
|
137
|
+
params: {
|
|
138
|
+
pluginName: string;
|
|
139
|
+
actionName: string;
|
|
140
|
+
payload?: JsonValue;
|
|
141
|
+
};
|
|
87
142
|
};
|
|
88
143
|
|
|
89
144
|
type RpcSuccessFrame = {
|
|
@@ -119,6 +174,8 @@ export interface RpcServerStartOptions {
|
|
|
119
174
|
host: string;
|
|
120
175
|
/** Session 集合访问口。 */
|
|
121
176
|
sessionCollection: AgentSessionCollection;
|
|
177
|
+
/** Agent 上下文访问口。 */
|
|
178
|
+
getAgentContext?: () => AgentContext;
|
|
122
179
|
}
|
|
123
180
|
|
|
124
181
|
/**
|
|
@@ -143,7 +200,9 @@ export interface RpcServerInstance {
|
|
|
143
200
|
export async function startRpcServer(
|
|
144
201
|
options: RpcServerStartOptions,
|
|
145
202
|
): Promise<RpcServerInstance> {
|
|
203
|
+
const sockets = new Set<net.Socket>();
|
|
146
204
|
const server = net.createServer((socket) => {
|
|
205
|
+
sockets.add(socket);
|
|
147
206
|
const subscriptions = new Map<string, SocketSubscription>();
|
|
148
207
|
let buffered = "";
|
|
149
208
|
|
|
@@ -241,6 +300,72 @@ export async function startRpcServer(
|
|
|
241
300
|
writeSuccess(request.id, { unsubscribed: true });
|
|
242
301
|
return;
|
|
243
302
|
}
|
|
303
|
+
case "internal.status.get": {
|
|
304
|
+
writeSuccess(request.id, { status: "ok" });
|
|
305
|
+
return;
|
|
306
|
+
}
|
|
307
|
+
case "internal.plugins.catalog": {
|
|
308
|
+
const context = requireAgentContext(options);
|
|
309
|
+
writeSuccess(request.id, {
|
|
310
|
+
plugins: context.plugins.list(),
|
|
311
|
+
});
|
|
312
|
+
return;
|
|
313
|
+
}
|
|
314
|
+
case "internal.plugins.list": {
|
|
315
|
+
const context = requireAgentContext(options);
|
|
316
|
+
writeSuccess(request.id, {
|
|
317
|
+
plugins: listPluginStates({ context }),
|
|
318
|
+
});
|
|
319
|
+
return;
|
|
320
|
+
}
|
|
321
|
+
case "internal.plugins.control": {
|
|
322
|
+
const context = requireAgentContext(options);
|
|
323
|
+
const result = await controlPluginState({
|
|
324
|
+
pluginName: request.params.pluginName,
|
|
325
|
+
action: request.params.action,
|
|
326
|
+
context,
|
|
327
|
+
});
|
|
328
|
+
writeSuccess(request.id, result);
|
|
329
|
+
return;
|
|
330
|
+
}
|
|
331
|
+
case "internal.plugins.command": {
|
|
332
|
+
const context = requireAgentContext(options);
|
|
333
|
+
const body = parsePluginCommandRequestBody(request.params);
|
|
334
|
+
const result = await runPluginCommand({
|
|
335
|
+
pluginName: body.pluginName,
|
|
336
|
+
command: body.command,
|
|
337
|
+
payload: body.payload,
|
|
338
|
+
schedule: body.schedule,
|
|
339
|
+
context,
|
|
340
|
+
});
|
|
341
|
+
writeSuccess(request.id, result);
|
|
342
|
+
return;
|
|
343
|
+
}
|
|
344
|
+
case "internal.plugins.availability": {
|
|
345
|
+
const context = requireAgentContext(options);
|
|
346
|
+
const availability = await context.plugins.availability(
|
|
347
|
+
request.params.pluginName,
|
|
348
|
+
);
|
|
349
|
+
writeSuccess(request.id, {
|
|
350
|
+
pluginName: request.params.pluginName,
|
|
351
|
+
availability,
|
|
352
|
+
});
|
|
353
|
+
return;
|
|
354
|
+
}
|
|
355
|
+
case "internal.plugins.action": {
|
|
356
|
+
const context = requireAgentContext(options);
|
|
357
|
+
const result = await context.plugins.runAction({
|
|
358
|
+
plugin: request.params.pluginName,
|
|
359
|
+
action: request.params.actionName,
|
|
360
|
+
payload: request.params.payload,
|
|
361
|
+
});
|
|
362
|
+
writeSuccess(request.id, {
|
|
363
|
+
...result,
|
|
364
|
+
pluginName: request.params.pluginName,
|
|
365
|
+
actionName: request.params.actionName,
|
|
366
|
+
});
|
|
367
|
+
return;
|
|
368
|
+
}
|
|
244
369
|
}
|
|
245
370
|
} catch (error) {
|
|
246
371
|
writeError(request.id, error);
|
|
@@ -273,6 +398,7 @@ export async function startRpcServer(
|
|
|
273
398
|
cleanupSubscriptions();
|
|
274
399
|
});
|
|
275
400
|
socket.on("close", () => {
|
|
401
|
+
sockets.delete(socket);
|
|
276
402
|
cleanupSubscriptions();
|
|
277
403
|
});
|
|
278
404
|
socket.on("end", () => {
|
|
@@ -294,9 +420,22 @@ export async function startRpcServer(
|
|
|
294
420
|
url: `rpc://${options.host}:${options.port}`,
|
|
295
421
|
server,
|
|
296
422
|
async stop(): Promise<void> {
|
|
423
|
+
// 关键点(中文):RPC 是长连接;停止 server 时必须主动关闭现有 socket。
|
|
424
|
+
for (const socket of sockets) {
|
|
425
|
+
socket.destroy();
|
|
426
|
+
}
|
|
427
|
+
sockets.clear();
|
|
297
428
|
await new Promise<void>((resolve) => {
|
|
298
429
|
server.close(() => resolve());
|
|
299
430
|
});
|
|
300
431
|
},
|
|
301
432
|
};
|
|
302
433
|
}
|
|
434
|
+
|
|
435
|
+
function requireAgentContext(options: RpcServerStartOptions): AgentContext {
|
|
436
|
+
const context = options.getAgentContext?.();
|
|
437
|
+
if (!context) {
|
|
438
|
+
throw new Error("Agent RPC server was started without AgentContext");
|
|
439
|
+
}
|
|
440
|
+
return context;
|
|
441
|
+
}
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
*
|
|
4
4
|
* 关键点(中文)
|
|
5
5
|
* - session title 是 `meta.json` 顶层字段,列表与详情都以它为准。
|
|
6
|
-
* -
|
|
7
|
-
* -
|
|
6
|
+
* - title 默认允许为空;只有模型成功生成标题时才会写入。
|
|
7
|
+
* - 当 title 仍为空时,后续执行链路可以再次尝试生成。
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
10
|
import { generateText, type LanguageModel } from "ai";
|
|
@@ -16,7 +16,6 @@ import {
|
|
|
16
16
|
writeSessionMetadata,
|
|
17
17
|
} from "@/session/storage/Metadata.js";
|
|
18
18
|
|
|
19
|
-
const FALLBACK_SESSION_TITLE_MAX_CHARS = 60;
|
|
20
19
|
const GENERATED_SESSION_TITLE_MAX_CHARS = 24;
|
|
21
20
|
|
|
22
21
|
/**
|
|
@@ -100,20 +99,6 @@ function normalizeGeneratedTitle(input: string): string | undefined {
|
|
|
100
99
|
: undefined;
|
|
101
100
|
}
|
|
102
101
|
|
|
103
|
-
/**
|
|
104
|
-
* 从首条用户消息推导 fallback 标题。
|
|
105
|
-
*/
|
|
106
|
-
export function resolveFallbackSessionTitle(
|
|
107
|
-
messages: SessionMessageV1[],
|
|
108
|
-
): string | undefined {
|
|
109
|
-
const firstUserText = resolveFirstUserText(messages);
|
|
110
|
-
const title = truncateTitle(
|
|
111
|
-
firstUserText,
|
|
112
|
-
FALLBACK_SESSION_TITLE_MAX_CHARS,
|
|
113
|
-
);
|
|
114
|
-
return normalizeSessionTitle(title);
|
|
115
|
-
}
|
|
116
|
-
|
|
117
102
|
async function generateSessionTitle(input: {
|
|
118
103
|
/**
|
|
119
104
|
* 当前模型实例。
|
|
@@ -154,32 +139,18 @@ export async function ensureSessionTitle(
|
|
|
154
139
|
if (current.title) return current;
|
|
155
140
|
|
|
156
141
|
const firstUserText = resolveFirstUserText(input.messages);
|
|
157
|
-
const fallbackTitle = resolveFallbackSessionTitle(input.messages);
|
|
158
|
-
if (!fallbackTitle) return current;
|
|
159
|
-
|
|
160
|
-
const fallbackMeta: SessionHistoryMetaV1 = {
|
|
161
|
-
...current,
|
|
162
|
-
title: fallbackTitle,
|
|
163
|
-
};
|
|
164
|
-
await writeSessionMetadata({
|
|
165
|
-
projectRoot: input.projectRoot,
|
|
166
|
-
agentId: input.agentId,
|
|
167
|
-
sessionId: input.sessionId,
|
|
168
|
-
meta: fallbackMeta,
|
|
169
|
-
});
|
|
170
|
-
|
|
171
142
|
if (input.generate !== true || !input.model || !firstUserText) {
|
|
172
|
-
return
|
|
143
|
+
return current;
|
|
173
144
|
}
|
|
174
145
|
|
|
175
146
|
const generatedTitle = await generateSessionTitle({
|
|
176
147
|
model: input.model,
|
|
177
148
|
firstUserText,
|
|
178
149
|
});
|
|
179
|
-
if (!generatedTitle) return
|
|
150
|
+
if (!generatedTitle) return current;
|
|
180
151
|
|
|
181
152
|
const generatedMeta: SessionHistoryMetaV1 = {
|
|
182
|
-
...
|
|
153
|
+
...current,
|
|
183
154
|
title: generatedTitle,
|
|
184
155
|
};
|
|
185
156
|
await writeSessionMetadata({
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
*
|
|
4
4
|
* 关键点(中文)
|
|
5
5
|
* - 统一负责 session 列表摘要、session 详情与 history 分页的投影逻辑。
|
|
6
|
-
* -
|
|
6
|
+
* - session title 允许为空;浏览层不会再从首条 user message 推导 fallback title。
|
|
7
7
|
* - 面向 SDK / RemoteAgent / HTTP route 复用,避免在多个入口重复拼列表与分页语义。
|
|
8
8
|
* - 这里不持有运行态状态;执行状态等动态信息通过调用参数显式注入。
|
|
9
9
|
*/
|
|
@@ -36,7 +36,6 @@ import { getSdkAgentSessionsRootDirPath } from "@/session/storage/Paths.js";
|
|
|
36
36
|
import { readSessionMetadata } from "@/session/storage/Metadata.js";
|
|
37
37
|
import {
|
|
38
38
|
ensureSessionTitle,
|
|
39
|
-
resolveFallbackSessionTitle,
|
|
40
39
|
} from "@/session/SessionTitle.js";
|
|
41
40
|
|
|
42
41
|
type AnyUiPart = UIMessagePart<Record<string, never>, Record<string, never>>;
|
|
@@ -185,13 +184,6 @@ export function resolveSessionMessagePreview(message: SessionMessageV1): string
|
|
|
185
184
|
return extractAssistantToolSummary(message);
|
|
186
185
|
}
|
|
187
186
|
|
|
188
|
-
/**
|
|
189
|
-
* 推导当前 session 的可读标题。
|
|
190
|
-
*/
|
|
191
|
-
export function resolveSessionTitle(messages: SessionMessageV1[]): string | undefined {
|
|
192
|
-
return resolveFallbackSessionTitle(messages);
|
|
193
|
-
}
|
|
194
|
-
|
|
195
187
|
function resolveToolName(part: ToolPartCompatShape, aiToolName?: string): string {
|
|
196
188
|
const fromAi = String(aiToolName || "").trim();
|
|
197
189
|
if (fromAi) return fromAi;
|
package/src/session/index.ts
CHANGED
|
@@ -29,7 +29,6 @@ export {
|
|
|
29
29
|
} from "./storage/Metadata.js";
|
|
30
30
|
export {
|
|
31
31
|
ensureSessionTitle,
|
|
32
|
-
resolveFallbackSessionTitle,
|
|
33
32
|
} from "./SessionTitle.js";
|
|
34
33
|
export {
|
|
35
34
|
persistSdkAssistantResult,
|
|
@@ -44,6 +43,5 @@ export {
|
|
|
44
43
|
listAgentSessionSummaryPage,
|
|
45
44
|
loadSessionMessagesFromPath,
|
|
46
45
|
resolveSessionMessagePreview,
|
|
47
|
-
resolveSessionTitle,
|
|
48
46
|
toSessionTimelineEvents,
|
|
49
47
|
} from "./browse/Browse.js";
|
|
@@ -196,6 +196,15 @@ export interface RemoteAgentOptions {
|
|
|
196
196
|
* 或 `rpc://127.0.0.1:5314`
|
|
197
197
|
*/
|
|
198
198
|
url: string;
|
|
199
|
+
|
|
200
|
+
/**
|
|
201
|
+
* 访问远程 HTTP Agent 时使用的 Bearer token。
|
|
202
|
+
*
|
|
203
|
+
* 关键点(中文)
|
|
204
|
+
* - 仅 `http://` / `https://` transport 会携带该 token。
|
|
205
|
+
* - `rpc://` 是本机内部直连通道,不读取也不发送 token。
|
|
206
|
+
*/
|
|
207
|
+
token?: string;
|
|
199
208
|
}
|
|
200
209
|
|
|
201
210
|
/**
|