@fungi.computer/shiitake 0.0.0-stage → 0.1.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/LICENSE +21 -0
- package/README.md +454 -2
- package/dist/agar-extension.d.ts +9 -0
- package/dist/agar-extension.js +38 -0
- package/dist/agent-control.d.ts +77 -0
- package/dist/agent-control.js +434 -0
- package/dist/client-entry.d.ts +211 -0
- package/dist/client-entry.js +101 -0
- package/dist/client-wire.d.ts +199 -0
- package/dist/client-wire.js +271 -0
- package/dist/client.d.ts +439 -0
- package/dist/client.js +4 -0
- package/dist/cloudflare.d.ts +220 -0
- package/dist/cloudflare.js +531 -0
- package/dist/effect.d.ts +42 -0
- package/dist/effect.js +20 -0
- package/dist/errors.d.ts +50 -0
- package/dist/errors.js +81 -0
- package/dist/extension-client.d.ts +38 -0
- package/dist/extension-client.js +56 -0
- package/dist/extension-contract.d.ts +73 -0
- package/dist/extension-contract.js +11 -0
- package/dist/extensions.d.ts +589 -0
- package/dist/extensions.js +263 -0
- package/dist/fleet.d.ts +313 -0
- package/dist/fleet.js +540 -0
- package/dist/hosted.d.ts +133 -0
- package/dist/hosted.js +265 -0
- package/dist/http-routes.d.ts +772 -0
- package/dist/http-routes.js +242 -0
- package/dist/http.d.ts +1 -0
- package/dist/http.js +1 -0
- package/dist/index.d.ts +35 -0
- package/dist/index.js +13 -0
- package/dist/internal/accepted-run-executor.d.ts +23 -0
- package/dist/internal/accepted-run-executor.js +129 -0
- package/dist/internal/admission-door.d.ts +75 -0
- package/dist/internal/admission-door.js +105 -0
- package/dist/internal/agent-close.d.ts +4 -0
- package/dist/internal/agent-close.js +42 -0
- package/dist/internal/browser-sessions.d.ts +31 -0
- package/dist/internal/browser-sessions.js +173 -0
- package/dist/internal/client-boundary.d.ts +262 -0
- package/dist/internal/client-boundary.js +202 -0
- package/dist/internal/compaction/compaction.d.ts +54 -0
- package/dist/internal/compaction/compaction.js +291 -0
- package/dist/internal/compaction/session-compaction.d.ts +69 -0
- package/dist/internal/compaction/session-compaction.js +330 -0
- package/dist/internal/compaction/settings.d.ts +11 -0
- package/dist/internal/compaction/settings.js +40 -0
- package/dist/internal/compaction/utils.d.ts +45 -0
- package/dist/internal/compaction/utils.js +319 -0
- package/dist/internal/contracts.d.ts +235 -0
- package/dist/internal/contracts.js +1 -0
- package/dist/internal/coordinator.d.ts +18 -0
- package/dist/internal/coordinator.js +362 -0
- package/dist/internal/document-codec.d.ts +11 -0
- package/dist/internal/document-codec.js +39 -0
- package/dist/internal/effect-client.d.ts +13 -0
- package/dist/internal/effect-client.js +102 -0
- package/dist/internal/effect-contracts.d.ts +236 -0
- package/dist/internal/effect-contracts.js +2 -0
- package/dist/internal/extension-command-registry.d.ts +11 -0
- package/dist/internal/extension-command-registry.js +29 -0
- package/dist/internal/extension-command-tools.d.ts +17 -0
- package/dist/internal/extension-command-tools.js +50 -0
- package/dist/internal/extension-context.d.ts +25 -0
- package/dist/internal/extension-context.js +35 -0
- package/dist/internal/extension-definitions.d.ts +5 -0
- package/dist/internal/extension-definitions.js +6 -0
- package/dist/internal/extension-hook.d.ts +25 -0
- package/dist/internal/extension-hook.js +46 -0
- package/dist/internal/extension-roster.d.ts +23 -0
- package/dist/internal/extension-roster.js +228 -0
- package/dist/internal/extension-runtime.d.ts +63 -0
- package/dist/internal/extension-runtime.js +1004 -0
- package/dist/internal/failure.d.ts +2 -0
- package/dist/internal/failure.js +9 -0
- package/dist/internal/host-meta.d.ts +41 -0
- package/dist/internal/host-meta.js +39 -0
- package/dist/internal/json-value.d.ts +4 -0
- package/dist/internal/json-value.js +3 -0
- package/dist/internal/model-acquisition.d.ts +21 -0
- package/dist/internal/model-acquisition.js +98 -0
- package/dist/internal/model-preference.d.ts +21 -0
- package/dist/internal/model-preference.js +20 -0
- package/dist/internal/observation-kernel.d.ts +28 -0
- package/dist/internal/observation-kernel.js +169 -0
- package/dist/internal/promise-facade.d.ts +18 -0
- package/dist/internal/promise-facade.js +172 -0
- package/dist/internal/run-scope.d.ts +27 -0
- package/dist/internal/run-scope.js +214 -0
- package/dist/internal/runtime-coordinator.d.ts +34 -0
- package/dist/internal/runtime-coordinator.js +233 -0
- package/dist/internal/runtime-core.d.ts +19 -0
- package/dist/internal/runtime-core.js +39 -0
- package/dist/internal/runtime-reconciliation.d.ts +18 -0
- package/dist/internal/runtime-reconciliation.js +162 -0
- package/dist/internal/session-context.d.ts +11 -0
- package/dist/internal/session-context.js +67 -0
- package/dist/internal/session-status.d.ts +10 -0
- package/dist/internal/session-status.js +52 -0
- package/dist/internal/woodstock/agent-reply.d.ts +25 -0
- package/dist/internal/woodstock/agent-reply.js +67 -0
- package/dist/internal/woodstock/client-projection.d.ts +29 -0
- package/dist/internal/woodstock/client-projection.js +512 -0
- package/dist/internal/woodstock/compaction-activity.d.ts +17 -0
- package/dist/internal/woodstock/compaction-activity.js +32 -0
- package/dist/internal/woodstock/cursor.d.ts +9 -0
- package/dist/internal/woodstock/cursor.js +44 -0
- package/dist/internal/woodstock/extension-store.d.ts +72 -0
- package/dist/internal/woodstock/extension-store.js +262 -0
- package/dist/internal/woodstock/fleet-store.d.ts +36 -0
- package/dist/internal/woodstock/fleet-store.js +100 -0
- package/dist/internal/woodstock/identities.d.ts +6 -0
- package/dist/internal/woodstock/identities.js +11 -0
- package/dist/internal/woodstock/index.d.ts +170 -0
- package/dist/internal/woodstock/index.js +546 -0
- package/dist/internal/woodstock/progress.d.ts +32 -0
- package/dist/internal/woodstock/progress.js +89 -0
- package/dist/internal/woodstock/run-recovery.d.ts +8 -0
- package/dist/internal/woodstock/run-recovery.js +95 -0
- package/dist/internal/woodstock/session-attention.d.ts +16 -0
- package/dist/internal/woodstock/session-attention.js +88 -0
- package/dist/internal/woodstock/session-documents.d.ts +18 -0
- package/dist/internal/woodstock/session-documents.js +51 -0
- package/dist/internal/woodstock/session-entry.d.ts +478 -0
- package/dist/internal/woodstock/session-entry.js +484 -0
- package/dist/internal/woodstock/session-grants.d.ts +24 -0
- package/dist/internal/woodstock/session-grants.js +84 -0
- package/dist/internal/woodstock/session-inbox.d.ts +56 -0
- package/dist/internal/woodstock/session-inbox.js +307 -0
- package/dist/internal/woodstock/session-store.d.ts +432 -0
- package/dist/internal/woodstock/session-store.js +2006 -0
- package/dist/internal/woodstock/storage-admission.d.ts +14 -0
- package/dist/internal/woodstock/storage-admission.js +44 -0
- package/dist/model-preference.d.ts +20 -0
- package/dist/model-preference.js +30 -0
- package/dist/node.d.ts +64 -0
- package/dist/node.js +256 -0
- package/dist/remote-client.d.ts +11 -0
- package/dist/remote-client.js +298 -0
- package/dist/session-attention.d.ts +35 -0
- package/dist/session-attention.js +22 -0
- package/dist/session-documents.d.ts +28 -0
- package/dist/session-documents.js +1 -0
- package/dist/testing.d.ts +54 -0
- package/dist/testing.js +215 -0
- package/docs/api/README.md +26 -0
- package/docs/api/agar-extension.md +40 -0
- package/docs/api/agent-control.md +151 -0
- package/docs/api/client-entry.md +344 -0
- package/docs/api/client.md +1112 -0
- package/docs/api/cloudflare.md +500 -0
- package/docs/api/effect.md +884 -0
- package/docs/api/extensions.md +2003 -0
- package/docs/api/fleet.md +734 -0
- package/docs/api/hosted.md +382 -0
- package/docs/api/http.md +111 -0
- package/docs/api/index.md +1116 -0
- package/docs/api/model-preference.md +151 -0
- package/docs/api/node.md +142 -0
- package/docs/api/testing.md +250 -0
- package/package.json +130 -3
|
@@ -0,0 +1,484 @@
|
|
|
1
|
+
import { CompactionInstructionsSchema } from "../client-boundary.js";
|
|
2
|
+
import { HostMetaSchema } from "../host-meta.js";
|
|
3
|
+
import { userContextMessage, VerifiedAgentReplySchema } from "./agent-reply.js";
|
|
4
|
+
import { SandboxFailureEventSchema } from "@fungi.computer/mycelium";
|
|
5
|
+
import * as Schema from "effect/Schema";
|
|
6
|
+
import * as Effect from "effect/Effect";
|
|
7
|
+
import * as Result from "effect/Result";
|
|
8
|
+
import { ModelPreferenceSchema } from "../model-preference.js";
|
|
9
|
+
const closed = { onExcessProperty: "error" };
|
|
10
|
+
const encoder = new TextEncoder();
|
|
11
|
+
const boundedText = (maximumBytes) => Schema.String.pipe(Schema.check(Schema.isMinLength(1)), Schema.check(Schema.makeFilter((value) => encoder.encode(value).byteLength <= maximumBytes)));
|
|
12
|
+
const boundedId = boundedText(256);
|
|
13
|
+
const digest = Schema.String.pipe(Schema.check(Schema.isPattern(/^[0-9a-f]{64}$/u)));
|
|
14
|
+
const jsonValue = Schema.suspend(() => Schema.Union([
|
|
15
|
+
Schema.String,
|
|
16
|
+
Schema.Number,
|
|
17
|
+
Schema.Boolean,
|
|
18
|
+
Schema.Null,
|
|
19
|
+
Schema.Array(jsonValue),
|
|
20
|
+
Schema.Record(Schema.String, jsonValue),
|
|
21
|
+
]));
|
|
22
|
+
const textContent = Schema.Struct({
|
|
23
|
+
type: Schema.Literal("text"),
|
|
24
|
+
text: Schema.String,
|
|
25
|
+
textSignature: Schema.optionalKey(Schema.String),
|
|
26
|
+
});
|
|
27
|
+
const thinkingContent = Schema.Struct({
|
|
28
|
+
type: Schema.Literal("thinking"),
|
|
29
|
+
thinking: Schema.String,
|
|
30
|
+
thinkingSignature: Schema.optionalKey(Schema.String),
|
|
31
|
+
redacted: Schema.optionalKey(Schema.Boolean),
|
|
32
|
+
});
|
|
33
|
+
const imageContent = Schema.Struct({
|
|
34
|
+
type: Schema.Literal("image"),
|
|
35
|
+
data: Schema.String,
|
|
36
|
+
mimeType: Schema.String,
|
|
37
|
+
});
|
|
38
|
+
const StoredToolCallSchema = Schema.Struct({
|
|
39
|
+
type: Schema.Literal("toolCall"),
|
|
40
|
+
id: Schema.String,
|
|
41
|
+
name: Schema.String,
|
|
42
|
+
arguments: Schema.Record(Schema.String, jsonValue),
|
|
43
|
+
thoughtSignature: Schema.optionalKey(Schema.String),
|
|
44
|
+
namespace: Schema.optionalKey(Schema.String),
|
|
45
|
+
});
|
|
46
|
+
/** Provider-native usage grammar shared by stored messages and settlement facts. */
|
|
47
|
+
export const usage = Schema.Struct({
|
|
48
|
+
input: Schema.Number,
|
|
49
|
+
output: Schema.Number,
|
|
50
|
+
cacheRead: Schema.Number,
|
|
51
|
+
cacheWrite: Schema.Number,
|
|
52
|
+
cacheWrite1h: Schema.optionalKey(Schema.Number),
|
|
53
|
+
reasoning: Schema.optionalKey(Schema.Number),
|
|
54
|
+
totalTokens: Schema.Number,
|
|
55
|
+
cost: Schema.Struct({
|
|
56
|
+
input: Schema.Number,
|
|
57
|
+
output: Schema.Number,
|
|
58
|
+
cacheRead: Schema.Number,
|
|
59
|
+
cacheWrite: Schema.Number,
|
|
60
|
+
total: Schema.Number,
|
|
61
|
+
}),
|
|
62
|
+
});
|
|
63
|
+
const userMessage = Schema.Struct({
|
|
64
|
+
role: Schema.Literal("user"),
|
|
65
|
+
content: Schema.Union([
|
|
66
|
+
Schema.String,
|
|
67
|
+
Schema.mutable(Schema.Array(Schema.Union([textContent, imageContent]))),
|
|
68
|
+
]),
|
|
69
|
+
timestamp: Schema.Number,
|
|
70
|
+
});
|
|
71
|
+
const promptMessage = Schema.Struct({
|
|
72
|
+
role: Schema.Literal("user"),
|
|
73
|
+
content: Schema.String,
|
|
74
|
+
timestamp: Schema.Number,
|
|
75
|
+
});
|
|
76
|
+
const storedToolParameters = Schema.Record(Schema.String, jsonValue);
|
|
77
|
+
const storedToolSampling = Schema.Union([
|
|
78
|
+
Schema.Literal(false),
|
|
79
|
+
Schema.Struct({
|
|
80
|
+
type: Schema.Literal("json_schema"),
|
|
81
|
+
strict: Schema.Literals(["prefer", "require"]),
|
|
82
|
+
}),
|
|
83
|
+
Schema.Struct({
|
|
84
|
+
type: Schema.Literal("grammar"),
|
|
85
|
+
variants: Schema.Struct({
|
|
86
|
+
openai_lark: Schema.optionalKey(Schema.String),
|
|
87
|
+
openai_regex: Schema.optionalKey(Schema.String),
|
|
88
|
+
}),
|
|
89
|
+
}),
|
|
90
|
+
]);
|
|
91
|
+
const storedPiTool = Schema.Struct({
|
|
92
|
+
name: Schema.String,
|
|
93
|
+
description: Schema.String,
|
|
94
|
+
parameters: storedToolParameters,
|
|
95
|
+
constrainedSampling: Schema.optionalKey(storedToolSampling),
|
|
96
|
+
});
|
|
97
|
+
const systemMessage = Schema.Struct({
|
|
98
|
+
role: Schema.Literal("system"),
|
|
99
|
+
content: Schema.Union([
|
|
100
|
+
Schema.String,
|
|
101
|
+
Schema.mutable(Schema.Array(textContent)),
|
|
102
|
+
]),
|
|
103
|
+
sections: Schema.optionalKey(Schema.Record(Schema.String, Schema.Union([Schema.String, Schema.Null]))),
|
|
104
|
+
toolsAdded: Schema.optionalKey(Schema.mutable(Schema.Array(storedPiTool))),
|
|
105
|
+
toolsRemoved: Schema.optionalKey(Schema.mutable(Schema.Array(Schema.Struct({ name: Schema.String })))),
|
|
106
|
+
timestamp: Schema.Number,
|
|
107
|
+
});
|
|
108
|
+
const assistantMessage = Schema.Struct({
|
|
109
|
+
role: Schema.Literal("assistant"),
|
|
110
|
+
content: Schema.mutable(Schema.Array(Schema.Union([textContent, thinkingContent, StoredToolCallSchema]))),
|
|
111
|
+
api: Schema.String,
|
|
112
|
+
provider: Schema.String,
|
|
113
|
+
model: Schema.String,
|
|
114
|
+
responseModel: Schema.optionalKey(Schema.String),
|
|
115
|
+
responseId: Schema.optionalKey(Schema.String),
|
|
116
|
+
diagnostics: Schema.optionalKey(Schema.mutable(Schema.Array(Schema.Struct({
|
|
117
|
+
type: Schema.String,
|
|
118
|
+
timestamp: Schema.Number,
|
|
119
|
+
error: Schema.optionalKey(Schema.Struct({
|
|
120
|
+
name: Schema.optionalKey(Schema.String),
|
|
121
|
+
message: Schema.String,
|
|
122
|
+
stack: Schema.optionalKey(Schema.String),
|
|
123
|
+
code: Schema.optionalKey(Schema.Union([Schema.String, Schema.Number])),
|
|
124
|
+
})),
|
|
125
|
+
details: Schema.optionalKey(Schema.Record(Schema.String, jsonValue)),
|
|
126
|
+
})))),
|
|
127
|
+
usage,
|
|
128
|
+
stopReason: Schema.Literals([
|
|
129
|
+
"pending",
|
|
130
|
+
"stop",
|
|
131
|
+
"length",
|
|
132
|
+
"toolUse",
|
|
133
|
+
"error",
|
|
134
|
+
"aborted",
|
|
135
|
+
"deferred",
|
|
136
|
+
]),
|
|
137
|
+
deferred: Schema.optionalKey(Schema.Struct({
|
|
138
|
+
provider: Schema.String,
|
|
139
|
+
modelId: Schema.String,
|
|
140
|
+
api: Schema.String,
|
|
141
|
+
id: Schema.String,
|
|
142
|
+
expiresAt: Schema.optionalKey(Schema.Number),
|
|
143
|
+
pollAfterMs: Schema.optionalKey(Schema.Number),
|
|
144
|
+
data: Schema.optionalKey(jsonValue),
|
|
145
|
+
})),
|
|
146
|
+
errorMessage: Schema.optionalKey(Schema.String),
|
|
147
|
+
rawStopReason: Schema.optionalKey(Schema.String),
|
|
148
|
+
providerThinkingLevel: Schema.optionalKey(Schema.String),
|
|
149
|
+
endTurn: Schema.optionalKey(Schema.Boolean),
|
|
150
|
+
timestamp: Schema.Number,
|
|
151
|
+
});
|
|
152
|
+
const toolResultMessage = Schema.Struct({
|
|
153
|
+
role: Schema.Literal("toolResult"),
|
|
154
|
+
toolCallId: Schema.String,
|
|
155
|
+
toolName: Schema.String,
|
|
156
|
+
content: Schema.mutable(Schema.Array(Schema.Union([textContent, imageContent]))),
|
|
157
|
+
details: Schema.optionalKey(jsonValue),
|
|
158
|
+
usage: Schema.optionalKey(usage),
|
|
159
|
+
isError: Schema.Boolean,
|
|
160
|
+
timestamp: Schema.Number,
|
|
161
|
+
});
|
|
162
|
+
/** Exact Pi message grammar stored by Woodstock without normalization. */
|
|
163
|
+
export const StoredPiMessageSchema = Schema.Union([
|
|
164
|
+
systemMessage,
|
|
165
|
+
userMessage,
|
|
166
|
+
assistantMessage,
|
|
167
|
+
toolResultMessage,
|
|
168
|
+
]);
|
|
169
|
+
const causalKind = Schema.Literals([
|
|
170
|
+
"run",
|
|
171
|
+
"turn",
|
|
172
|
+
"message",
|
|
173
|
+
"tool_call",
|
|
174
|
+
"tool_result",
|
|
175
|
+
"terminal",
|
|
176
|
+
]);
|
|
177
|
+
const CausalIdentitySchema = Schema.suspend(() => Schema.Struct({
|
|
178
|
+
kind: causalKind,
|
|
179
|
+
value: boundedId,
|
|
180
|
+
parent: Schema.optional(CausalIdentitySchema),
|
|
181
|
+
}));
|
|
182
|
+
const LiveRetryEventSchema = Schema.Union([
|
|
183
|
+
Schema.Struct({
|
|
184
|
+
type: Schema.Literal("auto_retry_start"),
|
|
185
|
+
run: CausalIdentitySchema,
|
|
186
|
+
attempt: Schema.Number,
|
|
187
|
+
maxAttempts: Schema.Number,
|
|
188
|
+
delayMs: Schema.Number,
|
|
189
|
+
errorMessage: Schema.String,
|
|
190
|
+
}),
|
|
191
|
+
Schema.Struct({
|
|
192
|
+
type: Schema.Literal("auto_retry_attempt"),
|
|
193
|
+
run: CausalIdentitySchema,
|
|
194
|
+
attempt: Schema.Number,
|
|
195
|
+
}),
|
|
196
|
+
Schema.Struct({
|
|
197
|
+
type: Schema.Literal("auto_retry_end"),
|
|
198
|
+
run: CausalIdentitySchema,
|
|
199
|
+
attempt: Schema.Number,
|
|
200
|
+
success: Schema.Boolean,
|
|
201
|
+
finalError: Schema.optionalKey(Schema.String),
|
|
202
|
+
}),
|
|
203
|
+
]);
|
|
204
|
+
const fingerprint = Schema.String.pipe(Schema.check(Schema.isPattern(/^sha256:[0-9a-f]{64}$/u)));
|
|
205
|
+
/**
|
|
206
|
+
* A roster fingerprint snapshot. Admission records what was offered then;
|
|
207
|
+
* execution facts record what the reopened owner actually ran.
|
|
208
|
+
*/
|
|
209
|
+
const runContract = Schema.Struct({
|
|
210
|
+
core: digest,
|
|
211
|
+
extensions: Schema.Array(Schema.Tuple([boundedId, fingerprint])).pipe(Schema.check(Schema.isMaxLength(128))),
|
|
212
|
+
});
|
|
213
|
+
const StoredToolResultSchema = Schema.Struct({
|
|
214
|
+
content: Schema.mutable(Schema.Array(Schema.Union([textContent, imageContent]))),
|
|
215
|
+
details: Schema.optional(jsonValue),
|
|
216
|
+
usage: Schema.optional(usage),
|
|
217
|
+
isError: Schema.Boolean,
|
|
218
|
+
terminate: Schema.optional(Schema.Boolean),
|
|
219
|
+
});
|
|
220
|
+
const common = { workId: boundedId };
|
|
221
|
+
/** What started one compaction: the user, the context threshold, or an overflow. */
|
|
222
|
+
const CompactionTriggerSchema = Schema.Literals([
|
|
223
|
+
"manual",
|
|
224
|
+
"threshold",
|
|
225
|
+
"overflow",
|
|
226
|
+
]);
|
|
227
|
+
/** Closed grammar stored in one retained Session entry JSON column. */
|
|
228
|
+
const StoredSessionEntrySchema = Schema.Union([
|
|
229
|
+
Schema.Struct({
|
|
230
|
+
...common,
|
|
231
|
+
kind: Schema.Literal("sandbox_failure"),
|
|
232
|
+
event: SandboxFailureEventSchema,
|
|
233
|
+
}),
|
|
234
|
+
Schema.Struct({
|
|
235
|
+
kind: Schema.Literal("document"),
|
|
236
|
+
workId: Schema.Null,
|
|
237
|
+
extensionId: boundedId,
|
|
238
|
+
name: boundedId,
|
|
239
|
+
valueJson: Schema.String,
|
|
240
|
+
}),
|
|
241
|
+
Schema.Struct({
|
|
242
|
+
kind: Schema.Literal("model_preference"),
|
|
243
|
+
workId: Schema.Null,
|
|
244
|
+
preference: Schema.NullOr(ModelPreferenceSchema),
|
|
245
|
+
}),
|
|
246
|
+
Schema.Struct({
|
|
247
|
+
...common,
|
|
248
|
+
kind: Schema.Literal("command"),
|
|
249
|
+
meta: Schema.optionalKey(HostMetaSchema),
|
|
250
|
+
/** Present only when the host admitted this line as a verified Agent reply. */
|
|
251
|
+
reply: Schema.optionalKey(VerifiedAgentReplySchema),
|
|
252
|
+
delivery: Schema.optionalKey(Schema.Literals(["steer", "followUp"])),
|
|
253
|
+
requestId: boundedId,
|
|
254
|
+
targetWorkId: Schema.optionalKey(boundedId),
|
|
255
|
+
receiptId: boundedId,
|
|
256
|
+
message: userMessage,
|
|
257
|
+
contract: runContract,
|
|
258
|
+
}),
|
|
259
|
+
// A manual compaction request: accepted Session work with no message. It
|
|
260
|
+
// never enters model context, a title or the client message projection.
|
|
261
|
+
Schema.Struct({
|
|
262
|
+
...common,
|
|
263
|
+
kind: Schema.Literal("command"),
|
|
264
|
+
work: Schema.Literal("compact"),
|
|
265
|
+
/** The user's focus for the summary, as Pi's `/compact <instructions>`. */
|
|
266
|
+
instructions: Schema.optionalKey(CompactionInstructionsSchema),
|
|
267
|
+
meta: Schema.optionalKey(HostMetaSchema),
|
|
268
|
+
requestId: boundedId,
|
|
269
|
+
receiptId: boundedId,
|
|
270
|
+
timestamp: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),
|
|
271
|
+
contract: runContract,
|
|
272
|
+
}),
|
|
273
|
+
Schema.Struct({
|
|
274
|
+
kind: Schema.Literal("operator"),
|
|
275
|
+
workId: Schema.Null,
|
|
276
|
+
requestId: boundedId,
|
|
277
|
+
author: Schema.Literals(["operator", "party"]),
|
|
278
|
+
meta: Schema.optionalKey(HostMetaSchema),
|
|
279
|
+
message: promptMessage,
|
|
280
|
+
}),
|
|
281
|
+
Schema.Struct({
|
|
282
|
+
...common,
|
|
283
|
+
kind: Schema.Literal("cancellation"),
|
|
284
|
+
requestId: boundedId,
|
|
285
|
+
receiptId: boundedId,
|
|
286
|
+
targetWorkId: boundedId,
|
|
287
|
+
meta: Schema.optionalKey(HostMetaSchema),
|
|
288
|
+
}),
|
|
289
|
+
Schema.Struct({
|
|
290
|
+
...common,
|
|
291
|
+
kind: Schema.Literal("model_selection"),
|
|
292
|
+
provider: boundedId,
|
|
293
|
+
model: boundedId,
|
|
294
|
+
catalogRevision: boundedId,
|
|
295
|
+
definitionRevision: boundedId,
|
|
296
|
+
selectionPolicyRevision: boundedId,
|
|
297
|
+
}),
|
|
298
|
+
Schema.Struct({
|
|
299
|
+
...common,
|
|
300
|
+
kind: Schema.Literal("run_started"),
|
|
301
|
+
run: CausalIdentitySchema,
|
|
302
|
+
contract: runContract,
|
|
303
|
+
}),
|
|
304
|
+
Schema.Struct({
|
|
305
|
+
...common,
|
|
306
|
+
kind: Schema.Literal("turn_started"),
|
|
307
|
+
run: CausalIdentitySchema,
|
|
308
|
+
turn: CausalIdentitySchema,
|
|
309
|
+
}),
|
|
310
|
+
Schema.Struct({
|
|
311
|
+
...common,
|
|
312
|
+
kind: Schema.Literal("model_prompt"),
|
|
313
|
+
run: CausalIdentitySchema,
|
|
314
|
+
turn: CausalIdentitySchema,
|
|
315
|
+
attempt: Schema.Number.pipe(Schema.check(Schema.isInt()), Schema.check(Schema.isGreaterThan(0))),
|
|
316
|
+
contract: runContract,
|
|
317
|
+
systemPrompt: Schema.String.pipe(Schema.check(Schema.makeFilter((value) => encoder.encode(value).byteLength <= 1024 * 1024))),
|
|
318
|
+
}),
|
|
319
|
+
Schema.Struct({
|
|
320
|
+
...common,
|
|
321
|
+
kind: Schema.Literal("message_start"),
|
|
322
|
+
run: CausalIdentitySchema,
|
|
323
|
+
turn: CausalIdentitySchema,
|
|
324
|
+
message: CausalIdentitySchema,
|
|
325
|
+
role: Schema.Literals(["assistant", "system", "toolResult", "user"]),
|
|
326
|
+
}),
|
|
327
|
+
Schema.Struct({
|
|
328
|
+
...common,
|
|
329
|
+
kind: Schema.Literal("message"),
|
|
330
|
+
run: CausalIdentitySchema,
|
|
331
|
+
turn: CausalIdentitySchema,
|
|
332
|
+
message: CausalIdentitySchema,
|
|
333
|
+
value: StoredPiMessageSchema,
|
|
334
|
+
}),
|
|
335
|
+
Schema.Struct({
|
|
336
|
+
...common,
|
|
337
|
+
kind: Schema.Literal("tool_intent"),
|
|
338
|
+
replay: Schema.Literals(["safe", "unsafe"]).pipe(Schema.withDecodingDefaultType(Effect.succeed("unsafe"))),
|
|
339
|
+
contract: runContract,
|
|
340
|
+
run: CausalIdentitySchema,
|
|
341
|
+
turn: CausalIdentitySchema,
|
|
342
|
+
toolCall: CausalIdentitySchema,
|
|
343
|
+
call: StoredToolCallSchema,
|
|
344
|
+
}),
|
|
345
|
+
Schema.Struct({
|
|
346
|
+
...common,
|
|
347
|
+
kind: Schema.Literal("tool_outcome"),
|
|
348
|
+
run: CausalIdentitySchema,
|
|
349
|
+
turn: CausalIdentitySchema,
|
|
350
|
+
toolCall: CausalIdentitySchema,
|
|
351
|
+
call: StoredToolCallSchema,
|
|
352
|
+
result: StoredToolResultSchema,
|
|
353
|
+
}),
|
|
354
|
+
Schema.Struct({
|
|
355
|
+
...common,
|
|
356
|
+
kind: Schema.Literal("live_retry"),
|
|
357
|
+
event: LiveRetryEventSchema,
|
|
358
|
+
}),
|
|
359
|
+
Schema.Struct({
|
|
360
|
+
...common,
|
|
361
|
+
kind: Schema.Literal("compaction"),
|
|
362
|
+
resumesRun: Schema.optionalKey(Schema.Boolean),
|
|
363
|
+
// Optional only because Sessions compacted before these facts existed
|
|
364
|
+
// are still live; every new compaction records both.
|
|
365
|
+
trigger: Schema.optionalKey(CompactionTriggerSchema),
|
|
366
|
+
/** Estimated context tokens right after this compaction. */
|
|
367
|
+
tokensAfter: Schema.optionalKey(Schema.Number),
|
|
368
|
+
firstKeptEntryId: boundedId,
|
|
369
|
+
summary: Schema.String,
|
|
370
|
+
tokensBefore: Schema.Number,
|
|
371
|
+
usage,
|
|
372
|
+
contextRevision: boundedId,
|
|
373
|
+
details: Schema.optionalKey(Schema.Struct({
|
|
374
|
+
readFiles: Schema.Array(Schema.String),
|
|
375
|
+
modifiedFiles: Schema.Array(Schema.String),
|
|
376
|
+
})),
|
|
377
|
+
}),
|
|
378
|
+
// A compaction that committed nothing: a manual request with nothing to
|
|
379
|
+
// summarize, or any compaction that failed. Clients show it as a result.
|
|
380
|
+
Schema.Struct({
|
|
381
|
+
...common,
|
|
382
|
+
kind: Schema.Literal("compaction_notice"),
|
|
383
|
+
trigger: CompactionTriggerSchema,
|
|
384
|
+
result: Schema.Literals(["nothing_to_compact", "failed"]),
|
|
385
|
+
diagnostic: Schema.optionalKey(Schema.String.check(Schema.isMaxLength(200))),
|
|
386
|
+
}),
|
|
387
|
+
Schema.Struct({
|
|
388
|
+
...common,
|
|
389
|
+
kind: Schema.Literal("run_terminal"),
|
|
390
|
+
run: CausalIdentitySchema,
|
|
391
|
+
terminal: CausalIdentitySchema,
|
|
392
|
+
outcome: Schema.Literals(["completed", "cancelled", "failed"]),
|
|
393
|
+
}),
|
|
394
|
+
Schema.Struct({
|
|
395
|
+
...common,
|
|
396
|
+
kind: Schema.Literal("work_terminal"),
|
|
397
|
+
diagnostic: Schema.optionalKey(Schema.String),
|
|
398
|
+
outcome: Schema.Literals([
|
|
399
|
+
"completed",
|
|
400
|
+
"interrupted",
|
|
401
|
+
"cancelled",
|
|
402
|
+
"failed",
|
|
403
|
+
]),
|
|
404
|
+
}),
|
|
405
|
+
]);
|
|
406
|
+
const StoredSessionEntryTextSchema = Schema.fromJsonString(StoredSessionEntrySchema);
|
|
407
|
+
const JsonTextSchema = Schema.fromJsonString(Schema.Unknown);
|
|
408
|
+
const decodeEntryJson = Schema.decodeUnknownResult(StoredSessionEntryTextSchema, closed);
|
|
409
|
+
const encodeJson = Schema.encodeSync(JsonTextSchema);
|
|
410
|
+
const validateEntryJson = Schema.decodeUnknownSync(StoredSessionEntryTextSchema, closed);
|
|
411
|
+
/** Whether accepted work is a manual compaction request. */
|
|
412
|
+
export function isCompactCommand(entry) {
|
|
413
|
+
return "work" in entry;
|
|
414
|
+
}
|
|
415
|
+
/** The prompt a command carries; a compaction request carries none. */
|
|
416
|
+
export function promptCommand(entry) {
|
|
417
|
+
return entry.kind === "command" && !isCompactCommand(entry)
|
|
418
|
+
? entry
|
|
419
|
+
: undefined;
|
|
420
|
+
}
|
|
421
|
+
/** When the command was accepted, as its own data records it. */
|
|
422
|
+
export function commandTimestamp(entry) {
|
|
423
|
+
return isCompactCommand(entry) ? entry.timestamp : entry.message.timestamp;
|
|
424
|
+
}
|
|
425
|
+
/**
|
|
426
|
+
* What a later model run sees of an operator line: always a user-role note,
|
|
427
|
+
* so a human's words are never presented as the model's own output.
|
|
428
|
+
*/
|
|
429
|
+
export function operatorContextMessage(entry) {
|
|
430
|
+
return userContextMessage(entry.author === "party"
|
|
431
|
+
? entry.message
|
|
432
|
+
: {
|
|
433
|
+
role: "user",
|
|
434
|
+
content: `[A human operator replied to the user on your behalf]\n${entry.message.content}`,
|
|
435
|
+
timestamp: entry.message.timestamp,
|
|
436
|
+
});
|
|
437
|
+
}
|
|
438
|
+
/**
|
|
439
|
+
* What a model run sees of an accepted command: its stored user line, wrapped
|
|
440
|
+
* as a verified Agent reply only when the host admitted it as one.
|
|
441
|
+
*/
|
|
442
|
+
export function commandContextMessage(entry) {
|
|
443
|
+
return userContextMessage(entry.message, entry.reply);
|
|
444
|
+
}
|
|
445
|
+
/**
|
|
446
|
+
* What a client sees of an operator line: the party's words as a user
|
|
447
|
+
* message, the operator's as an assistant message from provider `operator`.
|
|
448
|
+
*/
|
|
449
|
+
export function operatorClientMessage(entry) {
|
|
450
|
+
if (entry.author === "party")
|
|
451
|
+
return entry.message;
|
|
452
|
+
const zero = { input: 0, output: 0, cacheRead: 0, cacheWrite: 0, total: 0 };
|
|
453
|
+
return {
|
|
454
|
+
role: "assistant",
|
|
455
|
+
content: [{ type: "text", text: entry.message.content }],
|
|
456
|
+
api: "operator",
|
|
457
|
+
provider: "operator",
|
|
458
|
+
model: "operator",
|
|
459
|
+
usage: {
|
|
460
|
+
input: 0,
|
|
461
|
+
output: 0,
|
|
462
|
+
cacheRead: 0,
|
|
463
|
+
cacheWrite: 0,
|
|
464
|
+
totalTokens: 0,
|
|
465
|
+
cost: zero,
|
|
466
|
+
},
|
|
467
|
+
stopReason: "stop",
|
|
468
|
+
timestamp: entry.message.timestamp,
|
|
469
|
+
};
|
|
470
|
+
}
|
|
471
|
+
/** Decode the one JSON representation admitted by retained Session storage. */
|
|
472
|
+
export function decodeStoredSessionEntry(value) {
|
|
473
|
+
return Result.map(decodeEntryJson(value), (entry) => entry.kind === "command" &&
|
|
474
|
+
!isCompactCommand(entry) &&
|
|
475
|
+
entry.delivery === undefined
|
|
476
|
+
? { ...entry, delivery: "followUp" }
|
|
477
|
+
: entry);
|
|
478
|
+
}
|
|
479
|
+
/** Serialize Pi's JSON representation, then validate the retained entry. */
|
|
480
|
+
export function encodeStoredSessionEntry(entry) {
|
|
481
|
+
const encoded = encodeJson(entry);
|
|
482
|
+
validateEntryJson(encoded);
|
|
483
|
+
return encoded;
|
|
484
|
+
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import type { Grants } from "@fungi.computer/mycelium";
|
|
2
|
+
import type { SqliteOwner } from "../contracts.js";
|
|
3
|
+
/** One versioned delivery of a Session's grants. */
|
|
4
|
+
export type GrantsDelivery = Readonly<{
|
|
5
|
+
version: number;
|
|
6
|
+
grants: Grants;
|
|
7
|
+
}>;
|
|
8
|
+
/** Whether a delivery replaced the stored grants or repeated them. */
|
|
9
|
+
export type GrantsDeliveryResult = "applied" | "unchanged";
|
|
10
|
+
/** Woodstock keeps each Session's newest delivered grants beside it. */
|
|
11
|
+
export declare function prepareSessionGrants(owner: SqliteOwner): void;
|
|
12
|
+
/**
|
|
13
|
+
* Store one versioned delivery of a Session's grants. A delivery may arrive
|
|
14
|
+
* before the Session's first prompt. An older version is stale and never
|
|
15
|
+
* writes. The same version with other grants replaces the stored grants: the
|
|
16
|
+
* host recomputed its decision (for example after a deploy) without a new
|
|
17
|
+
* version, and the newest computation always wins over the old grant. Only
|
|
18
|
+
* the in-process host delivers grants.
|
|
19
|
+
*/
|
|
20
|
+
export declare function deliverSessionGrants(owner: SqliteOwner, sessionId: string, delivery: GrantsDelivery): GrantsDeliveryResult;
|
|
21
|
+
/** One Session's newest delivery; null when the host delivered none. */
|
|
22
|
+
export declare function readSessionGrants(owner: SqliteOwner, sessionId: string): GrantsDelivery | null;
|
|
23
|
+
/** A fork keeps its source's delivery, so it never widens to the default. */
|
|
24
|
+
export declare function copySessionGrants(owner: SqliteOwner, fromSessionId: string, toSessionId: string): void;
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
import * as Result from "effect/Result";
|
|
2
|
+
import * as Schema from "effect/Schema";
|
|
3
|
+
import { ShiitakeError } from "../../errors.js";
|
|
4
|
+
/**
|
|
5
|
+
* One Session's tool grants as the host delivered them: module or extension
|
|
6
|
+
* ids mapped to a grant level. Bounded, so a host cannot grow the row.
|
|
7
|
+
*/
|
|
8
|
+
const SessionGrantsSchema = Schema.Record(Schema.String.check(Schema.isMinLength(1), Schema.isMaxLength(160)), Schema.Literals(["none", "read", "write"])).check(Schema.makeFilter((grants) => Object.keys(grants).length <= 256));
|
|
9
|
+
/**
|
|
10
|
+
* One versioned delivery of a host decision. The host owns the decision and
|
|
11
|
+
* its version; Shiitake keeps only the newest delivery it has seen.
|
|
12
|
+
*/
|
|
13
|
+
const GrantsDeliverySchema = Schema.Struct({
|
|
14
|
+
/** The host's own version of this decision; deliveries only move forward. */
|
|
15
|
+
version: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0), Schema.isLessThanOrEqualTo(Number.MAX_SAFE_INTEGER)),
|
|
16
|
+
grants: SessionGrantsSchema,
|
|
17
|
+
});
|
|
18
|
+
const decodeDelivery = Schema.decodeUnknownResult(GrantsDeliverySchema, {
|
|
19
|
+
onExcessProperty: "error",
|
|
20
|
+
});
|
|
21
|
+
const decodeStoredGrants = Schema.decodeUnknownResult(Schema.fromJsonString(SessionGrantsSchema));
|
|
22
|
+
const encodeGrants = Schema.encodeSync(Schema.fromJsonString(SessionGrantsSchema));
|
|
23
|
+
const decodeRow = Schema.decodeUnknownResult(Schema.Struct({ version: Schema.Int, grants_json: Schema.String }));
|
|
24
|
+
/** Woodstock keeps each Session's newest delivered grants beside it. */
|
|
25
|
+
export function prepareSessionGrants(owner) {
|
|
26
|
+
owner.sql.exec(`CREATE TABLE IF NOT EXISTS session_tool_grants (
|
|
27
|
+
session_id TEXT PRIMARY KEY,
|
|
28
|
+
version INTEGER NOT NULL,
|
|
29
|
+
grants_json TEXT NOT NULL
|
|
30
|
+
)`);
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Store one versioned delivery of a Session's grants. A delivery may arrive
|
|
34
|
+
* before the Session's first prompt. An older version is stale and never
|
|
35
|
+
* writes. The same version with other grants replaces the stored grants: the
|
|
36
|
+
* host recomputed its decision (for example after a deploy) without a new
|
|
37
|
+
* version, and the newest computation always wins over the old grant. Only
|
|
38
|
+
* the in-process host delivers grants.
|
|
39
|
+
*/
|
|
40
|
+
export function deliverSessionGrants(owner, sessionId, delivery) {
|
|
41
|
+
const decoded = decodeDelivery(delivery);
|
|
42
|
+
if (Result.isFailure(decoded))
|
|
43
|
+
throw new ShiitakeError("contract", "invalid", "Session grants delivery is invalid");
|
|
44
|
+
const grantsJson = encodeGrants(decoded.success.grants);
|
|
45
|
+
const stored = readStoredRow(owner, sessionId);
|
|
46
|
+
if (stored !== undefined) {
|
|
47
|
+
if (decoded.success.version < stored.version)
|
|
48
|
+
throw new ShiitakeError("contract", "conflict", "Session grants delivery is older than the stored delivery");
|
|
49
|
+
if (decoded.success.version === stored.version &&
|
|
50
|
+
stored.grantsJson === grantsJson)
|
|
51
|
+
return "unchanged";
|
|
52
|
+
}
|
|
53
|
+
owner.sql.exec(`INSERT INTO session_tool_grants (session_id, version, grants_json)
|
|
54
|
+
VALUES (?, ?, ?)
|
|
55
|
+
ON CONFLICT(session_id) DO UPDATE SET
|
|
56
|
+
version = excluded.version, grants_json = excluded.grants_json`, sessionId, decoded.success.version, grantsJson);
|
|
57
|
+
return "applied";
|
|
58
|
+
}
|
|
59
|
+
function readStoredRow(owner, sessionId) {
|
|
60
|
+
const [raw] = owner.sql
|
|
61
|
+
.exec("SELECT version, grants_json FROM session_tool_grants WHERE session_id = ?", sessionId)
|
|
62
|
+
.toArray();
|
|
63
|
+
if (raw === undefined)
|
|
64
|
+
return undefined;
|
|
65
|
+
const row = decodeRow(raw);
|
|
66
|
+
if (Result.isFailure(row))
|
|
67
|
+
throw new ShiitakeError("store", "unavailable", "Stored Session grants are invalid");
|
|
68
|
+
return { version: row.success.version, grantsJson: row.success.grants_json };
|
|
69
|
+
}
|
|
70
|
+
/** One Session's newest delivery; null when the host delivered none. */
|
|
71
|
+
export function readSessionGrants(owner, sessionId) {
|
|
72
|
+
const stored = readStoredRow(owner, sessionId);
|
|
73
|
+
if (stored === undefined)
|
|
74
|
+
return null;
|
|
75
|
+
const grants = decodeStoredGrants(stored.grantsJson);
|
|
76
|
+
if (Result.isFailure(grants))
|
|
77
|
+
throw new ShiitakeError("store", "unavailable", "Stored Session grants are invalid");
|
|
78
|
+
return { version: stored.version, grants: grants.success };
|
|
79
|
+
}
|
|
80
|
+
/** A fork keeps its source's delivery, so it never widens to the default. */
|
|
81
|
+
export function copySessionGrants(owner, fromSessionId, toSessionId) {
|
|
82
|
+
owner.sql.exec(`INSERT INTO session_tool_grants (session_id, version, grants_json)
|
|
83
|
+
SELECT ?, version, grants_json FROM session_tool_grants WHERE session_id = ?`, toSessionId, fromSessionId);
|
|
84
|
+
}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import type { WatchdogQueueTransition } from "@fungi.computer/watchdog/effect";
|
|
2
|
+
import type { SessionSummaryPage, SessionSummaryRow } from "../../client.js";
|
|
3
|
+
import type { SqliteOwner } from "../contracts.js";
|
|
4
|
+
/** Create the inbox table, its keyset and revision indexes and the revision clock. */
|
|
5
|
+
export declare function prepareSessionInbox(owner: SqliteOwner): void;
|
|
6
|
+
/** Conversation facts Woodstock supplies with each Session write. */
|
|
7
|
+
export type SessionInboxFacts = Readonly<{
|
|
8
|
+
sessionId: string;
|
|
9
|
+
/** Conversation activity; absent for display-only writes such as a title. */
|
|
10
|
+
activityAt?: number;
|
|
11
|
+
/**
|
|
12
|
+
* First prompt title; null when the stored lineage is unreadable, and
|
|
13
|
+
* undefined when this write cannot change it.
|
|
14
|
+
*/
|
|
15
|
+
title?: string | null;
|
|
16
|
+
}>;
|
|
17
|
+
/**
|
|
18
|
+
* Upsert title and recency in the caller's Session transaction. A new row
|
|
19
|
+
* starts `done`: nothing has run, and Watchdog's projector owns run state.
|
|
20
|
+
*/
|
|
21
|
+
export declare function touchSessionInbox(owner: SqliteOwner, facts: SessionInboxFacts): void;
|
|
22
|
+
/** Record a deletion in the Session owner's transaction and revision stream. */
|
|
23
|
+
export declare function recordSessionInboxDeletion(owner: SqliteOwner, sessionId: string): void;
|
|
24
|
+
/** Drop tombstones the current member subscribers have all acknowledged. */
|
|
25
|
+
export declare function pruneSessionInboxTombstones(owner: SqliteOwner, through: number): void;
|
|
26
|
+
/**
|
|
27
|
+
* Watchdog's same-transaction projector. Queues that are not saved Sessions
|
|
28
|
+
* have no row and are left alone.
|
|
29
|
+
*/
|
|
30
|
+
export declare function projectSessionRun(owner: SqliteOwner, transition: WatchdogQueueTransition, now: number): void;
|
|
31
|
+
/** Refresh attention using the current queue head in the extension transaction. */
|
|
32
|
+
export declare function projectSessionAttention(owner: SqliteOwner, sessionId: string, head: WatchdogQueueTransition["head"]): void;
|
|
33
|
+
/** Revisioned Session inbox changes after one owner revision, oldest first. */
|
|
34
|
+
export type SessionInboxChanges = Readonly<{
|
|
35
|
+
rows: readonly (SessionSummaryRow | Readonly<{
|
|
36
|
+
sessionId: string;
|
|
37
|
+
deleted: true;
|
|
38
|
+
}>)[];
|
|
39
|
+
/** Revision of the last returned row, or `after` when none changed. */
|
|
40
|
+
through: number;
|
|
41
|
+
/** Latest owner revision; `through < latest` means more remain. */
|
|
42
|
+
latest: number;
|
|
43
|
+
}>;
|
|
44
|
+
/**
|
|
45
|
+
* A bounded strict-after read of changed rows. Each Session appears once, at
|
|
46
|
+
* its latest revision, so pending delivery is bounded by Session count.
|
|
47
|
+
*/
|
|
48
|
+
export declare function readSessionInboxChanges(owner: SqliteOwner, after: number, limit: number): SessionInboxChanges;
|
|
49
|
+
/** Indexed lookup using the same row decoder and availability as the inbox listing. */
|
|
50
|
+
export declare function readSessionInboxSummary(owner: SqliteOwner, sessionId: string): SessionSummaryRow | undefined;
|
|
51
|
+
/**
|
|
52
|
+
* One bounded page in tier, then newest-activity order: a single indexed
|
|
53
|
+
* statement regardless of how many Sessions the Agent holds. A row whose
|
|
54
|
+
* stored facts are unreadable is its own `unavailable` row.
|
|
55
|
+
*/
|
|
56
|
+
export declare function readSessionInboxPage(owner: SqliteOwner, after: string | undefined): SessionSummaryPage;
|