pi2dsh 0.10.0 → 0.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +262 -151
- package/README.zh.md +224 -133
- package/dist/host.mjs +1 -1
- package/dist/index.mjs +1 -1
- package/dist/{runtime-Ce3PTbWU.mjs → runtime-DFD6u4NO.mjs} +132 -7
- package/dist/runtime-DFD6u4NO.mjs.map +1 -0
- package/dist/runtime.d.mts.map +1 -1
- package/dist/runtime.mjs +1 -1
- package/package.json +4 -2
- package/dist/runtime-Ce3PTbWU.mjs.map +0 -1
|
@@ -303,9 +303,22 @@ var PiSessionBridge = class {
|
|
|
303
303
|
//#endregion
|
|
304
304
|
//#region src/subagent-bridge.ts
|
|
305
305
|
let subagentSerial = 0;
|
|
306
|
+
/** Flatten a Pi message's content to text for transcript seeding. */
|
|
307
|
+
function piMessageText(message) {
|
|
308
|
+
const content = message.content;
|
|
309
|
+
if (typeof content === "string") return content;
|
|
310
|
+
if (!Array.isArray(content)) return "";
|
|
311
|
+
return content.map((block) => {
|
|
312
|
+
const record = block;
|
|
313
|
+
if (record?.type === "text" && typeof record.text === "string") return record.text;
|
|
314
|
+
if (record?.type === "toolCall" && typeof record.name === "string") return `(tool ${record.name})`;
|
|
315
|
+
return "";
|
|
316
|
+
}).filter((text) => text.length > 0).join("\n");
|
|
317
|
+
}
|
|
306
318
|
var PiBridgedAgentSession = class {
|
|
307
319
|
agent = {};
|
|
308
320
|
messages = [];
|
|
321
|
+
#seed = [];
|
|
309
322
|
#host;
|
|
310
323
|
#handle;
|
|
311
324
|
#session;
|
|
@@ -313,6 +326,10 @@ var PiBridgedAgentSession = class {
|
|
|
313
326
|
#subscribers = /* @__PURE__ */ new Set();
|
|
314
327
|
#disposers = [];
|
|
315
328
|
#activeToolNames;
|
|
329
|
+
#state;
|
|
330
|
+
#model;
|
|
331
|
+
#streaming = false;
|
|
332
|
+
#pendingToolCalls = /* @__PURE__ */ new Set();
|
|
316
333
|
#sessionName = "";
|
|
317
334
|
#turns = 0;
|
|
318
335
|
#aborted = false;
|
|
@@ -341,6 +358,51 @@ var PiBridgedAgentSession = class {
|
|
|
341
358
|
return next();
|
|
342
359
|
});
|
|
343
360
|
this.#disposers.push(offEvents, offPre);
|
|
361
|
+
const session = this;
|
|
362
|
+
this.#state = {
|
|
363
|
+
get systemPrompt() {
|
|
364
|
+
return "";
|
|
365
|
+
},
|
|
366
|
+
get model() {
|
|
367
|
+
return session.#model;
|
|
368
|
+
},
|
|
369
|
+
get thinkingLevel() {
|
|
370
|
+
return "off";
|
|
371
|
+
},
|
|
372
|
+
get tools() {
|
|
373
|
+
return [...session.#tools];
|
|
374
|
+
},
|
|
375
|
+
set tools(_next) {},
|
|
376
|
+
get messages() {
|
|
377
|
+
return [...session.messages];
|
|
378
|
+
},
|
|
379
|
+
set messages(next) {
|
|
380
|
+
session.#assignTranscript(next);
|
|
381
|
+
},
|
|
382
|
+
get isStreaming() {
|
|
383
|
+
return session.#streaming;
|
|
384
|
+
},
|
|
385
|
+
get pendingToolCalls() {
|
|
386
|
+
return new Set(session.#pendingToolCalls);
|
|
387
|
+
}
|
|
388
|
+
};
|
|
389
|
+
this.agent.state = this.#state;
|
|
390
|
+
}
|
|
391
|
+
/** Pi's AgentState projection, shared by `session.state` and `session.agent.state`. */
|
|
392
|
+
get state() {
|
|
393
|
+
return this.#state;
|
|
394
|
+
}
|
|
395
|
+
/**
|
|
396
|
+
* Pi's `state.messages = …` assignment. Messages already present in this
|
|
397
|
+
* child's projection stay as they are (they are durable); anything new is
|
|
398
|
+
* queued and delivered with the next prompt so the child model really sees
|
|
399
|
+
* the transcript the package seeded.
|
|
400
|
+
*/
|
|
401
|
+
#assignTranscript(next) {
|
|
402
|
+
const identity = (message) => JSON.stringify([message.role, message.content]);
|
|
403
|
+
const known = new Set(this.messages.map(identity));
|
|
404
|
+
this.#seed = next.filter((message) => !known.has(identity(message)));
|
|
405
|
+
for (const message of this.#seed) this.messages.push(message);
|
|
344
406
|
}
|
|
345
407
|
#project(event) {
|
|
346
408
|
const type = event.type;
|
|
@@ -349,12 +411,27 @@ var PiBridgedAgentSession = class {
|
|
|
349
411
|
handler(piEvent);
|
|
350
412
|
} catch {}
|
|
351
413
|
};
|
|
352
|
-
if (type === "turn/start")
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
414
|
+
if (type === "turn/start") {
|
|
415
|
+
this.#streaming = true;
|
|
416
|
+
emit({
|
|
417
|
+
type: "turn_start",
|
|
418
|
+
turnIndex: Number(event.data.turn ?? 1) - 1
|
|
419
|
+
});
|
|
420
|
+
}
|
|
421
|
+
if (type === "request/header") {
|
|
422
|
+
const config = event.data.config ?? {};
|
|
423
|
+
if (typeof config.model === "string") this.#model = {
|
|
424
|
+
id: config.model,
|
|
425
|
+
provider: String(config.provider ?? "")
|
|
426
|
+
};
|
|
427
|
+
}
|
|
428
|
+
if (type === "tools/result" || type === "tool/result") {
|
|
429
|
+
const data = event.data;
|
|
430
|
+
this.#pendingToolCalls.delete(String(data.callId ?? ""));
|
|
431
|
+
}
|
|
356
432
|
if (type === "tool/call") {
|
|
357
433
|
const data = event.data;
|
|
434
|
+
this.#pendingToolCalls.add(String(data.callId ?? ""));
|
|
358
435
|
let args = {};
|
|
359
436
|
try {
|
|
360
437
|
args = JSON.parse(String(data.arguments ?? "{}"));
|
|
@@ -401,6 +478,8 @@ var PiBridgedAgentSession = class {
|
|
|
401
478
|
}
|
|
402
479
|
if (type === "turn/end") {
|
|
403
480
|
this.#turns += 1;
|
|
481
|
+
this.#streaming = false;
|
|
482
|
+
this.#pendingToolCalls.clear();
|
|
404
483
|
emit({
|
|
405
484
|
type: "turn_end",
|
|
406
485
|
turnIndex: Number(event.data.turn ?? 1) - 1,
|
|
@@ -417,6 +496,28 @@ var PiBridgedAgentSession = class {
|
|
|
417
496
|
return () => this.#subscribers.delete(handler);
|
|
418
497
|
}
|
|
419
498
|
async prompt(text) {
|
|
499
|
+
if (this.#seed.length > 0) {
|
|
500
|
+
const seeded = this.#seed;
|
|
501
|
+
this.#seed = [];
|
|
502
|
+
const rendered = seeded.map((message) => {
|
|
503
|
+
const role = String(message.role ?? "user");
|
|
504
|
+
const content = piMessageText(message);
|
|
505
|
+
return content.length === 0 ? void 0 : `[${role}]: ${content}`;
|
|
506
|
+
}).filter((line) => line !== void 0);
|
|
507
|
+
if (rendered.length > 0) {
|
|
508
|
+
const seedBlocks = await this.#host.piContentToDsh([{
|
|
509
|
+
type: "text",
|
|
510
|
+
text: `<prior-conversation>\n${rendered.join("\n\n")}\n</prior-conversation>`
|
|
511
|
+
}]);
|
|
512
|
+
this.#host.deliver(this.#handle.agent, createUserMessage({
|
|
513
|
+
content: seedBlocks,
|
|
514
|
+
source: {
|
|
515
|
+
kind: "plugin",
|
|
516
|
+
plugin: this.#host.messageSource
|
|
517
|
+
}
|
|
518
|
+
}), "inject");
|
|
519
|
+
}
|
|
520
|
+
}
|
|
420
521
|
const blocks = await this.#host.piContentToDsh([{
|
|
421
522
|
type: "text",
|
|
422
523
|
text: String(text)
|
|
@@ -496,6 +597,18 @@ var PiBridgedAgentSession = class {
|
|
|
496
597
|
await this.#handle.dispose();
|
|
497
598
|
}
|
|
498
599
|
};
|
|
600
|
+
/**
|
|
601
|
+
* The name DSH's own child catalog shows for a side thread. Pi packages rarely
|
|
602
|
+
* label a child, so the package that started it is the honest fallback: with
|
|
603
|
+
* several Pi packages installed, their threads stay apart in one list.
|
|
604
|
+
* @param requested - a label the calling package supplied, if any.
|
|
605
|
+
* @param packageName - the Pi package the call came from.
|
|
606
|
+
*/
|
|
607
|
+
function childLabel(requested, packageName) {
|
|
608
|
+
if (typeof requested === "string" && requested.trim().length > 0) return requested.trim().slice(0, 80);
|
|
609
|
+
const owner = packageName?.trim();
|
|
610
|
+
return owner === void 0 || owner.length === 0 ? "Pi side conversation" : `${owner} side conversation`;
|
|
611
|
+
}
|
|
499
612
|
async function createBridgedAgentSession(host, options) {
|
|
500
613
|
const agents = host.cordis.get("agents");
|
|
501
614
|
if (agents?.create === void 0) throw new Error("pi2dsh: createAgentSession() needs the DSH agent registry in the host composition");
|
|
@@ -536,6 +649,17 @@ async function createBridgedAgentSession(host, options) {
|
|
|
536
649
|
throw new Error(`pi2dsh: subagent creation needs the DSH host loop (model runtime) to provide the agent factory; this composition cannot run one (${error instanceof Error ? error.message : String(error)})`);
|
|
537
650
|
}
|
|
538
651
|
const tools = [...Array.isArray(options.tools) ? options.tools : [], ...Array.isArray(options.customTools) ? options.customTools : []];
|
|
652
|
+
const childSession = handle.agent.session;
|
|
653
|
+
if (typeof childSession?.append === "function") try {
|
|
654
|
+
childSession.append("subagent/descriptor", {
|
|
655
|
+
version: 2,
|
|
656
|
+
mode: "continuable",
|
|
657
|
+
provider: "pi2dsh",
|
|
658
|
+
label: childLabel(options.label, host.packageName)
|
|
659
|
+
});
|
|
660
|
+
} catch (error) {
|
|
661
|
+
host.cordis.logger?.warn?.(`[pi2dsh] child session could not record its subagent identity: ${error instanceof Error ? error.message : String(error)}`);
|
|
662
|
+
}
|
|
539
663
|
return { session: new PiBridgedAgentSession(host, handle, tools) };
|
|
540
664
|
}
|
|
541
665
|
//#endregion
|
|
@@ -2908,7 +3032,7 @@ function registerCommand(ctx, state, command) {
|
|
|
2908
3032
|
const definitionFor = (dshName) => ({
|
|
2909
3033
|
name: dshName,
|
|
2910
3034
|
description: command.description || `Migrated Pi command /${command.name}`,
|
|
2911
|
-
|
|
3035
|
+
input: { hint: command.argumentHint ?? "arguments (optional)" },
|
|
2912
3036
|
async handler(invocation) {
|
|
2913
3037
|
const agent = invocation.agent;
|
|
2914
3038
|
const commandContext = contextFor(ctx, state, agent, invocation.signal, true);
|
|
@@ -3368,7 +3492,8 @@ async function applyPiPackage(ctx, options) {
|
|
|
3368
3492
|
piContentToDsh: (content) => piToDshContent(ctx, content),
|
|
3369
3493
|
deliver: (agent, message, mode) => deliverAgentMessage(agent, message, mode),
|
|
3370
3494
|
messageFromSessionEvent,
|
|
3371
|
-
messageSource: state.messageSource
|
|
3495
|
+
messageSource: state.messageSource,
|
|
3496
|
+
packageName: state.packageName
|
|
3372
3497
|
}, subagentOptions));
|
|
3373
3498
|
ctx.effect(() => () => __setSubagentSessionFactory(void 0));
|
|
3374
3499
|
await registerPromptCommands(ctx, state, rootDir, options.manifest);
|
|
@@ -3410,4 +3535,4 @@ const runtimeInternals = {
|
|
|
3410
3535
|
//#endregion
|
|
3411
3536
|
export { runtimeInternals as i, normalizeToolSchema as n, registerVisionCompanions as r, applyPiPackage as t };
|
|
3412
3537
|
|
|
3413
|
-
//# sourceMappingURL=runtime-
|
|
3538
|
+
//# sourceMappingURL=runtime-DFD6u4NO.mjs.map
|