@earendil-works/pi-durable 1.3.0 → 1.4.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 +41 -0
- package/README.md +111 -3
- package/dist/codemode/codemode.d.ts.map +1 -1
- package/dist/codemode/codemode.js +12 -4
- package/dist/codemode/codemode.js.map +1 -1
- package/dist/codemode/models.d.ts.map +1 -1
- package/dist/codemode/models.js +2 -0
- package/dist/codemode/models.js.map +1 -1
- package/dist/documents.d.ts +1 -1
- package/dist/documents.d.ts.map +1 -1
- package/dist/documents.js.map +1 -1
- package/dist/env/node.d.ts.map +1 -1
- package/dist/env/node.js +11 -3
- package/dist/env/node.js.map +1 -1
- package/dist/harness/agent.d.ts +13 -2
- package/dist/harness/agent.d.ts.map +1 -1
- package/dist/harness/agent.js +39 -5
- package/dist/harness/agent.js.map +1 -1
- package/dist/harness/compaction.d.ts +3 -1
- package/dist/harness/compaction.d.ts.map +1 -1
- package/dist/harness/compaction.js +19 -4
- package/dist/harness/compaction.js.map +1 -1
- package/dist/harness/generation.d.ts.map +1 -1
- package/dist/harness/generation.js +67 -27
- package/dist/harness/generation.js.map +1 -1
- package/dist/harness/harness.d.ts +5 -2
- package/dist/harness/harness.d.ts.map +1 -1
- package/dist/harness/harness.js +78 -13
- package/dist/harness/harness.js.map +1 -1
- package/dist/harness/inbox.d.ts +2 -2
- package/dist/harness/inbox.d.ts.map +1 -1
- package/dist/harness/inbox.js +3 -3
- package/dist/harness/inbox.js.map +1 -1
- package/dist/harness/prompt.d.ts +1 -1
- package/dist/harness/prompt.d.ts.map +1 -1
- package/dist/harness/prompt.js +1 -1
- package/dist/harness/prompt.js.map +1 -1
- package/dist/harness/scheduler.d.ts +55 -10
- package/dist/harness/scheduler.d.ts.map +1 -1
- package/dist/harness/scheduler.js +617 -124
- package/dist/harness/scheduler.js.map +1 -1
- package/dist/harness/submissions.d.ts +7 -2
- package/dist/harness/submissions.d.ts.map +1 -1
- package/dist/harness/submissions.js +48 -17
- package/dist/harness/submissions.js.map +1 -1
- package/dist/harness/task-graph.d.ts +18 -1
- package/dist/harness/task-graph.d.ts.map +1 -1
- package/dist/harness/task-graph.js +50 -11
- package/dist/harness/task-graph.js.map +1 -1
- package/dist/harness/telemetry.d.ts +307 -0
- package/dist/harness/telemetry.d.ts.map +1 -0
- package/dist/harness/telemetry.js +136 -0
- package/dist/harness/telemetry.js.map +1 -0
- package/dist/harness/tool.d.ts.map +1 -1
- package/dist/harness/tool.js +53 -7
- package/dist/harness/tool.js.map +1 -1
- package/dist/harness/types.d.ts +110 -15
- package/dist/harness/types.d.ts.map +1 -1
- package/dist/harness/types.js.map +1 -1
- package/dist/harness/util.d.ts +4 -0
- package/dist/harness/util.d.ts.map +1 -1
- package/dist/harness/util.js +4 -0
- package/dist/harness/util.js.map +1 -1
- package/dist/index.d.ts +6 -4
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -2
- package/dist/index.js.map +1 -1
- package/dist/session/session.d.ts +17 -6
- package/dist/session/session.d.ts.map +1 -1
- package/dist/session/session.js +64 -32
- package/dist/session/session.js.map +1 -1
- package/dist/session/transaction.d.ts +5 -1
- package/dist/session/transaction.d.ts.map +1 -1
- package/dist/session/transaction.js +26 -1
- package/dist/session/transaction.js.map +1 -1
- package/dist/storage/indexeddb.d.ts +60 -0
- package/dist/storage/indexeddb.d.ts.map +1 -0
- package/dist/storage/indexeddb.js +831 -0
- package/dist/storage/indexeddb.js.map +1 -0
- package/dist/storage/jsonl/storage.d.ts +16 -0
- package/dist/storage/jsonl/storage.d.ts.map +1 -1
- package/dist/storage/memory.js +1 -1
- package/dist/storage/memory.js.map +1 -1
- package/dist/storage/sqlite/cloudflare.d.ts +2 -51
- package/dist/storage/sqlite/cloudflare.d.ts.map +1 -1
- package/dist/storage/sqlite/cloudflare.js +2 -133
- package/dist/storage/sqlite/cloudflare.js.map +1 -1
- package/dist/storage/sqlite/database.d.ts +1 -36
- package/dist/storage/sqlite/database.d.ts.map +1 -1
- package/dist/storage/sqlite/database.js.map +1 -1
- package/dist/storage/sqlite/index.d.ts +1 -1
- package/dist/storage/sqlite/index.d.ts.map +1 -1
- package/dist/storage/sqlite/index.js.map +1 -1
- package/dist/storage/sqlite/migrations.d.ts +2 -5
- package/dist/storage/sqlite/migrations.d.ts.map +1 -1
- package/dist/storage/sqlite/migrations.js +28 -28
- package/dist/storage/sqlite/migrations.js.map +1 -1
- package/dist/storage/sqlite/node.d.ts +2 -37
- package/dist/storage/sqlite/node.d.ts.map +1 -1
- package/dist/storage/sqlite/node.js +3 -174
- package/dist/storage/sqlite/node.js.map +1 -1
- package/dist/storage/sqlite/schema.d.ts +1 -3
- package/dist/storage/sqlite/schema.d.ts.map +1 -1
- package/dist/storage/sqlite/schema.js +2 -9
- package/dist/storage/sqlite/schema.js.map +1 -1
- package/dist/storage/sqlite/storage.d.ts +1 -1
- package/dist/storage/sqlite/storage.d.ts.map +1 -1
- package/dist/storage/sqlite/storage.js.map +1 -1
- package/dist/testing/storage-conformance.d.ts.map +1 -1
- package/dist/testing/storage-conformance.js +17 -0
- package/dist/testing/storage-conformance.js.map +1 -1
- package/dist/timers.d.ts +21 -0
- package/dist/timers.d.ts.map +1 -0
- package/dist/timers.js +72 -0
- package/dist/timers.js.map +1 -0
- package/dist/types.d.ts +130 -9
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js.map +1 -1
- package/package.json +15 -5
package/dist/harness/harness.js
CHANGED
|
@@ -1,6 +1,9 @@
|
|
|
1
1
|
import { withAbortSignal, withoutAbortSignal } from "@earendil-works/chord/context";
|
|
2
|
+
import { mergeClientIdentity, PI_ATTRIBUTION, withClientIdentity, } from "@earendil-works/pi-ai/utils/identity";
|
|
3
|
+
import { createTypedMetrics, NOOP_TELEMETRY_CONTEXT, NOOP_TELEMETRY_METRICS, } from "@earendil-works/pi-telemetry";
|
|
2
4
|
import { ResetEntry } from "../entries.js";
|
|
3
5
|
import { contained, SessionImpl } from "../session/session.js";
|
|
6
|
+
import { hostTimers } from "../timers.js";
|
|
4
7
|
import { ROOT_CONVERSATION_ID } from "../types.js";
|
|
5
8
|
import { AgentDoc, configure, createAgent, resolveAgent, resolveSettings } from "./agent.js";
|
|
6
9
|
import { createCompaction } from "./compaction.js";
|
|
@@ -12,6 +15,7 @@ import { BUILTIN_TASKS } from "./registry.js";
|
|
|
12
15
|
import { TaskScheduler } from "./scheduler.js";
|
|
13
16
|
import { Submissions } from "./submissions.js";
|
|
14
17
|
import { TaskGraphView } from "./task-graph.js";
|
|
18
|
+
import { DURABLE_TELEMETRY_SCHEMA } from "./telemetry.js";
|
|
15
19
|
import { addUsageState, UsageDoc } from "./usage.js";
|
|
16
20
|
import { scanAll } from "./util.js";
|
|
17
21
|
import { ConversationViews } from "./view.js";
|
|
@@ -79,33 +83,57 @@ class ConversationImpl {
|
|
|
79
83
|
return this.#host.views.watch(this.id, context);
|
|
80
84
|
}
|
|
81
85
|
}
|
|
86
|
+
/** Request identity of a Harness's model requests: pi-ai's defaults with provider attribution to pi. */
|
|
87
|
+
export const DEFAULT_HARNESS_IDENTITY = { attribution: PI_ATTRIBUTION };
|
|
88
|
+
/**
|
|
89
|
+
* `HarnessOptions.models` as a function with `HarnessOptions.identity` applied. A plain `Models` is wrapped once; a
|
|
90
|
+
* function's result is wrapped at each call.
|
|
91
|
+
*/
|
|
92
|
+
function currentModels(models, identity) {
|
|
93
|
+
const merged = mergeClientIdentity(DEFAULT_HARNESS_IDENTITY, identity) ?? DEFAULT_HARNESS_IDENTITY;
|
|
94
|
+
if (typeof models === "function")
|
|
95
|
+
return () => withClientIdentity(models(), merged);
|
|
96
|
+
const wrapped = withClientIdentity(models, merged);
|
|
97
|
+
return () => wrapped;
|
|
98
|
+
}
|
|
99
|
+
/** `HarnessOptions.settings` as a function: plain settings, or none, are returned at every call. */
|
|
100
|
+
function currentSettings(settings) {
|
|
101
|
+
return typeof settings === "function" ? settings : () => settings;
|
|
102
|
+
}
|
|
82
103
|
/** Session kernel extended with conversation handles and a registry. */
|
|
83
104
|
class HarnessImpl extends SessionImpl {
|
|
84
105
|
#options;
|
|
106
|
+
#hostSettings;
|
|
85
107
|
#report;
|
|
86
108
|
#host;
|
|
87
109
|
#tasks;
|
|
88
110
|
#submissions;
|
|
89
111
|
#taskGraph;
|
|
90
112
|
constructor(rawStorage, options, context) {
|
|
91
|
-
const report = safeReport(options.onReport);
|
|
113
|
+
const report = safeReport(options.onReport, options.telemetry ?? NOOP_TELEMETRY_CONTEXT);
|
|
92
114
|
const now = safeNow(options.now, report);
|
|
115
|
+
const hostSettings = currentSettings(options.settings);
|
|
93
116
|
// Read at each use, as all settings are, but only this field: it is read on every commit.
|
|
94
|
-
super(rawStorage, now, () => options.
|
|
117
|
+
super(rawStorage, now, () => hostSettings()?.documentRetentionMs, options.setTimer);
|
|
95
118
|
// Every component reads and writes through the Session's failure guard: `rawStorage` serves only `super()`.
|
|
96
119
|
const storage = this.storage;
|
|
97
120
|
this.#options = options;
|
|
98
121
|
this.#report = report;
|
|
99
|
-
|
|
122
|
+
this.#hostSettings = hostSettings;
|
|
123
|
+
const settings = () => resolveSettings(hostSettings());
|
|
100
124
|
this.#tasks = new TaskScheduler({
|
|
125
|
+
telemetry: options.telemetry,
|
|
101
126
|
session: this,
|
|
102
127
|
storage,
|
|
103
128
|
registry: options.registry,
|
|
104
|
-
models: options.models,
|
|
129
|
+
models: currentModels(options.models, options.identity),
|
|
105
130
|
agent: (id, snapshot, callContext) => this.resolveAgent(id, snapshot, callContext),
|
|
106
131
|
settings,
|
|
107
132
|
env: (id, callContext) => this.buildEnv(id, callContext),
|
|
108
133
|
now,
|
|
134
|
+
onWake: options.onWake,
|
|
135
|
+
timers: hostTimers(options.setTimer, (error) => report(error, { type: "host_error", callback: "setTimer" })),
|
|
136
|
+
writeAtClose: (writes) => this.writeAtClose(writes),
|
|
109
137
|
report: this.#report,
|
|
110
138
|
settleOutcome: settleSchedulerOutcome,
|
|
111
139
|
withdrawInputs: withdrawQueuedInputs,
|
|
@@ -115,8 +143,11 @@ class HarnessImpl extends SessionImpl {
|
|
|
115
143
|
},
|
|
116
144
|
context: withoutAbortSignal(context),
|
|
117
145
|
});
|
|
118
|
-
this.#submissions = new Submissions(this, storage, now, settings, () => this.#tasks.resume());
|
|
119
|
-
this.#taskGraph = new TaskGraphView(this, storage
|
|
146
|
+
this.#submissions = new Submissions(this, storage, now, settings, () => this.#tasks.resume(), options.telemetry);
|
|
147
|
+
this.#taskGraph = new TaskGraphView(this, storage, {
|
|
148
|
+
blocked: (record) => this.#tasks.blockedReason(record),
|
|
149
|
+
subscribeBlocked: (listener) => this.#tasks.subscribeBlocked(listener),
|
|
150
|
+
});
|
|
120
151
|
this.#host = {
|
|
121
152
|
harness: this,
|
|
122
153
|
storage,
|
|
@@ -131,7 +162,7 @@ class HarnessImpl extends SessionImpl {
|
|
|
131
162
|
async resolveAgent(id, snapshot, context) {
|
|
132
163
|
const registry = snapshot ?? this.#options.registry.snapshot();
|
|
133
164
|
const state = await this.snapshot(AgentDoc, id, context);
|
|
134
|
-
return resolveAgent(state, registry, resolveSettings(this.#
|
|
165
|
+
return resolveAgent(state, registry, resolveSettings(this.#hostSettings()), (error, extension) => this.#report(error, { type: "extension_error", conversationId: id, extension }, context));
|
|
135
166
|
}
|
|
136
167
|
/** Build a conversation's environment from its current `cwd`; `undefined` without an `env` option. */
|
|
137
168
|
async buildEnv(id, context) {
|
|
@@ -149,6 +180,10 @@ class HarnessImpl extends SessionImpl {
|
|
|
149
180
|
this.assertUsable();
|
|
150
181
|
this.#tasks.resume();
|
|
151
182
|
}
|
|
183
|
+
wake() {
|
|
184
|
+
this.assertUsable();
|
|
185
|
+
return this.#tasks.wake();
|
|
186
|
+
}
|
|
152
187
|
getTask(id, context) {
|
|
153
188
|
return this.readOnLine(() => this.storage.task(id, context));
|
|
154
189
|
}
|
|
@@ -173,6 +208,10 @@ class HarnessImpl extends SessionImpl {
|
|
|
173
208
|
abortTask(id, context) {
|
|
174
209
|
return this.#tasks.abort(id, context);
|
|
175
210
|
}
|
|
211
|
+
retryTask(id, context) {
|
|
212
|
+
this.assertUsable();
|
|
213
|
+
return this.#tasks.retry(id, context);
|
|
214
|
+
}
|
|
176
215
|
waitForTask(id, context) {
|
|
177
216
|
this.#tasks.resume();
|
|
178
217
|
return this.#tasks.waitForTask(id, context);
|
|
@@ -209,8 +248,8 @@ class HarnessImpl extends SessionImpl {
|
|
|
209
248
|
createConversation(options, context) {
|
|
210
249
|
return this.#create({ kind: "independent", ownership: options.ownership }, options, context);
|
|
211
250
|
}
|
|
212
|
-
report(error) {
|
|
213
|
-
this.#report(error);
|
|
251
|
+
report(error, info = { type: "listener_error" }, context) {
|
|
252
|
+
this.#report(error, info, context);
|
|
214
253
|
}
|
|
215
254
|
/** Signal and join task invocations after the close listeners and before Storage closes; writes no task outcome. */
|
|
216
255
|
beforeClose() {
|
|
@@ -249,9 +288,35 @@ class HarnessImpl extends SessionImpl {
|
|
|
249
288
|
await this.#options.conversationCreated?.(tx, record);
|
|
250
289
|
}
|
|
251
290
|
}
|
|
252
|
-
/**
|
|
253
|
-
function safeReport(onReport) {
|
|
254
|
-
|
|
291
|
+
/** Preserve the host callback's error containment; telemetry adapters are responsible for their own failures. */
|
|
292
|
+
function safeReport(onReport, telemetry) {
|
|
293
|
+
const reports = createTypedMetrics(telemetry.metrics ?? NOOP_TELEMETRY_METRICS, [DURABLE_TELEMETRY_SCHEMA]).counter("pi.durable.reports");
|
|
294
|
+
return (error, info, context) => {
|
|
295
|
+
contained(() => onReport?.(error, info), () => { });
|
|
296
|
+
const attributes = {
|
|
297
|
+
type: info.type,
|
|
298
|
+
};
|
|
299
|
+
switch (info.type) {
|
|
300
|
+
case "task_faulted":
|
|
301
|
+
case "task_outdated":
|
|
302
|
+
attributes.reason = info.reason;
|
|
303
|
+
attributes.extension = info.extension;
|
|
304
|
+
attributes["task.id"] = info.task.id;
|
|
305
|
+
break;
|
|
306
|
+
case "task_parked":
|
|
307
|
+
case "migration_failed":
|
|
308
|
+
case "task_error":
|
|
309
|
+
case "extension_error":
|
|
310
|
+
attributes.extension = info.extension;
|
|
311
|
+
attributes["task.id"] = info.task?.id;
|
|
312
|
+
break;
|
|
313
|
+
case "host_error":
|
|
314
|
+
attributes["task.id"] = info.task?.id;
|
|
315
|
+
break;
|
|
316
|
+
}
|
|
317
|
+
reports.add(1, { type: info.type });
|
|
318
|
+
context?.telemetry.addEvent("pi.durable.report", attributes);
|
|
319
|
+
};
|
|
255
320
|
}
|
|
256
321
|
/**
|
|
257
322
|
* The host clock, falling back to `Date.now` when it throws: a broken clock must not stop commits. The first throw is
|
|
@@ -269,7 +334,7 @@ export function safeNow(now, report) {
|
|
|
269
334
|
// Set first: a report handler that reads the clock again must not report again.
|
|
270
335
|
if (!reported) {
|
|
271
336
|
reported = true;
|
|
272
|
-
report(error);
|
|
337
|
+
report(error, { type: "host_error", callback: "now" });
|
|
273
338
|
}
|
|
274
339
|
return Date.now();
|
|
275
340
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"harness.js","sourceRoot":"","sources":["../../src/harness/harness.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AttachedReplicatedState, Context, JsonValue } from \"@earendil-works/chord\";\nimport { withAbortSignal, withoutAbortSignal } from \"@earendil-works/chord/context\";\nimport { ResetEntry } from \"../entries.ts\";\nimport type { ExecutionEnv } from \"../env/index.ts\";\nimport { contained, SessionImpl } from \"../session/session.ts\";\nimport type { Transaction } from \"../session/transaction.ts\";\nimport type {\n\tConversationId,\n\tConversationOwnership,\n\tConversationRecord,\n\tCursor,\n\tEntryId,\n\tEntryQuery,\n\tEntryRecord,\n\tPage,\n\tStorage,\n\tSubmissionId,\n\tTaskId,\n\tTaskRecord,\n\tTx,\n} from \"../types.ts\";\nimport { ROOT_CONVERSATION_ID } from \"../types.ts\";\nimport { AgentDoc, configure, createAgent, resolveAgent, resolveSettings } from \"./agent.ts\";\nimport { createCompaction } from \"./compaction.ts\";\nimport { readContext } from \"./context.ts\";\nimport { InboxDoc, withdrawQueuedInputs } from \"./inbox.ts\";\nimport { LiveDoc, settleSchedulerOutcome } from \"./live.ts\";\nimport { ProviderDoc } from \"./provider.ts\";\nimport { BUILTIN_TASKS } from \"./registry.ts\";\nimport { type InvocationBinding, TaskScheduler } from \"./scheduler.ts\";\nimport { Submissions } from \"./submissions.ts\";\nimport { type TaskGraph, TaskGraphView, type TaskGraphWatch } from \"./task-graph.ts\";\nimport type {\n\tAgent,\n\tAgentChange,\n\tCompactionResult,\n\tContextView,\n\tConversation,\n\tConversationAbortOptions,\n\tConversationCreateOptions,\n\tConversationHandle,\n\tConversationInit,\n\tConversationWatch,\n\tHarnessInspection,\n\tHarnessOptions,\n\tHarness as HarnessType,\n\tRegistrySnapshot,\n\tSettledTask,\n\tSubmission,\n\tSubmissionDraft,\n\tToolRegistration,\n} from \"./types.ts\";\nimport { addUsageState, UsageDoc, type UsageState } from \"./usage.ts\";\nimport { scanAll } from \"./util.ts\";\nimport { type ConversationView, ConversationViews } from \"./view.ts\";\n\nconst SCAN_PAGE_SIZE = 256;\n\ntype CreateTarget =\n\t| { readonly kind: \"root\" }\n\t| { readonly kind: \"independent\"; readonly ownership: ConversationOwnership }\n\t| {\n\t\t\treadonly kind: \"fork\";\n\t\t\treadonly parentId: ConversationId;\n\t\t\treadonly at: EntryId;\n\t\t\treadonly ownership: ConversationOwnership;\n\t };\n\n/** What the conveniences apply in the creating commit, after the creation hook. */\ntype CreateOptions = { readonly agent?: AgentChange; readonly init?: ConversationInit };\n\n/** Harness-private services used by Conversation handles. */\ntype ConversationHost<Tool extends ToolRegistration> = {\n\treadonly harness: HarnessImpl<Tool>;\n\treadonly storage: Storage;\n\treadonly tasks: TaskScheduler;\n\treadonly submissions: Submissions;\n\treadonly views: ConversationViews;\n\treadonly now: () => number;\n\tcreate(target: CreateTarget, options: CreateOptions, context: Context): Promise<Conversation>;\n};\n\n/** Key of the Harness's internal index-size getter, for tests. */\nexport const SCHEDULER_INDEX_SIZES = Symbol.for(\"pi-durable.schedulerIndexSizes\");\n\nclass ConversationImpl<Tool extends ToolRegistration> implements Conversation {\n\treadonly id: ConversationId;\n\treadonly #host: ConversationHost<Tool>;\n\n\tconstructor(id: ConversationId, host: ConversationHost<Tool>) {\n\t\tthis.id = id;\n\t\tthis.#host = host;\n\t}\n\n\tagent(context: Context): Promise<Agent> {\n\t\treturn this.#host.harness.resolveAgent(this.id, undefined, context);\n\t}\n\n\tconfigure(change: AgentChange, context: Context): Promise<void> {\n\t\treturn this.#host.harness.commitWith((tx) => configure(tx, this.id, change), context);\n\t}\n\n\tsubmit(submission: SubmissionDraft, context: Context): Promise<Submission> {\n\t\treturn this.#host.submissions.submit(this.id, submission, context);\n\t}\n\n\tcompact(instructions: string | undefined, context: Context): Promise<TaskId<CompactionResult>> {\n\t\tthis.#host.tasks.resume();\n\t\tconst input = { reason: \"manual\", ...(instructions === undefined ? {} : { instructions }) } as const;\n\t\treturn this.#host.harness.commitWith((tx) => createCompaction(tx, this.id, input), context);\n\t}\n\n\tasync reset(handoff: string | undefined, context: Context): Promise<void> {\n\t\tconst model =\n\t\t\thandoff === undefined\n\t\t\t\t? {}\n\t\t\t\t: { model: [{ role: \"user\", content: handoff, timestamp: this.#host.now() } as const] };\n\t\tconst entry = { kind: ResetEntry.kind, head: \"self\", ...model } as const;\n\t\tawait this.#host.submissions.submit(this.id, { type: \"write\", entry }, context);\n\t}\n\n\tcommit<T>(change: (tx: Tx) => T | Promise<T>, context: Context): Promise<T> {\n\t\treturn this.#host.harness.commitWith(change, context, { conversationId: this.id });\n\t}\n\n\tcontext(context: Context, options?: { readonly at?: EntryId }): Promise<ContextView> {\n\t\treturn readContext(this.#host.harness, this.#host.storage, this.id, context, options?.at);\n\t}\n\n\tentries(\n\t\tquery: Omit<EntryQuery, \"conversationId\">,\n\t\tlimit: number,\n\t\tcursor: Cursor | undefined,\n\t\tcontext: Context,\n\t): Promise<Page<EntryRecord, Cursor>> {\n\t\tconst bounded: EntryQuery = {\n\t\t\tconversationId: this.id,\n\t\t\t...(query.minEntryId === undefined ? {} : { minEntryId: query.minEntryId }),\n\t\t\t...(query.maxEntryId === undefined ? {} : { maxEntryId: query.maxEntryId }),\n\t\t\t...(query.order === undefined ? {} : { order: query.order }),\n\t\t};\n\t\treturn this.#host.harness.readOnLine(() => this.#host.storage.scanEntries(bounded, limit, cursor, context));\n\t}\n\n\tfork(at: EntryId, options: ConversationCreateOptions, context: Context): Promise<Conversation> {\n\t\treturn this.#host.create({ kind: \"fork\", parentId: this.id, at, ownership: options.ownership }, options, context);\n\t}\n\n\tabort(context: Context, options?: ConversationAbortOptions): Promise<void> {\n\t\tthis.#host.tasks.resume();\n\t\treturn this.#host.tasks.abortConversation(this.id, options?.background === true, context);\n\t}\n\n\twaitForIdle(context: Context): Promise<void> {\n\t\tthis.#host.tasks.resume();\n\t\treturn this.#host.tasks.waitForIdle(this.id, context);\n\t}\n\n\tviewState(context: Context): Promise<AttachedReplicatedState<ConversationView>> {\n\t\treturn this.#host.views.state(this.id, context);\n\t}\n\n\twatch(context: Context): Promise<ConversationWatch> {\n\t\treturn this.#host.views.watch(this.id, context);\n\t}\n}\n\n/** Session kernel extended with conversation handles and a registry. */\nclass HarnessImpl<Tool extends ToolRegistration> extends SessionImpl implements HarnessType {\n\treadonly #options: HarnessOptions<Tool>;\n\treadonly #report: (error: unknown) => void;\n\treadonly #host: ConversationHost<Tool>;\n\treadonly #tasks: TaskScheduler;\n\treadonly #submissions: Submissions;\n\treadonly #taskGraph: TaskGraphView;\n\n\tconstructor(rawStorage: Storage, options: HarnessOptions<Tool>, context: Context) {\n\t\tconst report = safeReport(options.onReport);\n\t\tconst now = safeNow(options.now, report);\n\t\t// Read at each use, as all settings are, but only this field: it is read on every commit.\n\t\tsuper(rawStorage, now, () => options.settings?.documentRetentionMs);\n\t\t// Every component reads and writes through the Session's failure guard: `rawStorage` serves only `super()`.\n\t\tconst storage = this.storage;\n\t\tthis.#options = options;\n\t\tthis.#report = report;\n\t\tconst settings = () => resolveSettings(options.settings);\n\t\tthis.#tasks = new TaskScheduler({\n\t\t\tsession: this,\n\t\t\tstorage,\n\t\t\tregistry: options.registry,\n\t\t\tmodels: options.models,\n\t\t\tagent: (id, snapshot, callContext) => this.resolveAgent(id, snapshot as RegistrySnapshot<Tool>, callContext),\n\t\t\tsettings,\n\t\t\tenv: (id, callContext) => this.buildEnv(id, callContext),\n\t\t\tnow,\n\t\t\treport: this.#report,\n\t\t\tsettleOutcome: settleSchedulerOutcome,\n\t\t\twithdrawInputs: withdrawQueuedInputs,\n\t\t\tconversation: async (id, binding, callContext) => {\n\t\t\t\tconst record = await this.readOnLine(() => storage.conversation(id, callContext));\n\t\t\t\treturn record === undefined ? undefined : boundConversation(id, binding, this.#submissions, this.#tasks);\n\t\t\t},\n\t\t\tcontext: withoutAbortSignal(context),\n\t\t});\n\t\tthis.#submissions = new Submissions(this, storage, now, settings, () => this.#tasks.resume());\n\t\tthis.#taskGraph = new TaskGraphView(this, storage);\n\t\tthis.#host = {\n\t\t\tharness: this,\n\t\t\tstorage,\n\t\t\ttasks: this.#tasks,\n\t\t\tsubmissions: this.#submissions,\n\t\t\tviews: new ConversationViews(this, storage),\n\t\t\tnow,\n\t\t\tcreate: (target, createOptions, context) => this.#create(target, createOptions, context),\n\t\t};\n\t}\n\n\t/** Resolve a conversation's committed `pi.agent` against `snapshot`, or the current one, and the current settings. */\n\tasync resolveAgent(\n\t\tid: ConversationId,\n\t\tsnapshot: RegistrySnapshot<Tool> | undefined,\n\t\tcontext: Context,\n\t): Promise<Agent<Tool>> {\n\t\tconst registry = snapshot ?? this.#options.registry.snapshot();\n\t\tconst state = await this.snapshot(AgentDoc, id, context);\n\t\treturn resolveAgent(state, registry, resolveSettings(this.#options.settings), this.#report);\n\t}\n\n\t/** Build a conversation's environment from its current `cwd`; `undefined` without an `env` option. */\n\tasync buildEnv(id: ConversationId, context: Context): Promise<ExecutionEnv | undefined> {\n\t\tconst build = this.#options.env;\n\t\tif (build === undefined) return undefined;\n\t\tconst cwd = (await this.snapshot(AgentDoc, id, context))?.cwd;\n\t\treturn build({ conversationId: id, ...(cwd === undefined ? {} : { cwd }), read: this }, context);\n\t}\n\n\t/** Reconcile surviving `running` tasks to `pending`; part of open. */\n\topenTasks(context: Context): Promise<void> {\n\t\treturn this.#tasks.open(context);\n\t}\n\n\tresume(): void {\n\t\tthis.assertUsable();\n\t\tthis.#tasks.resume();\n\t}\n\n\tgetTask<R>(id: TaskId<R>, context: Context): Promise<TaskRecord<JsonValue, JsonValue, R> | undefined> {\n\t\treturn this.readOnLine(() => this.storage.task(id, context)) as Promise<\n\t\t\tTaskRecord<JsonValue, JsonValue, R> | undefined\n\t\t>;\n\t}\n\n\t/** Internal, for tests: sizes of the scheduler's ownership indexes. */\n\tget [SCHEDULER_INDEX_SIZES](): TaskScheduler[\"indexSizes\"] {\n\t\treturn this.#tasks.indexSizes;\n\t}\n\n\tinspect(context: Context): Promise<HarnessInspection> {\n\t\treturn this.readOnLine(async () => {\n\t\t\tconst { scheduling, tasks } = await this.#tasks.inspect(this.#options.registry.snapshot());\n\t\t\tconst scan = (status: \"queued\" | \"placed\") =>\n\t\t\t\tscanAll((cursor) => this.storage.scanSubmissions({ status }, SCAN_PAGE_SIZE, cursor, context));\n\t\t\tconst submissions = [...(await scan(\"queued\")), ...(await scan(\"placed\"))].sort((a, b) => a.id - b.id);\n\t\t\treturn { scheduling, tasks, submissions };\n\t\t});\n\t}\n\n\tsubmission(id: SubmissionId, context: Context): Promise<Submission | undefined> {\n\t\treturn this.#submissions.get(id, context);\n\t}\n\n\tabortSubmission(\n\t\tid: SubmissionId,\n\t\tcontext: Context,\n\t\tconversationId?: ConversationId,\n\t): Promise<\"aborted\" | \"already_placed\" | \"settled\" | \"not_found\"> {\n\t\treturn this.#submissions.abort(id, context, conversationId);\n\t}\n\n\tabortTask(id: TaskId, context: Context): Promise<\"marked\" | \"terminal\"> {\n\t\treturn this.#tasks.abort(id, context);\n\t}\n\n\twaitForTask<R>(id: TaskId<R>, context: Context): Promise<SettledTask<R>> {\n\t\tthis.#tasks.resume();\n\t\treturn this.#tasks.waitForTask(id, context) as Promise<SettledTask<R>>;\n\t}\n\n\twaitForIdle(context: Context): Promise<void> {\n\t\tthis.#tasks.resume();\n\t\treturn this.#tasks.waitForIdle(undefined, context);\n\t}\n\n\t/** Sum every conversation's committed `pi.usage`. Each document is read at its own point; totals only grow. */\n\tasync usage(context: Context): Promise<UsageState> {\n\t\tconst conversations = await this.readOnLine(() =>\n\t\t\tscanAll((cursor) => this.storage.scanConversations({}, SCAN_PAGE_SIZE, cursor, context)),\n\t\t);\n\t\tconst total = UsageDoc.definition.initial();\n\t\tfor (const { id } of conversations) {\n\t\t\tconst state = await this.snapshot(UsageDoc, id, context);\n\t\t\tif (state !== undefined) addUsageState(total, state);\n\t\t}\n\t\treturn total;\n\t}\n\n\ttaskGraph(context: Context): Promise<AttachedReplicatedState<TaskGraph>> {\n\t\treturn this.#taskGraph.state(context);\n\t}\n\n\twatchTaskGraph(context: Context): Promise<TaskGraphWatch> {\n\t\treturn this.#taskGraph.watch(context);\n\t}\n\n\troot(\n\t\tcontext: Context,\n\t\toptions?: { readonly agent?: AgentChange; readonly init?: ConversationInit },\n\t): Promise<Conversation> {\n\t\treturn this.#create({ kind: \"root\" }, options ?? {}, context);\n\t}\n\n\tasync conversation(id: ConversationId, context: Context): Promise<Conversation | undefined> {\n\t\tthis.assertUsable();\n\t\tconst record = await this.readOnLine(() => this.storage.conversation(id, context));\n\t\treturn record === undefined ? undefined : new ConversationImpl(record.id, this.#host);\n\t}\n\n\tcreateConversation(options: ConversationCreateOptions, context: Context): Promise<Conversation> {\n\t\treturn this.#create({ kind: \"independent\", ownership: options.ownership }, options, context);\n\t}\n\n\toverride report(error: unknown): void {\n\t\tthis.#report(error);\n\t}\n\n\t/** Signal and join task invocations after the close listeners and before Storage closes; writes no task outcome. */\n\tprotected override beforeClose(): Promise<void> {\n\t\treturn this.#tasks.join();\n\t}\n\n\tasync #create(target: CreateTarget, options: CreateOptions, context: Context): Promise<Conversation> {\n\t\tthis.assertUsable();\n\t\tconst id = await this.commitWith(async (tx) => {\n\t\t\tif (target.kind === \"root\" && (await tx.conversation(ROOT_CONVERSATION_ID)) !== undefined) {\n\t\t\t\treturn ROOT_CONVERSATION_ID;\n\t\t\t}\n\t\t\tconst record =\n\t\t\t\ttarget.kind === \"root\"\n\t\t\t\t\t? await tx.createRootConversation()\n\t\t\t\t\t: target.kind === \"fork\"\n\t\t\t\t\t\t? await tx.forkConversation(target.parentId, target.at, { ownership: target.ownership })\n\t\t\t\t\t\t: await tx.createConversation({ ownership: target.ownership });\n\t\t\tif (options.agent !== undefined) await configure(tx, record.id, options.agent);\n\t\t\tif (options.init !== undefined) await options.init(tx, record.id);\n\t\t\treturn record.id;\n\t\t}, context);\n\t\treturn new ConversationImpl(id, this.#host);\n\t}\n\n\t/**\n\t * The built-in creation hook, in every commit that creates or forks a conversation: empty `pi.live`, `pi.inbox`, and\n\t * `pi.usage`, a fresh `pi.provider`, the conversation's `pi.agent` (see `createAgent()`), then\n\t * `HarnessOptions.conversationCreated`.\n\t */\n\tprotected override async conversationCreated(tx: Transaction, record: ConversationRecord): Promise<void> {\n\t\tawait tx.doc(LiveDoc, record.id);\n\t\tawait tx.doc(InboxDoc, record.id);\n\t\tawait tx.doc(UsageDoc, record.id);\n\t\tawait tx.doc(ProviderDoc, record.id);\n\t\tawait createAgent(tx, record);\n\t\tawait this.#options.conversationCreated?.(tx, record);\n\t}\n}\n\n/** `onReport` that cannot fail: it is the last place an error goes, so its own throw or rejection is dropped. */\nfunction safeReport(onReport: ((error: unknown) => void) | undefined): (error: unknown) => void {\n\treturn (error) =>\n\t\tcontained(\n\t\t\t() => onReport?.(error),\n\t\t\t() => {},\n\t\t);\n}\n\n/**\n * The host clock, falling back to `Date.now` when it throws: a broken clock must not stop commits. The first throw is\n * reported; the clock is read in every task change, so later ones are not.\n */\nexport function safeNow(now: (() => number) | undefined, report: (error: unknown) => void): () => number {\n\tif (now === undefined) return Date.now;\n\tlet reported = false;\n\treturn () => {\n\t\ttry {\n\t\t\treturn now();\n\t\t} catch (error) {\n\t\t\t// Set first: a report handler that reads the clock again must not report again.\n\t\t\tif (!reported) {\n\t\t\t\treported = true;\n\t\t\t\treport(error);\n\t\t\t}\n\t\t\treturn Date.now();\n\t\t}\n\t};\n}\n\n/**\n * Invocation-bound handle for tasks and tools. Every operation, and every operation of a submission it returns, first\n * checks the invocation and runs under its signal, so it rejects once the invocation ends; admitted work stays durable.\n */\nfunction boundConversation(\n\tid: ConversationId,\n\tbinding: InvocationBinding,\n\tsubmissions: Submissions,\n\ttasks: TaskScheduler,\n): ConversationHandle {\n\tconst bind = (context: Context): Context => withAbortSignal(binding.signal, context);\n\tconst bound = <T>(operation: (context: Context) => Promise<T>) => {\n\t\treturn async (context: Context): Promise<T> => {\n\t\t\tbinding.check();\n\t\t\treturn operation(bind(context));\n\t\t};\n\t};\n\treturn {\n\t\tid,\n\t\tsubmit: async (draft, context) => {\n\t\t\tbinding.check();\n\t\t\tconst submission = await submissions.submit(id, draft, bind(context));\n\t\t\treturn {\n\t\t\t\tid: submission.id,\n\t\t\t\tstatus: bound((callContext) => submission.status(callContext)),\n\t\t\t\twait: bound((callContext) => submission.wait(callContext)),\n\t\t\t\tabort: bound((callContext) => submission.abort(callContext)),\n\t\t\t};\n\t\t},\n\t\tabort: async (context, options) => {\n\t\t\tbinding.check();\n\t\t\treturn tasks.abortConversation(id, options?.background === true, bind(context));\n\t\t},\n\t\twaitForIdle: bound((callContext) => tasks.waitForIdle(id, callContext)),\n\t};\n}\n\n/** Durable agent harness over one Session. */\nexport type Harness = HarnessType;\n\nexport const Harness = {\n\t/** Open a Harness over storage. The registry may keep changing while the Harness runs. */\n\tasync open<Tool extends ToolRegistration>(\n\t\tstorage: Storage,\n\t\toptions: HarnessOptions<Tool>,\n\t\tcontext: Context,\n\t): Promise<Harness> {\n\t\tcontext.abortSignal?.throwIfAborted();\n\t\tconst snapshot = options.registry.snapshot();\n\t\tconst missing = BUILTIN_TASKS.filter((task) => snapshot.task(task.definition.name) === undefined);\n\t\tif (missing.length > 0) {\n\t\t\tconst names = missing.map((task) => task.definition.name).join(\", \");\n\t\t\tthrow new Error(`Registry lacks built-in tasks ${names}; create it with createRegistry()`);\n\t\t}\n\t\tconst harness = new HarnessImpl(storage, options, context);\n\t\ttry {\n\t\t\tawait harness.openTasks(context);\n\t\t} catch (error) {\n\t\t\t// The caller's context may be what failed open: close without it, and rethrow the open error.\n\t\t\t// A failing Storage close fails the Session, which reports it.\n\t\t\tawait harness.close(withoutAbortSignal(context)).catch(() => {});\n\t\t\tthrow error;\n\t\t}\n\t\treturn harness;\n\t},\n};\n"]}
|
|
1
|
+
{"version":3,"file":"harness.js","sourceRoot":"","sources":["../../src/harness/harness.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AttachedReplicatedState, Context, JsonValue } from \"@earendil-works/chord\";\nimport { withAbortSignal, withoutAbortSignal } from \"@earendil-works/chord/context\";\nimport type { Models } from \"@earendil-works/pi-ai\";\nimport {\n\ttype ClientIdentity,\n\tmergeClientIdentity,\n\tPI_ATTRIBUTION,\n\twithClientIdentity,\n} from \"@earendil-works/pi-ai/utils/identity\";\nimport {\n\tcreateTypedMetrics,\n\tNOOP_TELEMETRY_CONTEXT,\n\tNOOP_TELEMETRY_METRICS,\n\ttype SpanAttributes,\n\ttype TelemetryContext,\n} from \"@earendil-works/pi-telemetry\";\nimport { ResetEntry } from \"../entries.ts\";\nimport type { ExecutionEnv } from \"../env/index.ts\";\nimport { contained, SessionImpl } from \"../session/session.ts\";\nimport type { Transaction } from \"../session/transaction.ts\";\nimport { hostTimers } from \"../timers.ts\";\nimport type {\n\tConversationId,\n\tConversationOwnership,\n\tConversationRecord,\n\tCursor,\n\tEntryId,\n\tEntryQuery,\n\tEntryRecord,\n\tPage,\n\tReportInfo,\n\tStorage,\n\tSubmissionId,\n\tTaskId,\n\tTaskRecord,\n\tTx,\n} from \"../types.ts\";\nimport { ROOT_CONVERSATION_ID } from \"../types.ts\";\nimport { AgentDoc, configure, createAgent, resolveAgent, resolveSettings } from \"./agent.ts\";\nimport { createCompaction } from \"./compaction.ts\";\nimport { readContext } from \"./context.ts\";\nimport { InboxDoc, withdrawQueuedInputs } from \"./inbox.ts\";\nimport { LiveDoc, settleSchedulerOutcome } from \"./live.ts\";\nimport { ProviderDoc } from \"./provider.ts\";\nimport { BUILTIN_TASKS } from \"./registry.ts\";\nimport { type InvocationBinding, TaskScheduler } from \"./scheduler.ts\";\nimport { Submissions } from \"./submissions.ts\";\nimport { type TaskGraph, TaskGraphView, type TaskGraphWatch } from \"./task-graph.ts\";\nimport { DURABLE_TELEMETRY_SCHEMA } from \"./telemetry.ts\";\nimport type {\n\tAgent,\n\tAgentChange,\n\tCompactionResult,\n\tContextView,\n\tConversation,\n\tConversationAbortOptions,\n\tConversationCreateOptions,\n\tConversationHandle,\n\tConversationInit,\n\tConversationWatch,\n\tHarnessInspection,\n\tHarnessOptions,\n\tHarnessSettings,\n\tHarness as HarnessType,\n\tRegistrySnapshot,\n\tSettledTask,\n\tSubmission,\n\tSubmissionDraft,\n\tToolRegistration,\n\tWake,\n} from \"./types.ts\";\nimport { addUsageState, UsageDoc, type UsageState } from \"./usage.ts\";\nimport { scanAll } from \"./util.ts\";\nimport { type ConversationView, ConversationViews } from \"./view.ts\";\n\nconst SCAN_PAGE_SIZE = 256;\n\ntype CreateTarget =\n\t| { readonly kind: \"root\" }\n\t| { readonly kind: \"independent\"; readonly ownership: ConversationOwnership }\n\t| {\n\t\t\treadonly kind: \"fork\";\n\t\t\treadonly parentId: ConversationId;\n\t\t\treadonly at: EntryId;\n\t\t\treadonly ownership: ConversationOwnership;\n\t };\n\n/** What the conveniences apply in the creating commit, after the creation hook. */\ntype CreateOptions = { readonly agent?: AgentChange; readonly init?: ConversationInit };\n\n/** Harness-private services used by Conversation handles. */\ntype ConversationHost<Tool extends ToolRegistration> = {\n\treadonly harness: HarnessImpl<Tool>;\n\treadonly storage: Storage;\n\treadonly tasks: TaskScheduler;\n\treadonly submissions: Submissions;\n\treadonly views: ConversationViews;\n\treadonly now: () => number;\n\tcreate(target: CreateTarget, options: CreateOptions, context: Context): Promise<Conversation>;\n};\n\n/** Key of the Harness's internal index-size getter, for tests. */\nexport const SCHEDULER_INDEX_SIZES = Symbol.for(\"pi-durable.schedulerIndexSizes\");\n\nclass ConversationImpl<Tool extends ToolRegistration> implements Conversation {\n\treadonly id: ConversationId;\n\treadonly #host: ConversationHost<Tool>;\n\n\tconstructor(id: ConversationId, host: ConversationHost<Tool>) {\n\t\tthis.id = id;\n\t\tthis.#host = host;\n\t}\n\n\tagent(context: Context): Promise<Agent> {\n\t\treturn this.#host.harness.resolveAgent(this.id, undefined, context);\n\t}\n\n\tconfigure(change: AgentChange, context: Context): Promise<void> {\n\t\treturn this.#host.harness.commitWith((tx) => configure(tx, this.id, change), context);\n\t}\n\n\tsubmit(submission: SubmissionDraft, context: Context): Promise<Submission> {\n\t\treturn this.#host.submissions.submit(this.id, submission, context);\n\t}\n\n\tcompact(instructions: string | undefined, context: Context): Promise<TaskId<CompactionResult>> {\n\t\tthis.#host.tasks.resume();\n\t\tconst input = { reason: \"manual\", ...(instructions === undefined ? {} : { instructions }) } as const;\n\t\treturn this.#host.harness.commitWith((tx) => createCompaction(tx, this.id, input), context);\n\t}\n\n\tasync reset(handoff: string | undefined, context: Context): Promise<void> {\n\t\tconst model =\n\t\t\thandoff === undefined\n\t\t\t\t? {}\n\t\t\t\t: { model: [{ role: \"user\", content: handoff, timestamp: this.#host.now() } as const] };\n\t\tconst entry = { kind: ResetEntry.kind, head: \"self\", ...model } as const;\n\t\tawait this.#host.submissions.submit(this.id, { type: \"write\", entry }, context);\n\t}\n\n\tcommit<T>(change: (tx: Tx) => T | Promise<T>, context: Context): Promise<T> {\n\t\treturn this.#host.harness.commitWith(change, context, { conversationId: this.id });\n\t}\n\n\tcontext(context: Context, options?: { readonly at?: EntryId }): Promise<ContextView> {\n\t\treturn readContext(this.#host.harness, this.#host.storage, this.id, context, options?.at);\n\t}\n\n\tentries(\n\t\tquery: Omit<EntryQuery, \"conversationId\">,\n\t\tlimit: number,\n\t\tcursor: Cursor | undefined,\n\t\tcontext: Context,\n\t): Promise<Page<EntryRecord, Cursor>> {\n\t\tconst bounded: EntryQuery = {\n\t\t\tconversationId: this.id,\n\t\t\t...(query.minEntryId === undefined ? {} : { minEntryId: query.minEntryId }),\n\t\t\t...(query.maxEntryId === undefined ? {} : { maxEntryId: query.maxEntryId }),\n\t\t\t...(query.order === undefined ? {} : { order: query.order }),\n\t\t};\n\t\treturn this.#host.harness.readOnLine(() => this.#host.storage.scanEntries(bounded, limit, cursor, context));\n\t}\n\n\tfork(at: EntryId, options: ConversationCreateOptions, context: Context): Promise<Conversation> {\n\t\treturn this.#host.create({ kind: \"fork\", parentId: this.id, at, ownership: options.ownership }, options, context);\n\t}\n\n\tabort(context: Context, options?: ConversationAbortOptions): Promise<void> {\n\t\tthis.#host.tasks.resume();\n\t\treturn this.#host.tasks.abortConversation(this.id, options?.background === true, context);\n\t}\n\n\twaitForIdle(context: Context): Promise<void> {\n\t\tthis.#host.tasks.resume();\n\t\treturn this.#host.tasks.waitForIdle(this.id, context);\n\t}\n\n\tviewState(context: Context): Promise<AttachedReplicatedState<ConversationView>> {\n\t\treturn this.#host.views.state(this.id, context);\n\t}\n\n\twatch(context: Context): Promise<ConversationWatch> {\n\t\treturn this.#host.views.watch(this.id, context);\n\t}\n}\n\n/** Request identity of a Harness's model requests: pi-ai's defaults with provider attribution to pi. */\nexport const DEFAULT_HARNESS_IDENTITY: ClientIdentity = { attribution: PI_ATTRIBUTION };\n\n/**\n * `HarnessOptions.models` as a function with `HarnessOptions.identity` applied. A plain `Models` is wrapped once; a\n * function's result is wrapped at each call.\n */\nfunction currentModels(models: HarnessOptions[\"models\"], identity: ClientIdentity | undefined): () => Models {\n\tconst merged = mergeClientIdentity(DEFAULT_HARNESS_IDENTITY, identity) ?? DEFAULT_HARNESS_IDENTITY;\n\tif (typeof models === \"function\") return () => withClientIdentity(models(), merged);\n\tconst wrapped = withClientIdentity(models, merged);\n\treturn () => wrapped;\n}\n\n/** `HarnessOptions.settings` as a function: plain settings, or none, are returned at every call. */\nfunction currentSettings(settings: HarnessOptions[\"settings\"]): () => HarnessSettings | undefined {\n\treturn typeof settings === \"function\" ? settings : () => settings;\n}\n\n/** Session kernel extended with conversation handles and a registry. */\nclass HarnessImpl<Tool extends ToolRegistration> extends SessionImpl implements HarnessType {\n\treadonly #options: HarnessOptions<Tool>;\n\treadonly #hostSettings: () => HarnessSettings | undefined;\n\treadonly #report: (error: unknown, info: ReportInfo, context?: Context) => void;\n\treadonly #host: ConversationHost<Tool>;\n\treadonly #tasks: TaskScheduler;\n\treadonly #submissions: Submissions;\n\treadonly #taskGraph: TaskGraphView;\n\n\tconstructor(rawStorage: Storage, options: HarnessOptions<Tool>, context: Context) {\n\t\tconst report = safeReport(options.onReport, options.telemetry ?? NOOP_TELEMETRY_CONTEXT);\n\t\tconst now = safeNow(options.now, report);\n\t\tconst hostSettings = currentSettings(options.settings);\n\t\t// Read at each use, as all settings are, but only this field: it is read on every commit.\n\t\tsuper(rawStorage, now, () => hostSettings()?.documentRetentionMs, options.setTimer);\n\t\t// Every component reads and writes through the Session's failure guard: `rawStorage` serves only `super()`.\n\t\tconst storage = this.storage;\n\t\tthis.#options = options;\n\t\tthis.#report = report;\n\t\tthis.#hostSettings = hostSettings;\n\t\tconst settings = () => resolveSettings(hostSettings());\n\t\tthis.#tasks = new TaskScheduler({\n\t\t\ttelemetry: options.telemetry,\n\t\t\tsession: this,\n\t\t\tstorage,\n\t\t\tregistry: options.registry,\n\t\t\tmodels: currentModels(options.models, options.identity),\n\t\t\tagent: (id, snapshot, callContext) => this.resolveAgent(id, snapshot as RegistrySnapshot<Tool>, callContext),\n\t\t\tsettings,\n\t\t\tenv: (id, callContext) => this.buildEnv(id, callContext),\n\t\t\tnow,\n\t\t\tonWake: options.onWake,\n\t\t\ttimers: hostTimers(options.setTimer, (error) => report(error, { type: \"host_error\", callback: \"setTimer\" })),\n\t\t\twriteAtClose: (writes) => this.writeAtClose(writes),\n\t\t\treport: this.#report,\n\t\t\tsettleOutcome: settleSchedulerOutcome,\n\t\t\twithdrawInputs: withdrawQueuedInputs,\n\t\t\tconversation: async (id, binding, callContext) => {\n\t\t\t\tconst record = await this.readOnLine(() => storage.conversation(id, callContext));\n\t\t\t\treturn record === undefined ? undefined : boundConversation(id, binding, this.#submissions, this.#tasks);\n\t\t\t},\n\t\t\tcontext: withoutAbortSignal(context),\n\t\t});\n\t\tthis.#submissions = new Submissions(this, storage, now, settings, () => this.#tasks.resume(), options.telemetry);\n\t\tthis.#taskGraph = new TaskGraphView(this, storage, {\n\t\t\tblocked: (record) => this.#tasks.blockedReason(record),\n\t\t\tsubscribeBlocked: (listener) => this.#tasks.subscribeBlocked(listener),\n\t\t});\n\t\tthis.#host = {\n\t\t\tharness: this,\n\t\t\tstorage,\n\t\t\ttasks: this.#tasks,\n\t\t\tsubmissions: this.#submissions,\n\t\t\tviews: new ConversationViews(this, storage),\n\t\t\tnow,\n\t\t\tcreate: (target, createOptions, context) => this.#create(target, createOptions, context),\n\t\t};\n\t}\n\n\t/** Resolve a conversation's committed `pi.agent` against `snapshot`, or the current one, and the current settings. */\n\tasync resolveAgent(\n\t\tid: ConversationId,\n\t\tsnapshot: RegistrySnapshot<Tool> | undefined,\n\t\tcontext: Context,\n\t): Promise<Agent<Tool>> {\n\t\tconst registry = snapshot ?? this.#options.registry.snapshot();\n\t\tconst state = await this.snapshot(AgentDoc, id, context);\n\t\treturn resolveAgent(state, registry, resolveSettings(this.#hostSettings()), (error, extension) =>\n\t\t\tthis.#report(error, { type: \"extension_error\", conversationId: id, extension }, context),\n\t\t);\n\t}\n\n\t/** Build a conversation's environment from its current `cwd`; `undefined` without an `env` option. */\n\tasync buildEnv(id: ConversationId, context: Context): Promise<ExecutionEnv | undefined> {\n\t\tconst build = this.#options.env;\n\t\tif (build === undefined) return undefined;\n\t\tconst cwd = (await this.snapshot(AgentDoc, id, context))?.cwd;\n\t\treturn build({ conversationId: id, ...(cwd === undefined ? {} : { cwd }), read: this }, context);\n\t}\n\n\t/** Reconcile surviving `running` tasks to `pending`; part of open. */\n\topenTasks(context: Context): Promise<void> {\n\t\treturn this.#tasks.open(context);\n\t}\n\n\tresume(): void {\n\t\tthis.assertUsable();\n\t\tthis.#tasks.resume();\n\t}\n\n\twake(): Wake {\n\t\tthis.assertUsable();\n\t\treturn this.#tasks.wake();\n\t}\n\n\tgetTask<R>(id: TaskId<R>, context: Context): Promise<TaskRecord<JsonValue, JsonValue, R> | undefined> {\n\t\treturn this.readOnLine(() => this.storage.task(id, context)) as Promise<\n\t\t\tTaskRecord<JsonValue, JsonValue, R> | undefined\n\t\t>;\n\t}\n\n\t/** Internal, for tests: sizes of the scheduler's ownership indexes. */\n\tget [SCHEDULER_INDEX_SIZES](): TaskScheduler[\"indexSizes\"] {\n\t\treturn this.#tasks.indexSizes;\n\t}\n\n\tinspect(context: Context): Promise<HarnessInspection> {\n\t\treturn this.readOnLine(async () => {\n\t\t\tconst { scheduling, tasks } = await this.#tasks.inspect(this.#options.registry.snapshot());\n\t\t\tconst scan = (status: \"queued\" | \"placed\") =>\n\t\t\t\tscanAll((cursor) => this.storage.scanSubmissions({ status }, SCAN_PAGE_SIZE, cursor, context));\n\t\t\tconst submissions = [...(await scan(\"queued\")), ...(await scan(\"placed\"))].sort((a, b) => a.id - b.id);\n\t\t\treturn { scheduling, tasks, submissions };\n\t\t});\n\t}\n\n\tsubmission(id: SubmissionId, context: Context): Promise<Submission | undefined> {\n\t\treturn this.#submissions.get(id, context);\n\t}\n\n\tabortSubmission(\n\t\tid: SubmissionId,\n\t\tcontext: Context,\n\t\tconversationId?: ConversationId,\n\t): Promise<\"aborted\" | \"already_placed\" | \"settled\" | \"not_found\"> {\n\t\treturn this.#submissions.abort(id, context, conversationId);\n\t}\n\n\tabortTask(id: TaskId, context: Context): Promise<\"marked\" | \"terminal\"> {\n\t\treturn this.#tasks.abort(id, context);\n\t}\n\n\tretryTask(id: TaskId, context: Context): Promise<void> {\n\t\tthis.assertUsable();\n\t\treturn this.#tasks.retry(id, context);\n\t}\n\n\twaitForTask<R>(id: TaskId<R>, context: Context): Promise<SettledTask<R>> {\n\t\tthis.#tasks.resume();\n\t\treturn this.#tasks.waitForTask(id, context) as Promise<SettledTask<R>>;\n\t}\n\n\twaitForIdle(context: Context): Promise<void> {\n\t\tthis.#tasks.resume();\n\t\treturn this.#tasks.waitForIdle(undefined, context);\n\t}\n\n\t/** Sum every conversation's committed `pi.usage`. Each document is read at its own point; totals only grow. */\n\tasync usage(context: Context): Promise<UsageState> {\n\t\tconst conversations = await this.readOnLine(() =>\n\t\t\tscanAll((cursor) => this.storage.scanConversations({}, SCAN_PAGE_SIZE, cursor, context)),\n\t\t);\n\t\tconst total = UsageDoc.definition.initial();\n\t\tfor (const { id } of conversations) {\n\t\t\tconst state = await this.snapshot(UsageDoc, id, context);\n\t\t\tif (state !== undefined) addUsageState(total, state);\n\t\t}\n\t\treturn total;\n\t}\n\n\ttaskGraph(context: Context): Promise<AttachedReplicatedState<TaskGraph>> {\n\t\treturn this.#taskGraph.state(context);\n\t}\n\n\twatchTaskGraph(context: Context): Promise<TaskGraphWatch> {\n\t\treturn this.#taskGraph.watch(context);\n\t}\n\n\troot(\n\t\tcontext: Context,\n\t\toptions?: { readonly agent?: AgentChange; readonly init?: ConversationInit },\n\t): Promise<Conversation> {\n\t\treturn this.#create({ kind: \"root\" }, options ?? {}, context);\n\t}\n\n\tasync conversation(id: ConversationId, context: Context): Promise<Conversation | undefined> {\n\t\tthis.assertUsable();\n\t\tconst record = await this.readOnLine(() => this.storage.conversation(id, context));\n\t\treturn record === undefined ? undefined : new ConversationImpl(record.id, this.#host);\n\t}\n\n\tcreateConversation(options: ConversationCreateOptions, context: Context): Promise<Conversation> {\n\t\treturn this.#create({ kind: \"independent\", ownership: options.ownership }, options, context);\n\t}\n\n\toverride report(error: unknown, info: ReportInfo = { type: \"listener_error\" }, context?: Context): void {\n\t\tthis.#report(error, info, context);\n\t}\n\n\t/** Signal and join task invocations after the close listeners and before Storage closes; writes no task outcome. */\n\tprotected override beforeClose(): Promise<void> {\n\t\treturn this.#tasks.join();\n\t}\n\n\tasync #create(target: CreateTarget, options: CreateOptions, context: Context): Promise<Conversation> {\n\t\tthis.assertUsable();\n\t\tconst id = await this.commitWith(async (tx) => {\n\t\t\tif (target.kind === \"root\" && (await tx.conversation(ROOT_CONVERSATION_ID)) !== undefined) {\n\t\t\t\treturn ROOT_CONVERSATION_ID;\n\t\t\t}\n\t\t\tconst record =\n\t\t\t\ttarget.kind === \"root\"\n\t\t\t\t\t? await tx.createRootConversation()\n\t\t\t\t\t: target.kind === \"fork\"\n\t\t\t\t\t\t? await tx.forkConversation(target.parentId, target.at, { ownership: target.ownership })\n\t\t\t\t\t\t: await tx.createConversation({ ownership: target.ownership });\n\t\t\tif (options.agent !== undefined) await configure(tx, record.id, options.agent);\n\t\t\tif (options.init !== undefined) await options.init(tx, record.id);\n\t\t\treturn record.id;\n\t\t}, context);\n\t\treturn new ConversationImpl(id, this.#host);\n\t}\n\n\t/**\n\t * The built-in creation hook, in every commit that creates or forks a conversation: empty `pi.live`, `pi.inbox`, and\n\t * `pi.usage`, a fresh `pi.provider`, the conversation's `pi.agent` (see `createAgent()`), then\n\t * `HarnessOptions.conversationCreated`.\n\t */\n\tprotected override async conversationCreated(tx: Transaction, record: ConversationRecord): Promise<void> {\n\t\tawait tx.doc(LiveDoc, record.id);\n\t\tawait tx.doc(InboxDoc, record.id);\n\t\tawait tx.doc(UsageDoc, record.id);\n\t\tawait tx.doc(ProviderDoc, record.id);\n\t\tawait createAgent(tx, record);\n\t\tawait this.#options.conversationCreated?.(tx, record);\n\t}\n}\n\n/** Preserve the host callback's error containment; telemetry adapters are responsible for their own failures. */\nfunction safeReport(\n\tonReport: ((error: unknown, info: ReportInfo) => void) | undefined,\n\ttelemetry: TelemetryContext,\n): (error: unknown, info: ReportInfo, context?: Context) => void {\n\tconst reports = createTypedMetrics(telemetry.metrics ?? NOOP_TELEMETRY_METRICS, [DURABLE_TELEMETRY_SCHEMA]).counter(\n\t\t\"pi.durable.reports\",\n\t);\n\treturn (error, info, context) => {\n\t\tcontained(\n\t\t\t() => onReport?.(error, info),\n\t\t\t() => {},\n\t\t);\n\t\tconst attributes: SpanAttributes = {\n\t\t\ttype: info.type,\n\t\t};\n\t\tswitch (info.type) {\n\t\t\tcase \"task_faulted\":\n\t\t\tcase \"task_outdated\":\n\t\t\t\tattributes.reason = info.reason;\n\t\t\t\tattributes.extension = info.extension;\n\t\t\t\tattributes[\"task.id\"] = info.task.id;\n\t\t\t\tbreak;\n\t\t\tcase \"task_parked\":\n\t\t\tcase \"migration_failed\":\n\t\t\tcase \"task_error\":\n\t\t\tcase \"extension_error\":\n\t\t\t\tattributes.extension = info.extension;\n\t\t\t\tattributes[\"task.id\"] = info.task?.id;\n\t\t\t\tbreak;\n\t\t\tcase \"host_error\":\n\t\t\t\tattributes[\"task.id\"] = info.task?.id;\n\t\t\t\tbreak;\n\t\t}\n\t\treports.add(1, { type: info.type });\n\t\tcontext?.telemetry.addEvent(\"pi.durable.report\", attributes);\n\t};\n}\n\n/**\n * The host clock, falling back to `Date.now` when it throws: a broken clock must not stop commits. The first throw is\n * reported; the clock is read in every task change, so later ones are not.\n */\nexport function safeNow(\n\tnow: (() => number) | undefined,\n\treport: (error: unknown, info: ReportInfo) => void,\n): () => number {\n\tif (now === undefined) return Date.now;\n\tlet reported = false;\n\treturn () => {\n\t\ttry {\n\t\t\treturn now();\n\t\t} catch (error) {\n\t\t\t// Set first: a report handler that reads the clock again must not report again.\n\t\t\tif (!reported) {\n\t\t\t\treported = true;\n\t\t\t\treport(error, { type: \"host_error\", callback: \"now\" });\n\t\t\t}\n\t\t\treturn Date.now();\n\t\t}\n\t};\n}\n\n/**\n * Invocation-bound handle for tasks and tools. Every operation, and every operation of a submission it returns, first\n * checks the invocation and runs under its signal, so it rejects once the invocation ends; admitted work stays durable.\n */\nfunction boundConversation(\n\tid: ConversationId,\n\tbinding: InvocationBinding,\n\tsubmissions: Submissions,\n\ttasks: TaskScheduler,\n): ConversationHandle {\n\tconst bind = (context: Context): Context => withAbortSignal(binding.signal, context);\n\tconst bound = <T>(operation: (context: Context) => Promise<T>) => {\n\t\treturn async (context: Context): Promise<T> => {\n\t\t\tbinding.check();\n\t\t\treturn operation(bind(context));\n\t\t};\n\t};\n\treturn {\n\t\tid,\n\t\tsubmit: async (draft, context) => {\n\t\t\tbinding.check();\n\t\t\tconst submission = await submissions.submit(id, draft, bind(context));\n\t\t\treturn {\n\t\t\t\tid: submission.id,\n\t\t\t\tstatus: bound((callContext) => submission.status(callContext)),\n\t\t\t\twait: bound((callContext) => submission.wait(callContext)),\n\t\t\t\tabort: bound((callContext) => submission.abort(callContext)),\n\t\t\t};\n\t\t},\n\t\tabort: async (context, options) => {\n\t\t\tbinding.check();\n\t\t\treturn tasks.abortConversation(id, options?.background === true, bind(context));\n\t\t},\n\t\twaitForIdle: bound((callContext) => tasks.waitForIdle(id, callContext)),\n\t};\n}\n\n/** Durable agent harness over one Session. */\nexport type Harness = HarnessType;\n\nexport const Harness = {\n\t/** Open a Harness over storage. The registry may keep changing while the Harness runs. */\n\tasync open<Tool extends ToolRegistration>(\n\t\tstorage: Storage,\n\t\toptions: HarnessOptions<Tool>,\n\t\tcontext: Context,\n\t): Promise<Harness> {\n\t\tcontext.abortSignal?.throwIfAborted();\n\t\tconst snapshot = options.registry.snapshot();\n\t\tconst missing = BUILTIN_TASKS.filter((task) => snapshot.task(task.definition.name) === undefined);\n\t\tif (missing.length > 0) {\n\t\t\tconst names = missing.map((task) => task.definition.name).join(\", \");\n\t\t\tthrow new Error(`Registry lacks built-in tasks ${names}; create it with createRegistry()`);\n\t\t}\n\t\tconst harness = new HarnessImpl(storage, options, context);\n\t\ttry {\n\t\t\tawait harness.openTasks(context);\n\t\t} catch (error) {\n\t\t\t// The caller's context may be what failed open: close without it, and rethrow the open error.\n\t\t\t// A failing Storage close fails the Session, which reports it.\n\t\t\tawait harness.close(withoutAbortSignal(context)).catch(() => {});\n\t\t\tthrow error;\n\t\t}\n\t\treturn harness;\n\t},\n};\n"]}
|
package/dist/harness/inbox.d.ts
CHANGED
|
@@ -65,7 +65,7 @@ export declare function isStale(boundary: Boundary, entry: EntryDraft): boolean;
|
|
|
65
65
|
export declare function removeInboxItem(tx: Tx, conversationId: ConversationId, id: SubmissionId): Promise<void>;
|
|
66
66
|
/**
|
|
67
67
|
* Withdraw every queued input of a conversation, as `Conversation.abort()` and abort cascades do: each settles
|
|
68
|
-
* `unanswered` with `aborted` and leaves the inbox; queued writes stay for later placement.
|
|
68
|
+
* `unanswered` with `reason` (default `aborted`) and leaves the inbox; queued writes stay for later placement.
|
|
69
69
|
*/
|
|
70
|
-
export declare function withdrawQueuedInputs(tx: Tx, conversationId: ConversationId): Promise<void>;
|
|
70
|
+
export declare function withdrawQueuedInputs(tx: Tx, conversationId: ConversationId, reason?: string): Promise<void>;
|
|
71
71
|
//# sourceMappingURL=inbox.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"inbox.d.ts","sourceRoot":"","sources":["../../src/harness/inbox.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"inbox.d.ts","sourceRoot":"","sources":["../../src/harness/inbox.ts"],"names":[],"mappings":"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"}
|
package/dist/harness/inbox.js
CHANGED
|
@@ -105,15 +105,15 @@ export async function removeInboxItem(tx, conversationId, id) {
|
|
|
105
105
|
}
|
|
106
106
|
/**
|
|
107
107
|
* Withdraw every queued input of a conversation, as `Conversation.abort()` and abort cascades do: each settles
|
|
108
|
-
* `unanswered` with `aborted` and leaves the inbox; queued writes stay for later placement.
|
|
108
|
+
* `unanswered` with `reason` (default `aborted`) and leaves the inbox; queued writes stay for later placement.
|
|
109
109
|
*/
|
|
110
|
-
export async function withdrawQueuedInputs(tx, conversationId) {
|
|
110
|
+
export async function withdrawQueuedInputs(tx, conversationId, reason = "aborted") {
|
|
111
111
|
const items = (await tx.doc(InboxDoc, conversationId)).items;
|
|
112
112
|
for (let index = items.length - 1; index >= 0; index--) {
|
|
113
113
|
const item = items[index];
|
|
114
114
|
if (item.mode === "write")
|
|
115
115
|
continue;
|
|
116
|
-
tx.settleSubmission(item.id, { status: "unanswered", reason
|
|
116
|
+
tx.settleSubmission(item.id, { status: "unanswered", reason });
|
|
117
117
|
items.splice(index, 1);
|
|
118
118
|
}
|
|
119
119
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"inbox.js","sourceRoot":"","sources":["../../src/harness/inbox.ts"],"names":[],"mappings":"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","sourcesContent":["import { copyJson, type Draft, type JsonRepresentation } from \"@earendil-works/chord\";\nimport { defineDoc } from \"../documents.ts\";\nimport { UserEntry } from \"../entries.ts\";\nimport type { ConversationId, EntryDraft, EntryId, EntryRecord, JsonObject, SubmissionId, Tx } from \"../types.ts\";\nimport type { InputEntry, QueueMode, Settings, UserInput } from \"./types.ts\";\n\n/** A queued submission: user input for a run, with the entry it is placed as when not `pi.user`, or an entry write. */\nexport type InboxItem =\n\t| {\n\t\t\tid: SubmissionId;\n\t\t\tmode: \"steer\" | \"followUp\";\n\t\t\tcontent: JsonRepresentation<UserInput>;\n\t\t\tentry?: JsonRepresentation<InputEntry>;\n\t }\n\t/** `entry` is an `EntryDraft`, stored as plain JSON. */\n\t| { id: SubmissionId; mode: \"write\"; entry: JsonObject };\n\n/** Built-in queue of one conversation's submissions waiting for a boundary, in ID order. */\nexport type InboxState = { items: InboxItem[] };\n\nexport const InboxDoc = defineDoc<InboxState>({\n\tkind: \"pi.inbox\",\n\tversion: 1,\n\tscope: \"conversation\",\n\thistory: \"latest\",\n\tfork: \"initial\",\n\tinitial: () => ({ items: [] }),\n\tcheckpointWhen: (value) => value.items.length === 0,\n});\n\n/** The settings a boundary reads, on the Session line. */\nexport type QueueModes = Pick<Settings, \"steeringMode\" | \"followUpMode\">;\n\n/** What a boundary reads before the commit's first table write, and the newest head it has seen so far. */\nexport type Boundary = {\n\treadonly conversationId: ConversationId;\n\treadonly inbox: Draft<InboxState>;\n\treadonly steeringMode: QueueMode;\n\treadonly followUpMode: QueueMode;\n\t/** Start of the active range, the newest head marker's `head`; advanced by heads written in this commit. */\n\thead: EntryId | undefined;\n};\n\n/** Selected user items, in ID order, and whether a `head: \"self\"` write (a reset) was placed. */\nexport type BoundaryResult = { readonly users: SubmissionId[]; readonly reset: boolean };\n\n/**\n * Read what a boundary needs. Table reads must precede the commit's first table write, so callers prepare the\n * boundary at the start of their commit.\n */\nexport async function prepareBoundary(tx: Tx, conversationId: ConversationId, modes: QueueModes): Promise<Boundary> {\n\tconst head = (await tx.latestHeadMarker(conversationId))?.head;\n\tconst inbox = await tx.doc(InboxDoc, conversationId);\n\treturn {\n\t\tconversationId,\n\t\tinbox,\n\t\tsteeringMode: modes.steeringMode,\n\t\tfollowUpMode: modes.followUpMode,\n\t\thead,\n\t};\n}\n\n/**\n * Place the queued items a boundary selects (spec §6): every write, the first or all steers, and at `final` the first\n * or all follow-ups. A selected reset turns a `postTools` boundary into `final`. Writes are placed first and user\n * items after them, each in ID order, so user items queued before a reset run in the new context. A write whose head\n * targets an entry before the active range, including a range started earlier in this commit, is stale. Selected and\n * stale items are removed positionally.\n */\nexport async function applyBoundary(\n\ttx: Tx,\n\tboundary: Boundary,\n\tat: \"postTools\" | \"final\",\n\tnow: number,\n): Promise<BoundaryResult> {\n\tconst { conversationId, inbox } = boundary;\n\tconst items = inbox.items;\n\tconst reset = hasQueuedReset(items);\n\tconst final = at === \"final\" || reset;\n\tconst pick = (mode: \"steer\" | \"followUp\", queueMode: QueueMode): number[] => {\n\t\tconst indexes = items.flatMap((item, index) => (item.mode === mode ? [index] : []));\n\t\treturn queueMode === \"all\" ? indexes : indexes.slice(0, 1);\n\t};\n\tconst writes = items.flatMap((item, index) => (item.mode === \"write\" ? [index] : []));\n\tconst users = [...pick(\"steer\", boundary.steeringMode), ...(final ? pick(\"followUp\", boundary.followUpMode) : [])];\n\tusers.sort((a, b) => a - b);\n\n\t// `appendEntry()` copies the drafts' values; the items are removed only afterwards.\n\tfor (const index of writes) {\n\t\tconst item = items[index] as Draft<Extract<InboxItem, { mode: \"write\" }>>;\n\t\tconst draft = item.entry as unknown as EntryDraft;\n\t\tif (isStale(boundary, draft)) {\n\t\t\ttx.settleSubmission(item.id, { status: \"unanswered\", reason: \"stale\" });\n\t\t\tcontinue;\n\t\t}\n\t\tconst entry = await tx.appendEntry(conversationId, draft);\n\t\tif (draft.head !== undefined) boundary.head = draft.head === \"self\" ? entry.id : draft.head;\n\t\ttx.placeSubmission(item.id, entry.id);\n\t}\n\tconst placed: SubmissionId[] = [];\n\tfor (const index of users) {\n\t\tconst item = items[index] as Draft<Extract<InboxItem, { mode: \"steer\" | \"followUp\" }>>;\n\t\tconst entry = await appendInput(tx, conversationId, item.content as UserInput, item.entry as InputEntry, now);\n\t\ttx.placeSubmission(item.id, entry.id);\n\t\tplaced.push(item.id);\n\t}\n\tconst removed = [...writes, ...users].sort((a, b) => b - a);\n\tfor (const index of removed) items.splice(index, 1);\n\treturn { users: placed, reset };\n}\n\n/** Append the entry an input is placed as: `entry`'s kind and data, or `pi.user`, with the user message of `content`. */\nexport function appendInput(\n\ttx: Tx,\n\tconversationId: ConversationId,\n\tcontent: UserInput,\n\tentry: InputEntry | undefined,\n\tnow: number,\n): Promise<EntryRecord> {\n\tconst message = { role: \"user\", content, timestamp: now } as const;\n\tif (entry === undefined) return tx.appendEntry(UserEntry, conversationId, { model: [message] });\n\treturn tx.appendEntry(conversationId, { ...pickInputEntry(entry), model: [message] });\n}\n\n/** The kind and data of an input's entry as strict JSON, without other fields an untyped caller might pass. */\nexport function pickInputEntry({ kind, data }: InputEntry): JsonRepresentation<InputEntry> {\n\tconst picked = data === undefined ? { kind } : { kind, data };\n\treturn copyJson(picked, { omitUndefinedProperties: true }) as JsonRepresentation<InputEntry>;\n}\n\n/**\n * Whether a write is display-only: it has no `model`, `head`, or `edits` (present counts, even if empty), so it changes\n * nothing the model sees and needs no boundary.\n */\nexport function isDisplayOnly(entry: EntryDraft): boolean {\n\treturn entry.model === undefined && entry.head === undefined && entry.edits === undefined;\n}\n\n/** Whether a reset (`head: \"self\"` write) is queued; entries appended before it leave the active range when it lands. */\nexport function hasQueuedReset(items: readonly InboxItem[]): boolean {\n\treturn items.some((item) => item.mode === \"write\" && item.entry.head === \"self\");\n}\n\n/** Whether a head write targets an entry before the active range, so placing it would bring back cut history. */\nexport function isStale(boundary: Boundary, entry: EntryDraft): boolean {\n\treturn typeof entry.head === \"number\" && boundary.head !== undefined && entry.head < boundary.head;\n}\n\n/** Remove a withdrawn submission's item; the caller settles the submission. */\nexport async function removeInboxItem(tx: Tx, conversationId: ConversationId, id: SubmissionId): Promise<void> {\n\tconst items = (await tx.doc(InboxDoc, conversationId)).items;\n\tconst index = items.findIndex((item) => item.id === id);\n\tif (index >= 0) items.splice(index, 1);\n}\n\n/**\n * Withdraw every queued input of a conversation, as `Conversation.abort()` and abort cascades do: each settles\n * `unanswered` with `aborted` and leaves the inbox; queued writes stay for later placement.\n */\nexport async function withdrawQueuedInputs(tx: Tx, conversationId: ConversationId): Promise<void> {\n\tconst items = (await tx.doc(InboxDoc, conversationId)).items;\n\tfor (let index = items.length - 1; index >= 0; index--) {\n\t\tconst item = items[index]!;\n\t\tif (item.mode === \"write\") continue;\n\t\ttx.settleSubmission(item.id, { status: \"unanswered\", reason: \"aborted\" });\n\t\titems.splice(index, 1);\n\t}\n}\n"]}
|
|
1
|
+
{"version":3,"file":"inbox.js","sourceRoot":"","sources":["../../src/harness/inbox.ts"],"names":[],"mappings":"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","sourcesContent":["import { copyJson, type Draft, type JsonRepresentation } from \"@earendil-works/chord\";\nimport { defineDoc } from \"../documents.ts\";\nimport { UserEntry } from \"../entries.ts\";\nimport type { ConversationId, EntryDraft, EntryId, EntryRecord, JsonObject, SubmissionId, Tx } from \"../types.ts\";\nimport type { InputEntry, QueueMode, Settings, UserInput } from \"./types.ts\";\n\n/** A queued submission: user input for a run, with the entry it is placed as when not `pi.user`, or an entry write. */\nexport type InboxItem =\n\t| {\n\t\t\tid: SubmissionId;\n\t\t\tmode: \"steer\" | \"followUp\";\n\t\t\tcontent: JsonRepresentation<UserInput>;\n\t\t\tentry?: JsonRepresentation<InputEntry>;\n\t }\n\t/** `entry` is an `EntryDraft`, stored as plain JSON. */\n\t| { id: SubmissionId; mode: \"write\"; entry: JsonObject };\n\n/** Built-in queue of one conversation's submissions waiting for a boundary, in ID order. */\nexport type InboxState = { items: InboxItem[] };\n\nexport const InboxDoc = defineDoc<InboxState>({\n\tkind: \"pi.inbox\",\n\tversion: 1,\n\tscope: \"conversation\",\n\thistory: \"latest\",\n\tfork: \"initial\",\n\tinitial: () => ({ items: [] }),\n\tcheckpointWhen: (value) => value.items.length === 0,\n});\n\n/** The settings a boundary reads, on the Session line. */\nexport type QueueModes = Pick<Settings, \"steeringMode\" | \"followUpMode\">;\n\n/** What a boundary reads before the commit's first table write, and the newest head it has seen so far. */\nexport type Boundary = {\n\treadonly conversationId: ConversationId;\n\treadonly inbox: Draft<InboxState>;\n\treadonly steeringMode: QueueMode;\n\treadonly followUpMode: QueueMode;\n\t/** Start of the active range, the newest head marker's `head`; advanced by heads written in this commit. */\n\thead: EntryId | undefined;\n};\n\n/** Selected user items, in ID order, and whether a `head: \"self\"` write (a reset) was placed. */\nexport type BoundaryResult = { readonly users: SubmissionId[]; readonly reset: boolean };\n\n/**\n * Read what a boundary needs. Table reads must precede the commit's first table write, so callers prepare the\n * boundary at the start of their commit.\n */\nexport async function prepareBoundary(tx: Tx, conversationId: ConversationId, modes: QueueModes): Promise<Boundary> {\n\tconst head = (await tx.latestHeadMarker(conversationId))?.head;\n\tconst inbox = await tx.doc(InboxDoc, conversationId);\n\treturn {\n\t\tconversationId,\n\t\tinbox,\n\t\tsteeringMode: modes.steeringMode,\n\t\tfollowUpMode: modes.followUpMode,\n\t\thead,\n\t};\n}\n\n/**\n * Place the queued items a boundary selects (spec §6): every write, the first or all steers, and at `final` the first\n * or all follow-ups. A selected reset turns a `postTools` boundary into `final`. Writes are placed first and user\n * items after them, each in ID order, so user items queued before a reset run in the new context. A write whose head\n * targets an entry before the active range, including a range started earlier in this commit, is stale. Selected and\n * stale items are removed positionally.\n */\nexport async function applyBoundary(\n\ttx: Tx,\n\tboundary: Boundary,\n\tat: \"postTools\" | \"final\",\n\tnow: number,\n): Promise<BoundaryResult> {\n\tconst { conversationId, inbox } = boundary;\n\tconst items = inbox.items;\n\tconst reset = hasQueuedReset(items);\n\tconst final = at === \"final\" || reset;\n\tconst pick = (mode: \"steer\" | \"followUp\", queueMode: QueueMode): number[] => {\n\t\tconst indexes = items.flatMap((item, index) => (item.mode === mode ? [index] : []));\n\t\treturn queueMode === \"all\" ? indexes : indexes.slice(0, 1);\n\t};\n\tconst writes = items.flatMap((item, index) => (item.mode === \"write\" ? [index] : []));\n\tconst users = [...pick(\"steer\", boundary.steeringMode), ...(final ? pick(\"followUp\", boundary.followUpMode) : [])];\n\tusers.sort((a, b) => a - b);\n\n\t// `appendEntry()` copies the drafts' values; the items are removed only afterwards.\n\tfor (const index of writes) {\n\t\tconst item = items[index] as Draft<Extract<InboxItem, { mode: \"write\" }>>;\n\t\tconst draft = item.entry as unknown as EntryDraft;\n\t\tif (isStale(boundary, draft)) {\n\t\t\ttx.settleSubmission(item.id, { status: \"unanswered\", reason: \"stale\" });\n\t\t\tcontinue;\n\t\t}\n\t\tconst entry = await tx.appendEntry(conversationId, draft);\n\t\tif (draft.head !== undefined) boundary.head = draft.head === \"self\" ? entry.id : draft.head;\n\t\ttx.placeSubmission(item.id, entry.id);\n\t}\n\tconst placed: SubmissionId[] = [];\n\tfor (const index of users) {\n\t\tconst item = items[index] as Draft<Extract<InboxItem, { mode: \"steer\" | \"followUp\" }>>;\n\t\tconst entry = await appendInput(tx, conversationId, item.content as UserInput, item.entry as InputEntry, now);\n\t\ttx.placeSubmission(item.id, entry.id);\n\t\tplaced.push(item.id);\n\t}\n\tconst removed = [...writes, ...users].sort((a, b) => b - a);\n\tfor (const index of removed) items.splice(index, 1);\n\treturn { users: placed, reset };\n}\n\n/** Append the entry an input is placed as: `entry`'s kind and data, or `pi.user`, with the user message of `content`. */\nexport function appendInput(\n\ttx: Tx,\n\tconversationId: ConversationId,\n\tcontent: UserInput,\n\tentry: InputEntry | undefined,\n\tnow: number,\n): Promise<EntryRecord> {\n\tconst message = { role: \"user\", content, timestamp: now } as const;\n\tif (entry === undefined) return tx.appendEntry(UserEntry, conversationId, { model: [message] });\n\treturn tx.appendEntry(conversationId, { ...pickInputEntry(entry), model: [message] });\n}\n\n/** The kind and data of an input's entry as strict JSON, without other fields an untyped caller might pass. */\nexport function pickInputEntry({ kind, data }: InputEntry): JsonRepresentation<InputEntry> {\n\tconst picked = data === undefined ? { kind } : { kind, data };\n\treturn copyJson(picked, { omitUndefinedProperties: true }) as JsonRepresentation<InputEntry>;\n}\n\n/**\n * Whether a write is display-only: it has no `model`, `head`, or `edits` (present counts, even if empty), so it changes\n * nothing the model sees and needs no boundary.\n */\nexport function isDisplayOnly(entry: EntryDraft): boolean {\n\treturn entry.model === undefined && entry.head === undefined && entry.edits === undefined;\n}\n\n/** Whether a reset (`head: \"self\"` write) is queued; entries appended before it leave the active range when it lands. */\nexport function hasQueuedReset(items: readonly InboxItem[]): boolean {\n\treturn items.some((item) => item.mode === \"write\" && item.entry.head === \"self\");\n}\n\n/** Whether a head write targets an entry before the active range, so placing it would bring back cut history. */\nexport function isStale(boundary: Boundary, entry: EntryDraft): boolean {\n\treturn typeof entry.head === \"number\" && boundary.head !== undefined && entry.head < boundary.head;\n}\n\n/** Remove a withdrawn submission's item; the caller settles the submission. */\nexport async function removeInboxItem(tx: Tx, conversationId: ConversationId, id: SubmissionId): Promise<void> {\n\tconst items = (await tx.doc(InboxDoc, conversationId)).items;\n\tconst index = items.findIndex((item) => item.id === id);\n\tif (index >= 0) items.splice(index, 1);\n}\n\n/**\n * Withdraw every queued input of a conversation, as `Conversation.abort()` and abort cascades do: each settles\n * `unanswered` with `reason` (default `aborted`) and leaves the inbox; queued writes stay for later placement.\n */\nexport async function withdrawQueuedInputs(tx: Tx, conversationId: ConversationId, reason = \"aborted\"): Promise<void> {\n\tconst items = (await tx.doc(InboxDoc, conversationId)).items;\n\tfor (let index = items.length - 1; index >= 0; index--) {\n\t\tconst item = items[index]!;\n\t\tif (item.mode === \"write\") continue;\n\t\ttx.settleSubmission(item.id, { status: \"unanswered\", reason });\n\t\titems.splice(index, 1);\n\t}\n}\n"]}
|
package/dist/harness/prompt.d.ts
CHANGED
|
@@ -8,7 +8,7 @@ export declare function replaySections(messages: readonly Message[]): Map<string
|
|
|
8
8
|
* Render the agent's sections in order. `undefined` omits a section; tagged text is wrapped as `<key>\n...\n</key>`. A
|
|
9
9
|
* section that throws keeps its shown text, if any, and is reported; errors after `context` is aborted propagate.
|
|
10
10
|
*/
|
|
11
|
-
export declare function renderSections<Tool extends ToolRegistration>(sections: readonly PromptSection<Tool>[], input: PromptInput<Tool>, shown: ReadonlyMap<string, string>, report: (error: unknown) => void, context: Context): Promise<Map<string, string>>;
|
|
11
|
+
export declare function renderSections<Tool extends ToolRegistration>(sections: readonly PromptSection<Tool>[], input: PromptInput<Tool>, shown: ReadonlyMap<string, string>, report: (error: unknown, section: PromptSection<Tool>) => void, context: Context): Promise<Map<string, string>>;
|
|
12
12
|
type SystemDraft = TypedEntryDraft<never>;
|
|
13
13
|
/**
|
|
14
14
|
* Plan the `pi.system` entries that make the replayed sections and tools of `view` equal `desired` and `tools` in values
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"prompt.d.ts","sourceRoot":"","sources":["../../src/harness/prompt.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,KAAK,EAAE,OAAO,EAAiB,IAAI,EAAiB,MAAM,uBAAuB,CAAC;AAGzF,OAAO,KAAK,EAAe,eAAe,EAAE,MAAM,aAAa,CAAC;AAChE,OAAO,KAAK,EAAE,WAAW,EAAE,WAAW,EAAE,aAAa,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE5F,oHAAoH;AACpH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,SAAS,OAAO,EAAE,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAUhF;AAED;;;GAGG;AACH,wBAAsB,cAAc,CAAC,IAAI,SAAS,gBAAgB,EACjE,QAAQ,EAAE,SAAS,aAAa,CAAC,IAAI,CAAC,EAAE,EACxC,KAAK,EAAE,WAAW,CAAC,IAAI,CAAC,EACxB,KAAK,EAAE,WAAW,CAAC,MAAM,EAAE,MAAM,CAAC,EAClC,MAAM,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,IAAI,
|
|
1
|
+
{"version":3,"file":"prompt.d.ts","sourceRoot":"","sources":["../../src/harness/prompt.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,KAAK,EAAE,OAAO,EAAiB,IAAI,EAAiB,MAAM,uBAAuB,CAAC;AAGzF,OAAO,KAAK,EAAe,eAAe,EAAE,MAAM,aAAa,CAAC;AAChE,OAAO,KAAK,EAAE,WAAW,EAAE,WAAW,EAAE,aAAa,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE5F,oHAAoH;AACpH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,SAAS,OAAO,EAAE,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAUhF;AAED;;;GAGG;AACH,wBAAsB,cAAc,CAAC,IAAI,SAAS,gBAAgB,EACjE,QAAQ,EAAE,SAAS,aAAa,CAAC,IAAI,CAAC,EAAE,EACxC,KAAK,EAAE,WAAW,CAAC,IAAI,CAAC,EACxB,KAAK,EAAE,WAAW,CAAC,MAAM,EAAE,MAAM,CAAC,EAClC,MAAM,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,aAAa,CAAC,IAAI,CAAC,KAAK,IAAI,EAC9D,OAAO,EAAE,OAAO,GACd,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAiB9B;AAED,KAAK,WAAW,GAAG,eAAe,CAAC,KAAK,CAAC,CAAC;AAI1C;;;;;;;;;;;GAWG;AACH,wBAAgB,iBAAiB,CAChC,IAAI,EAAE,WAAW,EACjB,OAAO,EAAE,WAAW,CAAC,MAAM,EAAE,MAAM,CAAC,EACpC,KAAK,EAAE,SAAS,IAAI,EAAE,EACtB,SAAS,EAAE,MAAM,GACf,WAAW,EAAE,CAsBf"}
|
package/dist/harness/prompt.js
CHANGED
|
@@ -29,7 +29,7 @@ export async function renderSections(sections, input, shown, report, context) {
|
|
|
29
29
|
catch (error) {
|
|
30
30
|
if (context.abortSignal?.aborted)
|
|
31
31
|
throw error;
|
|
32
|
-
report(error);
|
|
32
|
+
report(error, section);
|
|
33
33
|
const kept = shown.get(section.key);
|
|
34
34
|
if (kept !== undefined)
|
|
35
35
|
desired.set(section.key, kept);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"prompt.js","sourceRoot":"","sources":["../../src/harness/prompt.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,iBAAiB,EAAE,eAAe,EAAE,iBAAiB,EAAE,MAAM,wCAAwC,CAAC;AAC/G,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAI5C,oHAAoH;AACpH,MAAM,UAAU,cAAc,CAAC,QAA4B;IAC1D,MAAM,KAAK,GAAG,IAAI,GAAG,EAAkB,CAAC;IACxC,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;QAChC,IAAI,OAAO,CAAC,IAAI,KAAK,QAAQ,IAAI,OAAO,CAAC,QAAQ,KAAK,SAAS;YAAE,SAAS;QAC1E,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAC;YAC7D,IAAI,KAAK,KAAK,IAAI;gBAAE,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;;gBACjC,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;QAC5B,CAAC;IACF,CAAC;IACD,OAAO,KAAK,CAAC;AACd,CAAC;AAED;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc,CACnC,QAAwC,EACxC,KAAwB,EACxB,KAAkC,EAClC,MAAgC,EAChC,OAAgB;IAEhB,MAAM,OAAO,GAAG,IAAI,GAAG,EAAkB,CAAC;IAC1C,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;QAChC,IAAI,IAAwB,CAAC;QAC7B,IAAI,CAAC;YACJ,IAAI,GAAG,MAAM,OAAO,CAAC,MAAM,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC;QAC7C,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YAChB,IAAI,OAAO,CAAC,WAAW,EAAE,OAAO;gBAAE,MAAM,KAAK,CAAC;YAC9C,MAAM,CAAC,KAAK,CAAC,CAAC;YACd,MAAM,IAAI,GAAG,KAAK,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;YACpC,IAAI,IAAI,KAAK,SAAS;gBAAE,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC;YACvD,SAAS;QACV,CAAC;QACD,IAAI,IAAI,KAAK,SAAS;YAAE,SAAS;QACjC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,EAAE,OAAO,CAAC,GAAG,KAAK,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,OAAO,CAAC,GAAG,MAAM,IAAI,OAAO,OAAO,CAAC,GAAG,GAAG,CAAC,CAAC;IACzG,CAAC;IACD,OAAO,OAAO,CAAC;AAChB,CAAC;AAMD;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,iBAAiB,CAChC,IAAiB,EACjB,OAAoC,EACpC,KAAsB,EACtB,SAAiB;IAEjB,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC;IACvB,IAAI,IAAI,KAAK,SAAS,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,WAAW,CAAC,EAAE,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,EAAE,GAAG,IAAI,CAAC,EAAE,CAAC,EAAE,CAAC;QACtG,MAAM,KAAK,GAAkB,IAAI,CAAC,OAAO;aACvC,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,WAAW,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC;aACxC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC;QACzD,MAAM,QAAQ,GAAG,WAAW,CAC3B,MAAM,CAAC,WAAW,CAAC,OAAO,CAAC,EAC3B,EAAE,YAAY,EAAE,EAAE,EAAE,UAAU,EAAE,KAAK,CAAC,GAAG,CAAC,iBAAiB,CAAC,EAAE,EAC9D,SAAS,CACT,CAAC;QACF,OAAO,CAAC,KAAK,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,GAAG,QAAQ,EAAE,KAAK,EAAE,CAAC,CAAC;IACjE,CAAC;IACD,MAAM,QAAQ,GAAG,YAAY,CAAC,cAAc,CAAC,IAAI,CAAC,QAAQ,CAAC,EAAE,OAAO,CAAC,CAAC;IACtE,MAAM,OAAO,GAAG,SAAS,CAAC,eAAe,CAAC,IAAI,CAAC,QAAQ,CAAC,EAAE,KAAK,CAAC,CAAC;IACjE,IAAI,OAAO,CAAC,YAAY,CAAC,MAAM,KAAK,CAAC,IAAI,OAAO,CAAC,UAAU,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QAC1E,OAAO,QAAQ,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,WAAW,CAAC,KAAK,EAAE,SAAS,EAAE,SAAS,CAAC,CAAC,CAAC;IAC1E,CAAC;IACD,IAAI,QAAQ,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,CAAC,WAAW,CAAC,SAAS,EAAE,OAAO,EAAE,SAAS,CAAC,CAAC,CAAC;IAC/E,OAAO,QAAQ,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,KAAK,EAAE,EAAE,CACpC,WAAW,CAAC,KAAK,EAAE,KAAK,KAAK,QAAQ,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,EAAE,SAAS,CAAC,CAClF,CAAC;AACH,CAAC;AAED;;;;GAIG;AACH,SAAS,SAAS,CAAC,OAAwB,EAAE,OAAwB;IACpE,MAAM,MAAM,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC,CAAC,CAAC;IACjE,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE;QACpC,MAAM,IAAI,GAAG,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACnC,OAAO,IAAI,KAAK,SAAS,IAAI,iBAAiB,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;IAC5D,CAAC,CAAC,CAAC;IACH,MAAM,SAAS,GAAG,IAAI,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IACzD,MAAM,KAAK,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IAClE,MAAM,QAAQ,GAAG,CAAC,GAAG,IAAI,EAAE,GAAG,KAAK,CAAC,CAAC;IACrC,IAAI,QAAQ,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,KAAK,OAAO,CAAC,KAAK,CAAE,CAAC,IAAI,CAAC,EAAE,CAAC;QACxE,OAAO;YACN,YAAY,EAAE,OAAO,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC;YAC1D,UAAU,EAAE,OAAO,CAAC,GAAG,CAAC,iBAAiB,CAAC;SAC1C,CAAC;IACH,CAAC;IACD,OAAO;QACN,YAAY,EAAE,OAAO,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC;QACtG,UAAU,EAAE,KAAK,CAAC,GAAG,CAAC,iBAAiB,CAAC;KACxC,CAAC;AACH,CAAC;AAED,6GAA6G;AAC7G,SAAS,YAAY,CACpB,KAAkC,EAClC,OAAoC;IAEpC,MAAM,YAAY,GAAG;QACpB,GAAG,CAAC,GAAG,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;QACtD,GAAG,CAAC,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;KACvD,CAAC;IACF,MAAM,YAAY,GAAG,CAAC,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC,CAAC;IACzC,IAAI,YAAY,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,KAAK,EAAE,EAAE,CAAC,GAAG,KAAK,YAAY,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC;QACpE,OAAO,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,GAAG,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,MAAM,CAAC,WAAW,CAAC,OAAO,CAAC,CAAC,CAAC;IACvG,CAAC;IAED,MAAM,KAAK,GAAkC,EAAE,CAAC;IAChD,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,KAAK,EAAE,CAAC;QAClC,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;QAC9B,IAAI,IAAI,KAAK,KAAK;YAAE,KAAK,CAAC,GAAG,CAAC,GAAG,IAAI,IAAI,IAAI,CAAC;IAC/C,CAAC;IACD,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,OAAO;QAAE,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC;YAAE,KAAK,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC;IAC5E,OAAO,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC;AACvD,CAAC;AAED,SAAS,WAAW,CACnB,QAAmD,EACnD,KAA8B,EAC9B,SAAiB;IAEjB,MAAM,OAAO,GAAkB;QAC9B,IAAI,EAAE,QAAQ;QACd,OAAO,EAAE,EAAE;QACX,GAAG,CAAC,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC;QAC/C,GAAG,CAAC,KAAK,KAAK,SAAS,IAAI,KAAK,CAAC,YAAY,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,YAAY,EAAE,KAAK,CAAC,YAAY,EAAE,CAAC;QACvG,GAAG,CAAC,KAAK,KAAK,SAAS,IAAI,KAAK,CAAC,UAAU,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,UAAU,EAAE,KAAK,CAAC,UAAU,EAAE,CAAC;QACjG,SAAS;KACT,CAAC;IACF,OAAO,EAAE,KAAK,EAAE,CAAC,OAAO,CAAC,EAAE,CAAC;AAC7B,CAAC","sourcesContent":["import type { Context } from \"@earendil-works/chord\";\nimport type { Message, SystemMessage, Tool, ToolReference } from \"@earendil-works/pi-ai\";\nimport { declarationsEqual, getCurrentTools, toToolDeclaration } from \"@earendil-works/pi-ai/utils/transcript\";\nimport { SystemEntry } from \"../entries.ts\";\nimport type { ContextEdit, TypedEntryDraft } from \"../types.ts\";\nimport type { ContextView, PromptInput, PromptSection, ToolRegistration } from \"./types.ts\";\n\n/** Sections in effect after replaying system messages in order: set in place, `null` deletes, re-adding appends. */\nexport function replaySections(messages: readonly Message[]): Map<string, string> {\n\tconst shown = new Map<string, string>();\n\tfor (const message of messages) {\n\t\tif (message.role !== \"system\" || message.sections === undefined) continue;\n\t\tfor (const [key, value] of Object.entries(message.sections)) {\n\t\t\tif (value === null) shown.delete(key);\n\t\t\telse shown.set(key, value);\n\t\t}\n\t}\n\treturn shown;\n}\n\n/**\n * Render the agent's sections in order. `undefined` omits a section; tagged text is wrapped as `<key>\\n...\\n</key>`. A\n * section that throws keeps its shown text, if any, and is reported; errors after `context` is aborted propagate.\n */\nexport async function renderSections<Tool extends ToolRegistration>(\n\tsections: readonly PromptSection<Tool>[],\n\tinput: PromptInput<Tool>,\n\tshown: ReadonlyMap<string, string>,\n\treport: (error: unknown) => void,\n\tcontext: Context,\n): Promise<Map<string, string>> {\n\tconst desired = new Map<string, string>();\n\tfor (const section of sections) {\n\t\tlet text: string | undefined;\n\t\ttry {\n\t\t\ttext = await section.render(input, context);\n\t\t} catch (error) {\n\t\t\tif (context.abortSignal?.aborted) throw error;\n\t\t\treport(error);\n\t\t\tconst kept = shown.get(section.key);\n\t\t\tif (kept !== undefined) desired.set(section.key, kept);\n\t\t\tcontinue;\n\t\t}\n\t\tif (text === undefined) continue;\n\t\tdesired.set(section.key, section.tag === false ? text : `<${section.key}>\\n${text}\\n</${section.key}>`);\n\t}\n\treturn desired;\n}\n\ntype SystemDraft = TypedEntryDraft<never>;\n\ntype ToolChanges = { readonly toolsRemoved: ToolReference[]; readonly toolsAdded: Tool[] };\n\n/**\n * Plan the `pi.system` entries that make the replayed sections and tools of `view` equal `desired` and `tools` in values\n * and order.\n *\n * - A head marker with no later `pi.system` entry in context: one complete baseline that omits every retained earlier\n * `pi.system` entry, written even when it restates the replayed values.\n * - Otherwise, when a minimal section patch would leave a different order: remove every shown section, then re-add\n * every desired section in order.\n * - Otherwise the minimal patch of changed values and `null` removals, or nothing.\n *\n * Tool changes ride on the last planned entry, or on one entry of their own.\n */\nexport function planSystemEntries(\n\tview: ContextView,\n\tdesired: ReadonlyMap<string, string>,\n\ttools: readonly Tool[],\n\ttimestamp: number,\n): SystemDraft[] {\n\tconst head = view.head;\n\tif (head !== undefined && !view.entries.some((entry) => SystemEntry.is(entry) && entry.id > head.id)) {\n\t\tconst edits: ContextEdit[] = view.entries\n\t\t\t.filter((entry) => SystemEntry.is(entry))\n\t\t\t.map((entry) => ({ target: entry.id, action: \"omit\" }));\n\t\tconst baseline = systemEntry(\n\t\t\tObject.fromEntries(desired),\n\t\t\t{ toolsRemoved: [], toolsAdded: tools.map(toToolDeclaration) },\n\t\t\ttimestamp,\n\t\t);\n\t\treturn [edits.length === 0 ? baseline : { ...baseline, edits }];\n\t}\n\tconst sections = planSections(replaySections(view.messages), desired);\n\tconst changes = planTools(getCurrentTools(view.messages), tools);\n\tif (changes.toolsRemoved.length === 0 && changes.toolsAdded.length === 0) {\n\t\treturn sections.map((patch) => systemEntry(patch, undefined, timestamp));\n\t}\n\tif (sections.length === 0) return [systemEntry(undefined, changes, timestamp)];\n\treturn sections.map((patch, index) =>\n\t\tsystemEntry(patch, index === sections.length - 1 ? changes : undefined, timestamp),\n\t);\n}\n\n/**\n * Tool changes from `offered` to `desired`. A changed declaration is removed and re-added. Replay keeps retained tools\n * in place and appends additions; when that would not yield the desired order, every offered tool is removed and\n * every desired tool re-added in order.\n */\nfunction planTools(offered: readonly Tool[], desired: readonly Tool[]): ToolChanges {\n\tconst wanted = new Map(desired.map((tool) => [tool.name, tool]));\n\tconst kept = offered.filter((tool) => {\n\t\tconst next = wanted.get(tool.name);\n\t\treturn next !== undefined && declarationsEqual(tool, next);\n\t});\n\tconst keptNames = new Set(kept.map((tool) => tool.name));\n\tconst added = desired.filter((tool) => !keptNames.has(tool.name));\n\tconst replayed = [...kept, ...added];\n\tif (replayed.some((tool, index) => tool.name !== desired[index]!.name)) {\n\t\treturn {\n\t\t\ttoolsRemoved: offered.map((tool) => ({ name: tool.name })),\n\t\t\ttoolsAdded: desired.map(toToolDeclaration),\n\t\t};\n\t}\n\treturn {\n\t\ttoolsRemoved: offered.filter((tool) => !keptNames.has(tool.name)).map((tool) => ({ name: tool.name })),\n\t\ttoolsAdded: added.map(toToolDeclaration),\n\t};\n}\n\n/** Section patches: none, the minimal patch, or a remove-all/re-add-all pair when the order would differ. */\nfunction planSections(\n\tshown: ReadonlyMap<string, string>,\n\tdesired: ReadonlyMap<string, string>,\n): Record<string, string | null>[] {\n\tconst patchedOrder = [\n\t\t...[...shown.keys()].filter((key) => desired.has(key)),\n\t\t...[...desired.keys()].filter((key) => !shown.has(key)),\n\t];\n\tconst desiredOrder = [...desired.keys()];\n\tif (patchedOrder.some((key, index) => key !== desiredOrder[index])) {\n\t\treturn [Object.fromEntries([...shown.keys()].map((key) => [key, null])), Object.fromEntries(desired)];\n\t}\n\n\tconst patch: Record<string, string | null> = {};\n\tfor (const [key, value] of shown) {\n\t\tconst next = desired.get(key);\n\t\tif (next !== value) patch[key] = next ?? null;\n\t}\n\tfor (const [key, value] of desired) if (!shown.has(key)) patch[key] = value;\n\treturn Object.keys(patch).length === 0 ? [] : [patch];\n}\n\nfunction systemEntry(\n\tsections: Record<string, string | null> | undefined,\n\ttools: ToolChanges | undefined,\n\ttimestamp: number,\n): SystemDraft {\n\tconst message: SystemMessage = {\n\t\trole: \"system\",\n\t\tcontent: \"\",\n\t\t...(sections === undefined ? {} : { sections }),\n\t\t...(tools === undefined || tools.toolsRemoved.length === 0 ? {} : { toolsRemoved: tools.toolsRemoved }),\n\t\t...(tools === undefined || tools.toolsAdded.length === 0 ? {} : { toolsAdded: tools.toolsAdded }),\n\t\ttimestamp,\n\t};\n\treturn { model: [message] };\n}\n"]}
|
|
1
|
+
{"version":3,"file":"prompt.js","sourceRoot":"","sources":["../../src/harness/prompt.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Context } from \"@earendil-works/chord\";\nimport type { Message, SystemMessage, Tool, ToolReference } from \"@earendil-works/pi-ai\";\nimport { declarationsEqual, getCurrentTools, toToolDeclaration } from \"@earendil-works/pi-ai/utils/transcript\";\nimport { SystemEntry } from \"../entries.ts\";\nimport type { ContextEdit, TypedEntryDraft } from \"../types.ts\";\nimport type { ContextView, PromptInput, PromptSection, ToolRegistration } from \"./types.ts\";\n\n/** Sections in effect after replaying system messages in order: set in place, `null` deletes, re-adding appends. */\nexport function replaySections(messages: readonly Message[]): Map<string, string> {\n\tconst shown = new Map<string, string>();\n\tfor (const message of messages) {\n\t\tif (message.role !== \"system\" || message.sections === undefined) continue;\n\t\tfor (const [key, value] of Object.entries(message.sections)) {\n\t\t\tif (value === null) shown.delete(key);\n\t\t\telse shown.set(key, value);\n\t\t}\n\t}\n\treturn shown;\n}\n\n/**\n * Render the agent's sections in order. `undefined` omits a section; tagged text is wrapped as `<key>\\n...\\n</key>`. A\n * section that throws keeps its shown text, if any, and is reported; errors after `context` is aborted propagate.\n */\nexport async function renderSections<Tool extends ToolRegistration>(\n\tsections: readonly PromptSection<Tool>[],\n\tinput: PromptInput<Tool>,\n\tshown: ReadonlyMap<string, string>,\n\treport: (error: unknown, section: PromptSection<Tool>) => void,\n\tcontext: Context,\n): Promise<Map<string, string>> {\n\tconst desired = new Map<string, string>();\n\tfor (const section of sections) {\n\t\tlet text: string | undefined;\n\t\ttry {\n\t\t\ttext = await section.render(input, context);\n\t\t} catch (error) {\n\t\t\tif (context.abortSignal?.aborted) throw error;\n\t\t\treport(error, section);\n\t\t\tconst kept = shown.get(section.key);\n\t\t\tif (kept !== undefined) desired.set(section.key, kept);\n\t\t\tcontinue;\n\t\t}\n\t\tif (text === undefined) continue;\n\t\tdesired.set(section.key, section.tag === false ? text : `<${section.key}>\\n${text}\\n</${section.key}>`);\n\t}\n\treturn desired;\n}\n\ntype SystemDraft = TypedEntryDraft<never>;\n\ntype ToolChanges = { readonly toolsRemoved: ToolReference[]; readonly toolsAdded: Tool[] };\n\n/**\n * Plan the `pi.system` entries that make the replayed sections and tools of `view` equal `desired` and `tools` in values\n * and order.\n *\n * - A head marker with no later `pi.system` entry in context: one complete baseline that omits every retained earlier\n * `pi.system` entry, written even when it restates the replayed values.\n * - Otherwise, when a minimal section patch would leave a different order: remove every shown section, then re-add\n * every desired section in order.\n * - Otherwise the minimal patch of changed values and `null` removals, or nothing.\n *\n * Tool changes ride on the last planned entry, or on one entry of their own.\n */\nexport function planSystemEntries(\n\tview: ContextView,\n\tdesired: ReadonlyMap<string, string>,\n\ttools: readonly Tool[],\n\ttimestamp: number,\n): SystemDraft[] {\n\tconst head = view.head;\n\tif (head !== undefined && !view.entries.some((entry) => SystemEntry.is(entry) && entry.id > head.id)) {\n\t\tconst edits: ContextEdit[] = view.entries\n\t\t\t.filter((entry) => SystemEntry.is(entry))\n\t\t\t.map((entry) => ({ target: entry.id, action: \"omit\" }));\n\t\tconst baseline = systemEntry(\n\t\t\tObject.fromEntries(desired),\n\t\t\t{ toolsRemoved: [], toolsAdded: tools.map(toToolDeclaration) },\n\t\t\ttimestamp,\n\t\t);\n\t\treturn [edits.length === 0 ? baseline : { ...baseline, edits }];\n\t}\n\tconst sections = planSections(replaySections(view.messages), desired);\n\tconst changes = planTools(getCurrentTools(view.messages), tools);\n\tif (changes.toolsRemoved.length === 0 && changes.toolsAdded.length === 0) {\n\t\treturn sections.map((patch) => systemEntry(patch, undefined, timestamp));\n\t}\n\tif (sections.length === 0) return [systemEntry(undefined, changes, timestamp)];\n\treturn sections.map((patch, index) =>\n\t\tsystemEntry(patch, index === sections.length - 1 ? changes : undefined, timestamp),\n\t);\n}\n\n/**\n * Tool changes from `offered` to `desired`. A changed declaration is removed and re-added. Replay keeps retained tools\n * in place and appends additions; when that would not yield the desired order, every offered tool is removed and\n * every desired tool re-added in order.\n */\nfunction planTools(offered: readonly Tool[], desired: readonly Tool[]): ToolChanges {\n\tconst wanted = new Map(desired.map((tool) => [tool.name, tool]));\n\tconst kept = offered.filter((tool) => {\n\t\tconst next = wanted.get(tool.name);\n\t\treturn next !== undefined && declarationsEqual(tool, next);\n\t});\n\tconst keptNames = new Set(kept.map((tool) => tool.name));\n\tconst added = desired.filter((tool) => !keptNames.has(tool.name));\n\tconst replayed = [...kept, ...added];\n\tif (replayed.some((tool, index) => tool.name !== desired[index]!.name)) {\n\t\treturn {\n\t\t\ttoolsRemoved: offered.map((tool) => ({ name: tool.name })),\n\t\t\ttoolsAdded: desired.map(toToolDeclaration),\n\t\t};\n\t}\n\treturn {\n\t\ttoolsRemoved: offered.filter((tool) => !keptNames.has(tool.name)).map((tool) => ({ name: tool.name })),\n\t\ttoolsAdded: added.map(toToolDeclaration),\n\t};\n}\n\n/** Section patches: none, the minimal patch, or a remove-all/re-add-all pair when the order would differ. */\nfunction planSections(\n\tshown: ReadonlyMap<string, string>,\n\tdesired: ReadonlyMap<string, string>,\n): Record<string, string | null>[] {\n\tconst patchedOrder = [\n\t\t...[...shown.keys()].filter((key) => desired.has(key)),\n\t\t...[...desired.keys()].filter((key) => !shown.has(key)),\n\t];\n\tconst desiredOrder = [...desired.keys()];\n\tif (patchedOrder.some((key, index) => key !== desiredOrder[index])) {\n\t\treturn [Object.fromEntries([...shown.keys()].map((key) => [key, null])), Object.fromEntries(desired)];\n\t}\n\n\tconst patch: Record<string, string | null> = {};\n\tfor (const [key, value] of shown) {\n\t\tconst next = desired.get(key);\n\t\tif (next !== value) patch[key] = next ?? null;\n\t}\n\tfor (const [key, value] of desired) if (!shown.has(key)) patch[key] = value;\n\treturn Object.keys(patch).length === 0 ? [] : [patch];\n}\n\nfunction systemEntry(\n\tsections: Record<string, string | null> | undefined,\n\ttools: ToolChanges | undefined,\n\ttimestamp: number,\n): SystemDraft {\n\tconst message: SystemMessage = {\n\t\trole: \"system\",\n\t\tcontent: \"\",\n\t\t...(sections === undefined ? {} : { sections }),\n\t\t...(tools === undefined || tools.toolsRemoved.length === 0 ? {} : { toolsRemoved: tools.toolsRemoved }),\n\t\t...(tools === undefined || tools.toolsAdded.length === 0 ? {} : { toolsAdded: tools.toolsAdded }),\n\t\ttimestamp,\n\t};\n\treturn { model: [message] };\n}\n"]}
|