@code-yeongyu/senpi-agent-core 2026.9.30 → 2026.10.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +49 -20
- package/dist/agent-loop.d.ts +27 -3
- package/dist/agent-loop.js +192 -56
- package/dist/agent.d.ts +21 -7
- package/dist/agent.js +38 -18
- package/dist/harness/execution/tools.d.ts +1 -1
- package/dist/harness/execution/tools.js +0 -2
- package/dist/harness/messages.js +1 -0
- package/dist/harness/pico3/bash.d.ts +10 -0
- package/dist/harness/pico3/bash.js +25 -0
- package/dist/harness/pico3/bounded.d.ts +21 -0
- package/dist/harness/pico3/bounded.js +95 -0
- package/dist/harness/pico3/chord.d.ts +41 -0
- package/dist/harness/pico3/chord.js +147 -0
- package/dist/harness/pico3/context.d.ts +16 -0
- package/dist/harness/pico3/context.js +88 -0
- package/dist/harness/pico3/harness.d.ts +198 -0
- package/dist/harness/pico3/harness.js +645 -0
- package/dist/harness/pico3/hooks.d.ts +10 -0
- package/dist/harness/pico3/hooks.js +33 -0
- package/dist/harness/pico3/index.d.ts +19 -0
- package/dist/harness/pico3/index.js +15 -0
- package/dist/harness/pico3/jsonl.d.ts +58 -0
- package/dist/harness/pico3/jsonl.js +322 -0
- package/dist/harness/pico3/kinds/collapse.d.ts +49 -0
- package/dist/harness/pico3/kinds/collapse.js +191 -0
- package/dist/harness/pico3/kinds/entries.d.ts +78 -0
- package/dist/harness/pico3/kinds/entries.js +13 -0
- package/dist/harness/pico3/kinds/frames.d.ts +9 -0
- package/dist/harness/pico3/kinds/frames.js +75 -0
- package/dist/harness/pico3/kinds/generation.d.ts +94 -0
- package/dist/harness/pico3/kinds/generation.js +504 -0
- package/dist/harness/pico3/kinds/job.d.ts +44 -0
- package/dist/harness/pico3/kinds/job.js +143 -0
- package/dist/harness/pico3/kinds/plugin.d.ts +15 -0
- package/dist/harness/pico3/kinds/plugin.js +35 -0
- package/dist/harness/pico3/kinds/post-tools.d.ts +22 -0
- package/dist/harness/pico3/kinds/post-tools.js +145 -0
- package/dist/harness/pico3/kinds/task-api.d.ts +3 -0
- package/dist/harness/pico3/kinds/task-api.js +45 -0
- package/dist/harness/pico3/kinds/tool.d.ts +43 -0
- package/dist/harness/pico3/kinds/tool.js +373 -0
- package/dist/harness/pico3/legacy-tracker.d.ts +11 -0
- package/dist/harness/pico3/legacy-tracker.js +39 -0
- package/dist/harness/pico3/membrane.d.ts +23 -0
- package/dist/harness/pico3/membrane.js +140 -0
- package/dist/harness/pico3/memory.d.ts +53 -0
- package/dist/harness/pico3/memory.js +265 -0
- package/dist/harness/pico3/scheduler.d.ts +49 -0
- package/dist/harness/pico3/scheduler.js +437 -0
- package/dist/harness/pico3/session.d.ts +264 -0
- package/dist/harness/pico3/session.js +1328 -0
- package/dist/harness/pico3/system.d.ts +126 -0
- package/dist/harness/pico3/system.js +244 -0
- package/dist/harness/pico3/types.d.ts +973 -0
- package/dist/harness/pico3/types.js +94 -0
- package/dist/harness/pico3/view.d.ts +34 -0
- package/dist/harness/pico3/view.js +404 -0
- package/dist/harness/runtime/drive/tool-placement.js +2 -27
- package/dist/harness/telemetry.d.ts +36 -36
- package/dist/harness/tools/image.js +1 -1
- package/dist/proxy.d.ts +2 -2
- package/dist/types.d.ts +111 -34
- package/package.json +9 -5
|
@@ -0,0 +1,264 @@
|
|
|
1
|
+
import { type Context } from "@earendil-works/chord";
|
|
2
|
+
import { type Op } from "@earendil-works/chord/delta";
|
|
3
|
+
import { type Tracker } from "./legacy-tracker.ts";
|
|
4
|
+
import { type AnyKind, type Checkpoint, type ContextView, type Conversation, type ConversationSpec, type CoreTx, type DocRef, type Entry, type EntryInput, type EntryKind, type EntryRef, type EntryScan, type Id, type Input, type InputOf, type Invoker, type JsonObject, type JsonValue, type Namespace, type NamespaceRegistration, type NewEntry, type OwnedConversationSpec, type RewindableState, type SendInput, type Seq, type SessionState, type SlotOf, type StickyState, type Storage, type Task, type TaskOf, type TaskRef, type TaskScan, type TaskSpec, type ToolSlot, type ViewEvent, type Write } from "./types.ts";
|
|
5
|
+
/** Remove matching elements from a tracked array IN PLACE (never `arr = arr.filter(...)` on a tracked doc). */
|
|
6
|
+
export declare function removeWhere<T>(arr: T[], pred: (item: T) => boolean): void;
|
|
7
|
+
export declare const isCoreKind: (name: string) => boolean;
|
|
8
|
+
/** Declared config defaults, derived from the registered kinds. Nothing is duplicated elsewhere. */
|
|
9
|
+
export declare class Defaults {
|
|
10
|
+
readonly rewindable: JsonObject;
|
|
11
|
+
readonly sticky: JsonObject;
|
|
12
|
+
readonly route: Map<string, "rewindable" | "sticky">;
|
|
13
|
+
private readonly owners;
|
|
14
|
+
constructor(kinds: Iterable<AnyKind>);
|
|
15
|
+
register(kind: AnyKind): void;
|
|
16
|
+
unregister(kind: AnyKind): void;
|
|
17
|
+
validate(key: string, value: unknown): value is JsonValue;
|
|
18
|
+
validateSeed(doc: "rewindable" | "sticky", seed: object): JsonObject;
|
|
19
|
+
/** Fill declared keys that are absent (never `??`: a stored null is a value). */
|
|
20
|
+
fill(doc: "rewindable" | "sticky", target: JsonObject): void;
|
|
21
|
+
freshRewindable(over?: Partial<RewindableState>, preservePlugins?: boolean): RewindableState;
|
|
22
|
+
freshSticky(over?: Partial<StickyState>): StickyState;
|
|
23
|
+
}
|
|
24
|
+
declare class Docs {
|
|
25
|
+
private readonly trackers;
|
|
26
|
+
private readonly storage;
|
|
27
|
+
private readonly defaults;
|
|
28
|
+
/** Bytes of ops written since the last base, per document. Drives rebase+truncate. */
|
|
29
|
+
readonly sinceBase: Map<string, number>;
|
|
30
|
+
constructor(storage: Storage, defaults: Defaults);
|
|
31
|
+
noteOps(ref: DocRef, ops: Op[]): void;
|
|
32
|
+
requestBase(ref: DocRef): void;
|
|
33
|
+
get(ref: DocRef, ctx: Context): Promise<Tracker<object>>;
|
|
34
|
+
evict(ref: DocRef): void;
|
|
35
|
+
peek(ref: DocRef): Tracker<object> | undefined;
|
|
36
|
+
loaded(ref: DocRef): JsonObject | undefined;
|
|
37
|
+
adopt(ref: DocRef, tracker: Tracker<object>): void;
|
|
38
|
+
}
|
|
39
|
+
export interface CommitChanges {
|
|
40
|
+
entries: Entry[];
|
|
41
|
+
tasks: Task[];
|
|
42
|
+
inputs: Input[];
|
|
43
|
+
conversations: Conversation[];
|
|
44
|
+
docs: {
|
|
45
|
+
ref: DocRef;
|
|
46
|
+
ops: Op[];
|
|
47
|
+
}[];
|
|
48
|
+
events: {
|
|
49
|
+
conversationId: Id;
|
|
50
|
+
event: ViewEvent;
|
|
51
|
+
}[];
|
|
52
|
+
}
|
|
53
|
+
/** Session-side conversation index: owner/parent graph for subtree checks and ancestry. */
|
|
54
|
+
export interface ConversationIndex {
|
|
55
|
+
get(id: Id): Conversation | undefined;
|
|
56
|
+
/** Conversation ids in the subtree rooted at `root` (inclusive), via ownership. */
|
|
57
|
+
subtree(root: Id): Set<Id>;
|
|
58
|
+
/** Conversation ids from the root down to `id` (exclusive of `id`) via ownership. */
|
|
59
|
+
ancestors(id: Id): Id[];
|
|
60
|
+
}
|
|
61
|
+
declare class TxImpl implements CoreTx {
|
|
62
|
+
private readonly writes;
|
|
63
|
+
private readonly touched;
|
|
64
|
+
private readonly membrane;
|
|
65
|
+
private readonly createdTasks;
|
|
66
|
+
private readonly createdEntries;
|
|
67
|
+
private readonly createdConversations;
|
|
68
|
+
private readonly inputsById;
|
|
69
|
+
private readonly inputsByRequest;
|
|
70
|
+
/**
|
|
71
|
+
* Transaction-local identity cache for heterogeneous namespace façades.
|
|
72
|
+
* Keys are current namespace token objects, validated before lookup; values are
|
|
73
|
+
* merged membrane wrappers. TxImpl owns the map and revoke() invalidates every value.
|
|
74
|
+
*/
|
|
75
|
+
private readonly namespaceViews;
|
|
76
|
+
private readonly changedConfig;
|
|
77
|
+
private readonly wroteEntries;
|
|
78
|
+
private wroteTasks;
|
|
79
|
+
private poisoned;
|
|
80
|
+
private surfaceActive;
|
|
81
|
+
/** Set while a terminal closure runs: the invoker's task counts as gone for busy(). */
|
|
82
|
+
closing: boolean;
|
|
83
|
+
readonly changes: CommitChanges;
|
|
84
|
+
readonly invoker: Invoker;
|
|
85
|
+
private readonly storage;
|
|
86
|
+
private readonly docs;
|
|
87
|
+
private readonly defaults;
|
|
88
|
+
private readonly kinds;
|
|
89
|
+
private readonly namespaces;
|
|
90
|
+
private readonly liveTasks;
|
|
91
|
+
private readonly conversations;
|
|
92
|
+
private readonly now;
|
|
93
|
+
private readonly ctx;
|
|
94
|
+
constructor(invoker: Invoker, storage: Storage, docs: Docs, defaults: Defaults, kinds: ReadonlyMap<string, AnyKind>, namespaces: ReadonlyMap<string, NamespaceRegistration>, liveTasks: ReadonlyMap<Id, Task>, conversations: ConversationIndex, now: () => number, ctx: Context);
|
|
95
|
+
callbackSurface(): TxImpl;
|
|
96
|
+
closeSurface(): void;
|
|
97
|
+
private assertSurfaceActive;
|
|
98
|
+
private get core();
|
|
99
|
+
private assertCore;
|
|
100
|
+
private assertNotHost;
|
|
101
|
+
/** A task may touch its own conversation and the subtree it owns. The host and core may touch anything. */
|
|
102
|
+
private inScope;
|
|
103
|
+
private assertScope;
|
|
104
|
+
private assertEntryScope;
|
|
105
|
+
private poison;
|
|
106
|
+
private assertNoEntryWrites;
|
|
107
|
+
private assertNoTaskWrites;
|
|
108
|
+
get poison_(): Error | undefined;
|
|
109
|
+
conversation(id: Id): Promise<Conversation | undefined>;
|
|
110
|
+
entry(id: Id): Promise<Entry | undefined>;
|
|
111
|
+
entry<E extends Entry>(kind: EntryKind<E>, id: Id): Promise<E | undefined>;
|
|
112
|
+
entries(ids: readonly Id[]): Promise<Map<number, Entry>>;
|
|
113
|
+
newestEntry(conversationId: Id, opts?: {
|
|
114
|
+
kind?: string;
|
|
115
|
+
withHead?: boolean;
|
|
116
|
+
}): Promise<Entry | undefined>;
|
|
117
|
+
newestEntry<E extends Entry>(conversationId: Id, kind: EntryKind<E>): Promise<E | undefined>;
|
|
118
|
+
scanEntries(scan: EntryScan): Promise<Entry[]>;
|
|
119
|
+
context(conversationId: Id, at?: Id): Promise<ContextView>;
|
|
120
|
+
task(id: Id): Promise<Task | undefined>;
|
|
121
|
+
task<K extends AnyKind>(ref: TaskRef<K>): Promise<TaskOf<K> | undefined>;
|
|
122
|
+
tasks(scan: TaskScan): Promise<Task<import("@earendil-works/chord").JsonValue, Checkpoint>[]>;
|
|
123
|
+
input(id: Id): Promise<Input | undefined>;
|
|
124
|
+
private inputByRequest;
|
|
125
|
+
rewindableAsOf(conversationId: Id, at: Id): Promise<RewindableState | undefined>;
|
|
126
|
+
snapshot(ref: {
|
|
127
|
+
doc: "rewindable";
|
|
128
|
+
conversationId: Id;
|
|
129
|
+
}): RewindableState;
|
|
130
|
+
snapshot(ref: {
|
|
131
|
+
doc: "sticky";
|
|
132
|
+
conversationId: Id;
|
|
133
|
+
}): StickyState;
|
|
134
|
+
snapshot(ref: {
|
|
135
|
+
doc: "session";
|
|
136
|
+
}): SessionState;
|
|
137
|
+
private doc;
|
|
138
|
+
private view;
|
|
139
|
+
preload(refs: DocRef[]): Promise<void>;
|
|
140
|
+
rewindable(conversationId: Id): RewindableState;
|
|
141
|
+
sticky(conversationId: Id): StickyState;
|
|
142
|
+
session(): SessionState;
|
|
143
|
+
/** Internal, unchecked. */
|
|
144
|
+
private raw;
|
|
145
|
+
plugins<T extends JsonObject>(namespace: Namespace<T>): T;
|
|
146
|
+
emit<T extends JsonObject>(namespace: Namespace<T>, name: string, data: JsonValue): void;
|
|
147
|
+
emit(event: ViewEvent): void;
|
|
148
|
+
private invocationConversationId;
|
|
149
|
+
config(conversationId: Id): {
|
|
150
|
+
get: (key: string) => import("@earendil-works/chord").JsonValue | undefined;
|
|
151
|
+
set: (key: string, value: JsonValue) => void;
|
|
152
|
+
reset: (key: string) => void;
|
|
153
|
+
};
|
|
154
|
+
slot<K extends AnyKind>(ref: TaskRef<K>): SlotOf<K>;
|
|
155
|
+
toolSlot(task: {
|
|
156
|
+
conversationId: Id;
|
|
157
|
+
input: {
|
|
158
|
+
index: number;
|
|
159
|
+
};
|
|
160
|
+
}): ToolSlot;
|
|
161
|
+
appendEntry(conversationId: Id, entry: NewEntry): Id;
|
|
162
|
+
appendEntry<E extends Entry>(conversationId: Id, kind: EntryKind<E>, entry: EntryInput<E>): EntryRef<E>;
|
|
163
|
+
private appendEntryInternal;
|
|
164
|
+
write(conversationId: Id, entry: NewEntry): Promise<Id>;
|
|
165
|
+
write<E extends Entry>(conversationId: Id, kind: EntryKind<E>, entry: EntryInput<E>): Promise<Id>;
|
|
166
|
+
checkpoint<C extends Checkpoint>(value: C): void;
|
|
167
|
+
/** Kernel-internal: replace a task's mutable fields. Persists only what changed. */
|
|
168
|
+
setTask(task: Task): void;
|
|
169
|
+
setTaskInternalForControl(task: Task): void;
|
|
170
|
+
private setTaskInternal;
|
|
171
|
+
createTask(spec: TaskSpec): Id;
|
|
172
|
+
createTask<K extends AnyKind>(kind: K, input: InputOf<K>, opts?: {
|
|
173
|
+
conversationId?: Id;
|
|
174
|
+
background?: true;
|
|
175
|
+
after?: Id[];
|
|
176
|
+
}): TaskRef<K>;
|
|
177
|
+
private createTaskInternal;
|
|
178
|
+
private hasLiveKind;
|
|
179
|
+
createConversation(spec: ConversationSpec): Id;
|
|
180
|
+
createForkConversation(spec: ConversationSpec): Id;
|
|
181
|
+
createOwnedConversation(ownerTaskId: Id, sourceConversationId: Id, spec: OwnedConversationSpec): Promise<Id>;
|
|
182
|
+
private insertConversation;
|
|
183
|
+
private seedDoc;
|
|
184
|
+
markTask(id: Id): void;
|
|
185
|
+
/** Prospective: live turn tasks, minus this transaction's terminals and the closing task, plus this transaction's new turn tasks. */
|
|
186
|
+
busy(conversationId: Id): boolean;
|
|
187
|
+
private putInput;
|
|
188
|
+
send(conversationId: Id, input: SendInput): Promise<Id>;
|
|
189
|
+
private setInput;
|
|
190
|
+
/** Kernel: withdraw a queued input. */
|
|
191
|
+
withdrawInput(id: Id): Promise<"aborted" | "already_placed" | "not_found">;
|
|
192
|
+
resolveInputs(ids: readonly Id[], resolution: {
|
|
193
|
+
status: "done";
|
|
194
|
+
answer: Id;
|
|
195
|
+
} | {
|
|
196
|
+
status: "unanswered";
|
|
197
|
+
reason: NonNullable<Input["reason"]>;
|
|
198
|
+
detail?: string;
|
|
199
|
+
}): Promise<void>;
|
|
200
|
+
/**
|
|
201
|
+
* Boundary placement (pico §9.5). No storage scan: `headBoundary` is the newest head as the
|
|
202
|
+
* caller knows it, and it advances locally as same-batch self-heads are placed.
|
|
203
|
+
*/
|
|
204
|
+
boundary(conversationId: Id, at: "postTools" | "final", headBoundary: Id | undefined): Promise<{
|
|
205
|
+
triggers: Id[];
|
|
206
|
+
terminated: boolean;
|
|
207
|
+
}>;
|
|
208
|
+
finish(): Write[];
|
|
209
|
+
/** Every wrapper handed out by this transaction throws from now on. */
|
|
210
|
+
revoke(): void;
|
|
211
|
+
evictTouched(): void;
|
|
212
|
+
}
|
|
213
|
+
export declare class NestedLineOperation extends Error {
|
|
214
|
+
constructor();
|
|
215
|
+
}
|
|
216
|
+
export interface CommitResult<T> {
|
|
217
|
+
value: T;
|
|
218
|
+
seq: Seq | undefined;
|
|
219
|
+
changes: CommitChanges;
|
|
220
|
+
}
|
|
221
|
+
export interface TransactionControl {
|
|
222
|
+
setTask(task: Task): void;
|
|
223
|
+
}
|
|
224
|
+
export declare class Session {
|
|
225
|
+
readonly storage: Storage;
|
|
226
|
+
readonly kinds: ReadonlyMap<string, AnyKind>;
|
|
227
|
+
readonly namespaces: ReadonlyMap<string, NamespaceRegistration>;
|
|
228
|
+
private tail;
|
|
229
|
+
private closed;
|
|
230
|
+
private fault;
|
|
231
|
+
private readonly now;
|
|
232
|
+
readonly docs: Docs;
|
|
233
|
+
readonly defaults: Defaults;
|
|
234
|
+
readonly liveTasks: Map<number, Task<import("@earendil-works/chord").JsonValue, Checkpoint>>;
|
|
235
|
+
/** Owner/parent graph, loaded at open and maintained on every commit. */
|
|
236
|
+
readonly conversationRecords: Map<number, Conversation>;
|
|
237
|
+
readonly lineListeners: Set<(result: CommitResult<unknown>) => void>;
|
|
238
|
+
readonly listeners: Set<(r: CommitResult<unknown>) => void>;
|
|
239
|
+
/** Errors from listeners and other post-commit work; never surface to the writer. */
|
|
240
|
+
onReport: (error: unknown) => void;
|
|
241
|
+
constructor(storage: Storage, kinds: ReadonlyMap<string, AnyKind>, namespaces: ReadonlyMap<string, NamespaceRegistration>, now?: () => number);
|
|
242
|
+
readonly index: ConversationIndex;
|
|
243
|
+
/** Owner tasks that are terminal but whose conversations still exist (ancestry after reopen). */
|
|
244
|
+
readonly ownerTaskCache: Map<number, Task<import("@earendil-works/chord").JsonValue, Checkpoint>>;
|
|
245
|
+
commit<T>(invoker: Invoker, fn: (tx: TxImpl, ctx: Context, control: TransactionControl) => T | Promise<T>, ctx: Context, opts?: {
|
|
246
|
+
docs?: DocRef[];
|
|
247
|
+
closing?: boolean;
|
|
248
|
+
}): Promise<CommitResult<T>>;
|
|
249
|
+
/** Read-only line operation without a transaction. */
|
|
250
|
+
read<T>(fn: (storage: Storage, ctx: Context) => Promise<T>, ctx: Context): Promise<T>;
|
|
251
|
+
/** Generic line operation (waiter registration and asynchronous lifecycle work). */
|
|
252
|
+
onLine<T>(fn: (ctx: Context) => T | Promise<T>, ctx: Context): Promise<T>;
|
|
253
|
+
static readonly STICKY_BASE_BUDGET: number;
|
|
254
|
+
/** After a task terminalizes: retire its slot; base + truncate when idle or over budget. Truncation runs on the line. */
|
|
255
|
+
retire(task: Task, ctx: Context): Promise<void>;
|
|
256
|
+
fork(parentId: Id, at: Id | "start", spec: Omit<ConversationSpec, "parent">, ctx: Context): Promise<Id>;
|
|
257
|
+
close(ctx: Context): Promise<void>;
|
|
258
|
+
loadedDocument(ref: DocRef): JsonObject | undefined;
|
|
259
|
+
private applyChanges;
|
|
260
|
+
private enter;
|
|
261
|
+
private assertUsable;
|
|
262
|
+
}
|
|
263
|
+
export type { TxImpl };
|
|
264
|
+
//# sourceMappingURL=session.d.ts.map
|