@cursor/july 0.1.38 → 0.1.39
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/dist/bin/agent-serve.js +0 -0
- package/dist/channels/slack/post-update-delivery.d.ts +85 -0
- package/dist/channels/slack/post-update-delivery.d.ts.map +1 -0
- package/dist/docs/404.html +1 -1
- package/dist/docs/ab.html +2 -2
- package/dist/docs/assets/{app.B4nJHNwO.js → app.BQ8Hihdf.js} +1 -1
- package/dist/docs/assets/chunks/@localSearchIndexroot.B-VTH4As.js +1 -0
- package/dist/docs/assets/chunks/{VPLocalSearchBox.DHrr3pLB.js → VPLocalSearchBox.BBCr8Yuy.js} +1 -1
- package/dist/docs/assets/chunks/{theme.DQNgSMha.js → theme.CK_NiGC-.js} +2 -2
- package/dist/docs/building-with-agents.html +2 -2
- package/dist/docs/concepts.html +2 -2
- package/dist/docs/deployment.html +2 -2
- package/dist/docs/evals.html +2 -2
- package/dist/docs/example-agents/approval-buddy.html +2 -2
- package/dist/docs/example-agents/benny.html +2 -2
- package/dist/docs/example-agents/bugbot.html +2 -2
- package/dist/docs/example-agents/codebase-wiki.html +2 -2
- package/dist/docs/example-agents/codeowners-review.html +2 -2
- package/dist/docs/example-agents/concierge.html +2 -2
- package/dist/docs/example-agents/fsd.html +2 -2
- package/dist/docs/example-agents/index.html +2 -2
- package/dist/docs/example-agents/knowledge-base.html +2 -2
- package/dist/docs/example-agents/oncall.html +2 -2
- package/dist/docs/example-agents/security-reviewer.html +2 -2
- package/dist/docs/example-agents/slack-agent.html +2 -2
- package/dist/docs/example-agents/weather-agent.html +2 -2
- package/dist/docs/guides/agent-to-agent.html +2 -2
- package/dist/docs/guides/cloud-runtime.html +2 -2
- package/dist/docs/guides/github.html +2 -2
- package/dist/docs/guides/human-in-the-loop.html +2 -2
- package/dist/docs/guides/mcp-oauth.html +2 -2
- package/dist/docs/guides/slack.html +2 -2
- package/dist/docs/guides/webhooks.html +2 -2
- package/dist/docs/hillclimbing.html +2 -2
- package/dist/docs/index.html +2 -2
- package/dist/docs/quickstart.html +2 -2
- package/dist/docs/reference/agent-config.html +2 -2
- package/dist/docs/reference/artifacts.html +2 -2
- package/dist/docs/reference/channels.html +2 -2
- package/dist/docs/reference/cli.html +2 -2
- package/dist/docs/reference/connections.html +2 -2
- package/dist/docs/reference/hooks.html +2 -2
- package/dist/docs/reference/http-api.html +2 -2
- package/dist/docs/reference/instructions.html +2 -2
- package/dist/docs/reference/playground.html +2 -2
- package/dist/docs/reference/project-layout.html +2 -2
- package/dist/docs/reference/prompt.html +2 -2
- package/dist/docs/reference/schedules.html +2 -2
- package/dist/docs/reference/sessions.html +2 -2
- package/dist/docs/reference/skills.html +2 -2
- package/dist/docs/reference/subagents.html +2 -2
- package/dist/docs/reference/tools.html +2 -2
- package/dist/docs/scaffolding-agents.html +2 -2
- package/dist/docs/storage.html +2 -2
- package/dist/docs/troubleshooting.html +2 -2
- package/dist/internal/json-dir-store.d.ts +32 -0
- package/dist/internal/json-dir-store.d.ts.map +1 -0
- package/dist/internal/persistence-coordinator.d.ts +127 -0
- package/dist/internal/persistence-coordinator.d.ts.map +1 -0
- package/dist/multi-tenant.d.ts +80 -0
- package/dist/multi-tenant.d.ts.map +1 -0
- package/dist/multi-tenant.js +69 -0
- package/dist/persistence.d.ts +184 -0
- package/dist/persistence.d.ts.map +1 -0
- package/dist/playground/assets/index-BRhBbnd4.css +1 -0
- package/dist/playground/assets/{index-DLtPsWuV.js → index-_2WKw9a-.js} +44 -44
- package/dist/playground/index.html +2 -2
- package/package.json +1 -1
- package/dist/docs/assets/chunks/@localSearchIndexroot.B6oHmJzD.js +0 -1
- package/dist/playground/assets/index-Bs6TgymR.css +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"persistence-coordinator.d.ts","sourceRoot":"","sources":["../../src/internal/persistence-coordinator.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Multi-customer managed-agent bindings for agentkit.
|
|
3
|
+
*
|
|
4
|
+
* Control plane checks the Statsig gate {@link MULTI_TENANT_ENABLED_GATE}
|
|
5
|
+
* before attaching bindings to a wake. Engines never call Statsig; they
|
|
6
|
+
* only react when a {@link TenantWakeContext} / binding list is present.
|
|
7
|
+
* Gate off ⇒ callers pass `multiTenant: false` and keep legacy allowlists.
|
|
8
|
+
*/
|
|
9
|
+
/** Statsig gate id — must match `FLAGS.multi_tenant_enabled`. */
|
|
10
|
+
export declare const MULTI_TENANT_ENABLED_GATE: "multi_tenant_enabled";
|
|
11
|
+
/**
|
|
12
|
+
* Per-customer binding for a catalog (managed) agentkit agent.
|
|
13
|
+
* Prompts / tools / MCP are overlays on the fixed agent image.
|
|
14
|
+
*/
|
|
15
|
+
export interface ManagedAgentBinding {
|
|
16
|
+
bindingId: string;
|
|
17
|
+
/** Catalog agent id (e.g. `security-reviewer`). */
|
|
18
|
+
agentId: string;
|
|
19
|
+
teamId: number;
|
|
20
|
+
/** `owner/name` repos this customer enabled. */
|
|
21
|
+
repos: readonly string[];
|
|
22
|
+
prompts?: {
|
|
23
|
+
/** Appended to base system instructions; does not replace them. */
|
|
24
|
+
overlay?: string;
|
|
25
|
+
/** Injected as the wake / task brief. */
|
|
26
|
+
task?: string;
|
|
27
|
+
};
|
|
28
|
+
tools?: {
|
|
29
|
+
/** When set, only these tool names are admitted for the wake. */
|
|
30
|
+
enable?: readonly string[];
|
|
31
|
+
};
|
|
32
|
+
mcp?: readonly {
|
|
33
|
+
id: string;
|
|
34
|
+
url: string;
|
|
35
|
+
secretRef?: string;
|
|
36
|
+
}[];
|
|
37
|
+
policy?: {
|
|
38
|
+
model?: string;
|
|
39
|
+
effort?: string;
|
|
40
|
+
[key: string]: unknown;
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
/** Request-scoped tenant bag attached to a managed-agent wake. */
|
|
44
|
+
export interface TenantWakeContext {
|
|
45
|
+
binding: ManagedAgentBinding;
|
|
46
|
+
}
|
|
47
|
+
export declare function normalizeRepoFullName(repo: string): string;
|
|
48
|
+
export declare function bindingAllowsRepo(binding: ManagedAgentBinding, repoFullName: string): boolean;
|
|
49
|
+
export declare function findBindingForRepo(bindings: readonly ManagedAgentBinding[], agentId: string, repoFullName: string): ManagedAgentBinding | undefined;
|
|
50
|
+
export type RepositoryAdmission = {
|
|
51
|
+
admitted: true;
|
|
52
|
+
binding?: ManagedAgentBinding;
|
|
53
|
+
} | {
|
|
54
|
+
admitted: false;
|
|
55
|
+
};
|
|
56
|
+
/**
|
|
57
|
+
* Admit a repository for a managed agent.
|
|
58
|
+
* - `multiTenant: true` → matching binding required (fail closed).
|
|
59
|
+
* - `multiTenant: false` → legacy static allowlist only.
|
|
60
|
+
*/
|
|
61
|
+
export declare function admitRepository(args: {
|
|
62
|
+
multiTenant: boolean;
|
|
63
|
+
agentId: string;
|
|
64
|
+
repoFullName: string;
|
|
65
|
+
bindings: readonly ManagedAgentBinding[];
|
|
66
|
+
legacyAllowlist: readonly string[];
|
|
67
|
+
}): RepositoryAdmission;
|
|
68
|
+
/** Tools with no `enable` list stay admitted (compat with unconfigured bindings). */
|
|
69
|
+
export declare function isToolAdmitted(binding: ManagedAgentBinding | undefined, toolName: string): boolean;
|
|
70
|
+
/**
|
|
71
|
+
* Author-KV key scoped to a customer team under the existing `kv/` scheme:
|
|
72
|
+
* `agentkit/v1/{agent}/kv/t/{teamId}/{key}`.
|
|
73
|
+
*/
|
|
74
|
+
export declare function tenantKvKey(agent: string, teamId: number, key: string): string;
|
|
75
|
+
/**
|
|
76
|
+
* Prefix for listing author-KV keys for one customer team.
|
|
77
|
+
* Matches the URI-encoded form produced by {@link tenantKvKey}.
|
|
78
|
+
*/
|
|
79
|
+
export declare function tenantKvPrefix(agent: string, teamId: number): string;
|
|
80
|
+
//# sourceMappingURL=multi-tenant.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"multi-tenant.d.ts","sourceRoot":"","sources":["../src/multi-tenant.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAIH,iEAAiE;AACjE,eAAO,MAAM,yBAAyB,EAAG,sBAA+B,CAAC;AAEzE;;;GAGG;AACH,MAAM,WAAW,mBAAmB;IAClC,SAAS,EAAE,MAAM,CAAC;IAClB,mDAAmD;IACnD,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,MAAM,CAAC;IACf,gDAAgD;IAChD,KAAK,EAAE,SAAS,MAAM,EAAE,CAAC;IACzB,OAAO,CAAC,EAAE;QACR,mEAAmE;QACnE,OAAO,CAAC,EAAE,MAAM,CAAC;QACjB,yCAAyC;QACzC,IAAI,CAAC,EAAE,MAAM,CAAC;KACf,CAAC;IACF,KAAK,CAAC,EAAE;QACN,iEAAiE;QACjE,MAAM,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;KAC5B,CAAC;IACF,GAAG,CAAC,EAAE,SAAS;QACb,EAAE,EAAE,MAAM,CAAC;QACX,GAAG,EAAE,MAAM,CAAC;QACZ,SAAS,CAAC,EAAE,MAAM,CAAC;KACpB,EAAE,CAAC;IACJ,MAAM,CAAC,EAAE;QACP,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;KACxB,CAAC;CACH;AAED,kEAAkE;AAClE,MAAM,WAAW,iBAAiB;IAChC,OAAO,EAAE,mBAAmB,CAAC;CAC9B;AAED,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAE1D;AAED,wBAAgB,iBAAiB,CAC/B,OAAO,EAAE,mBAAmB,EAC5B,YAAY,EAAE,MAAM,GACnB,OAAO,CAGT;AAED,wBAAgB,kBAAkB,CAChC,QAAQ,EAAE,SAAS,mBAAmB,EAAE,EACxC,OAAO,EAAE,MAAM,EACf,YAAY,EAAE,MAAM,GACnB,mBAAmB,GAAG,SAAS,CAIjC;AAED,MAAM,MAAM,mBAAmB,GAC3B;IAAE,QAAQ,EAAE,IAAI,CAAC;IAAC,OAAO,CAAC,EAAE,mBAAmB,CAAA;CAAE,GACjD;IAAE,QAAQ,EAAE,KAAK,CAAA;CAAE,CAAC;AAExB;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE;IACpC,WAAW,EAAE,OAAO,CAAC;IACrB,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,SAAS,mBAAmB,EAAE,CAAC;IACzC,eAAe,EAAE,SAAS,MAAM,EAAE,CAAC;CACpC,GAAG,mBAAmB,CAiBtB;AAED,qFAAqF;AACrF,wBAAgB,cAAc,CAC5B,OAAO,EAAE,mBAAmB,GAAG,SAAS,EACxC,QAAQ,EAAE,MAAM,GACf,OAAO,CAMT;AAED;;;GAGG;AACH,wBAAgB,WAAW,CACzB,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,MAAM,EACd,GAAG,EAAE,MAAM,GACV,MAAM,CAKR;AAED;;;GAGG;AACH,wBAAgB,cAAc,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CAKpE"}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Multi-customer managed-agent bindings for agentkit.
|
|
3
|
+
*
|
|
4
|
+
* Control plane checks the Statsig gate {@link MULTI_TENANT_ENABLED_GATE}
|
|
5
|
+
* before attaching bindings to a wake. Engines never call Statsig; they
|
|
6
|
+
* only react when a {@link TenantWakeContext} / binding list is present.
|
|
7
|
+
* Gate off ⇒ callers pass `multiTenant: false` and keep legacy allowlists.
|
|
8
|
+
*/
|
|
9
|
+
import { STORAGE_KEY_ROOT, storageKeys } from "./storage.js";
|
|
10
|
+
/** Statsig gate id — must match `FLAGS.multi_tenant_enabled`. */
|
|
11
|
+
export const MULTI_TENANT_ENABLED_GATE = "multi_tenant_enabled";
|
|
12
|
+
export function normalizeRepoFullName(repo) {
|
|
13
|
+
return repo.trim().toLowerCase();
|
|
14
|
+
}
|
|
15
|
+
export function bindingAllowsRepo(binding, repoFullName) {
|
|
16
|
+
const needle = normalizeRepoFullName(repoFullName);
|
|
17
|
+
return binding.repos.some((r) => normalizeRepoFullName(r) === needle);
|
|
18
|
+
}
|
|
19
|
+
export function findBindingForRepo(bindings, agentId, repoFullName) {
|
|
20
|
+
return bindings.find((b) => b.agentId === agentId && bindingAllowsRepo(b, repoFullName));
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Admit a repository for a managed agent.
|
|
24
|
+
* - `multiTenant: true` → matching binding required (fail closed).
|
|
25
|
+
* - `multiTenant: false` → legacy static allowlist only.
|
|
26
|
+
*/
|
|
27
|
+
export function admitRepository(args) {
|
|
28
|
+
if (args.multiTenant) {
|
|
29
|
+
const binding = findBindingForRepo(args.bindings, args.agentId, args.repoFullName);
|
|
30
|
+
if (binding === undefined) {
|
|
31
|
+
return { admitted: false };
|
|
32
|
+
}
|
|
33
|
+
return { admitted: true, binding };
|
|
34
|
+
}
|
|
35
|
+
const needle = normalizeRepoFullName(args.repoFullName);
|
|
36
|
+
if (!args.legacyAllowlist.some((r) => normalizeRepoFullName(r) === needle)) {
|
|
37
|
+
return { admitted: false };
|
|
38
|
+
}
|
|
39
|
+
return { admitted: true };
|
|
40
|
+
}
|
|
41
|
+
/** Tools with no `enable` list stay admitted (compat with unconfigured bindings). */
|
|
42
|
+
export function isToolAdmitted(binding, toolName) {
|
|
43
|
+
var _a;
|
|
44
|
+
const enable = (_a = binding === null || binding === void 0 ? void 0 : binding.tools) === null || _a === void 0 ? void 0 : _a.enable;
|
|
45
|
+
if (enable === undefined) {
|
|
46
|
+
return true;
|
|
47
|
+
}
|
|
48
|
+
return enable.includes(toolName);
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Author-KV key scoped to a customer team under the existing `kv/` scheme:
|
|
52
|
+
* `agentkit/v1/{agent}/kv/t/{teamId}/{key}`.
|
|
53
|
+
*/
|
|
54
|
+
export function tenantKvKey(agent, teamId, key) {
|
|
55
|
+
if (!Number.isInteger(teamId) || teamId < 0) {
|
|
56
|
+
throw new Error(`invalid teamId for tenant storage: ${String(teamId)}`);
|
|
57
|
+
}
|
|
58
|
+
return storageKeys.kv(agent, `t/${teamId}/${key}`);
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Prefix for listing author-KV keys for one customer team.
|
|
62
|
+
* Matches the URI-encoded form produced by {@link tenantKvKey}.
|
|
63
|
+
*/
|
|
64
|
+
export function tenantKvPrefix(agent, teamId) {
|
|
65
|
+
if (!Number.isInteger(teamId) || teamId < 0) {
|
|
66
|
+
throw new Error(`invalid teamId for tenant storage: ${String(teamId)}`);
|
|
67
|
+
}
|
|
68
|
+
return `${STORAGE_KEY_ROOT}/${agent}/kv/${encodeURIComponent(`t/${teamId}/`)}`;
|
|
69
|
+
}
|
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Durable persistence plug-in for agent-serve.
|
|
3
|
+
*
|
|
4
|
+
* Author `agent/persistence.ts` with {@link definePersistence} to mirror the
|
|
5
|
+
* framework's durable state into storage you own (a database, S3, a data
|
|
6
|
+
* pipeline, …). Without it, state lives under `--state-root` on local disk
|
|
7
|
+
* only (and eval/A/B history follows the narrower `persistRuns` /
|
|
8
|
+
* `persistSamples` / `persistSnapshots` hooks).
|
|
9
|
+
*
|
|
10
|
+
* The sink is a plain key-value store — four functions, no schema:
|
|
11
|
+
*
|
|
12
|
+
* ```ts
|
|
13
|
+
* import { definePersistence } from "@anysphere/agent-serve/persistence";
|
|
14
|
+
*
|
|
15
|
+
* export default definePersistence({
|
|
16
|
+
* put: (key, value) => db.upsert(key, value),
|
|
17
|
+
* get: (key) => db.get(key),
|
|
18
|
+
* delete: (key) => db.delete(key),
|
|
19
|
+
* list: (prefix) => db.listByPrefix(prefix), // [{ key, value }] in key order
|
|
20
|
+
* });
|
|
21
|
+
* ```
|
|
22
|
+
*
|
|
23
|
+
* The **framework mints every key** from a stable, versioned scheme (see
|
|
24
|
+
* {@link persistenceKeys}) and decides **when** to call the sink: session
|
|
25
|
+
* records and event chunks flush when a turn's handlers have settled,
|
|
26
|
+
* reads happen at serve start (bulk restore), on continuation-token misses
|
|
27
|
+
* (lazy restore), and at playground hydration. Authors do not schedule
|
|
28
|
+
* reads or writes — the only timing knobs are {@link PersistencePolicy}'s
|
|
29
|
+
* `debounceMs` (event write batching) and `restore` (startup hydration).
|
|
30
|
+
*
|
|
31
|
+
* Because keys are opaque strings to the sink, new kinds of durable state
|
|
32
|
+
* (reminders, channel cursors, thread affinity, …) are new key prefixes —
|
|
33
|
+
* existing sinks store them with no code changes.
|
|
34
|
+
*
|
|
35
|
+
* Delivery semantics: writes are **serialized** (one sink call in flight
|
|
36
|
+
* per agent, in order), **bounded** (a sink that falls behind sheds writes
|
|
37
|
+
* rather than growing memory), and **at-most-once** — a throwing `put` is
|
|
38
|
+
* logged and dropped, never retried, and never fails a turn. The local
|
|
39
|
+
* event log under `--state-root` remains the live source of truth; this
|
|
40
|
+
* interface is the durable mirror.
|
|
41
|
+
*/
|
|
42
|
+
import type { JsonValue } from "./types.js";
|
|
43
|
+
/** One `{ key, value }` pair returned by {@link PersistenceConfig.list}. */
|
|
44
|
+
export interface PersistenceEntry {
|
|
45
|
+
key: string;
|
|
46
|
+
value: JsonValue;
|
|
47
|
+
}
|
|
48
|
+
/** Context passed to every sink call. */
|
|
49
|
+
export interface PersistenceContext {
|
|
50
|
+
/** Agent name (also baked into every key; see {@link persistenceKeys}). */
|
|
51
|
+
agentName: string;
|
|
52
|
+
/** Absolute agent project root (directory that contains `agent/`). */
|
|
53
|
+
projectRoot: string;
|
|
54
|
+
/**
|
|
55
|
+
* Why the framework is calling:
|
|
56
|
+
* - `"policy"` — a flush trigger fired (turn end, debounce, change)
|
|
57
|
+
* - `"shutdown"` — the serve process is draining; last chance to write
|
|
58
|
+
* - `"restore"` — serve start or a lazy restore; reads rebuilding state
|
|
59
|
+
*/
|
|
60
|
+
reason: "policy" | "shutdown" | "restore";
|
|
61
|
+
}
|
|
62
|
+
export interface PersistencePolicy {
|
|
63
|
+
/**
|
|
64
|
+
* Batch event-chunk writes on a quiet-period timer instead of flushing
|
|
65
|
+
* once per turn. The debounce **spans turn boundaries** — a rapid
|
|
66
|
+
* multi-turn exchange becomes one write when the session goes quiet —
|
|
67
|
+
* so it is the right choice for chatty sessions where per-turn writes
|
|
68
|
+
* are too many. Unset (default): one event chunk per turn.
|
|
69
|
+
*/
|
|
70
|
+
debounceMs?: number;
|
|
71
|
+
/**
|
|
72
|
+
* Guardrails for the **startup bulk restore**. Whatever `list` returns
|
|
73
|
+
* is filtered to these caps before anything is written to local disk, so
|
|
74
|
+
* a large store cannot blow up `--state-root` or stall serve start.
|
|
75
|
+
* Newest sessions (by `updatedAt`) win within each cap.
|
|
76
|
+
*
|
|
77
|
+
* `"off"` disables the startup restore entirely — sessions then restore
|
|
78
|
+
* one at a time as follow-ups actually arrive (lazy-only; recommended
|
|
79
|
+
* for high-traffic deployments).
|
|
80
|
+
*/
|
|
81
|
+
restore?: PersistenceRestorePolicy | "off";
|
|
82
|
+
}
|
|
83
|
+
/** Caps applied to the startup bulk restore. See {@link PersistencePolicy.restore}. */
|
|
84
|
+
export interface PersistenceRestorePolicy {
|
|
85
|
+
/** Max sessions materialized (default {@link PERSISTENCE_DEFAULT_RESTORE_MAX_SESSIONS}). */
|
|
86
|
+
maxSessions?: number;
|
|
87
|
+
/**
|
|
88
|
+
* Skip sessions whose `updatedAt` is older than this (default
|
|
89
|
+
* {@link PERSISTENCE_DEFAULT_RESTORE_MAX_AGE_MS}). Older sessions remain
|
|
90
|
+
* reachable lazily on their next follow-up.
|
|
91
|
+
*/
|
|
92
|
+
maxAgeMs?: number;
|
|
93
|
+
/**
|
|
94
|
+
* Stop restoring once this many bytes of records + events have been
|
|
95
|
+
* written (default {@link PERSISTENCE_DEFAULT_RESTORE_MAX_TOTAL_BYTES}).
|
|
96
|
+
* Checked before each session is written, so one oversized stream
|
|
97
|
+
* cannot blow past the budget.
|
|
98
|
+
*/
|
|
99
|
+
maxTotalBytes?: number;
|
|
100
|
+
}
|
|
101
|
+
export interface PersistenceConfig {
|
|
102
|
+
/** Optional label surfaced on `GET /v1/info` diagnostics. */
|
|
103
|
+
name?: string;
|
|
104
|
+
/** Timing knobs; see {@link PersistencePolicy}. */
|
|
105
|
+
policy?: PersistencePolicy;
|
|
106
|
+
/**
|
|
107
|
+
* Store one value under a key (upsert, last-write-wins). Called on the
|
|
108
|
+
* framework's schedule — never concurrently, always in order. Keep it
|
|
109
|
+
* fast or buffer internally: the delivery queue is bounded, so a sink
|
|
110
|
+
* that falls behind sustained traffic sheds writes (logged) instead of
|
|
111
|
+
* growing memory; it never stalls the agent loop.
|
|
112
|
+
*/
|
|
113
|
+
put(key: string, value: JsonValue, ctx: PersistenceContext): void | Promise<void>;
|
|
114
|
+
/** Remove a key. Optional — without it, deletions are skipped. */
|
|
115
|
+
delete?(key: string, ctx: PersistenceContext): void | Promise<void>;
|
|
116
|
+
/**
|
|
117
|
+
* Point lookup. Optional — required for **lazy restore** (resolving a
|
|
118
|
+
* continuation token on a replacement host) and the A/B backfill.
|
|
119
|
+
* Return `undefined`/`null` only for a **definitive** miss: on the lazy
|
|
120
|
+
* restore path a throw propagates and fails the follow-up (retryable) —
|
|
121
|
+
* a store outage must not read as "unknown token", which would fork the
|
|
122
|
+
* conversation onto a new session.
|
|
123
|
+
*/
|
|
124
|
+
get?(key: string, ctx: PersistenceContext): JsonValue | undefined | null | Promise<JsonValue | undefined | null>;
|
|
125
|
+
/**
|
|
126
|
+
* All entries under a key prefix, in ascending key order. Optional —
|
|
127
|
+
* required for the **startup bulk restore** (sessions + event streams)
|
|
128
|
+
* and playground eval history.
|
|
129
|
+
*/
|
|
130
|
+
list?(prefix: string, ctx: PersistenceContext): PersistenceEntry[] | Promise<PersistenceEntry[]>;
|
|
131
|
+
}
|
|
132
|
+
export type PersistenceDefinition = PersistenceConfig & {
|
|
133
|
+
readonly __agentServe: "persistence";
|
|
134
|
+
};
|
|
135
|
+
/**
|
|
136
|
+
* Author the project persistence sink (`agent/persistence.ts`, default
|
|
137
|
+
* export). See the module doc for semantics and an example.
|
|
138
|
+
*/
|
|
139
|
+
export declare function definePersistence(config: PersistenceConfig): PersistenceDefinition;
|
|
140
|
+
/**
|
|
141
|
+
* The framework-owned key scheme. Keys are a **stable, versioned contract**
|
|
142
|
+
* (the `v1/` root): sinks may treat them as opaque strings, or route on
|
|
143
|
+
* prefixes (e.g. event chunks to object storage, everything else to a
|
|
144
|
+
* database). Channel ids and continuation tokens are the only segments
|
|
145
|
+
* that may contain caller-controlled characters; they are URI-encoded.
|
|
146
|
+
*
|
|
147
|
+
* | Key | Value |
|
|
148
|
+
* | --- | --- |
|
|
149
|
+
* | `v1/{agent}/session/{sessionId}` | `SessionRecord` |
|
|
150
|
+
* | `v1/{agent}/session-events/{sessionId}/{index}` | `SessionEvent[]` chunk (index = first event's index, zero-padded) |
|
|
151
|
+
* | `v1/{agent}/continuation/{channelId}/{token}` | `{ sessionId }` |
|
|
152
|
+
* | `v1/{agent}/eval-run/{runId}` | `EvalRunSnapshot` |
|
|
153
|
+
* | `v1/{agent}/ab-sample/{sessionId}/{at}` | `ABMetricSample` |
|
|
154
|
+
* | `v1/{agent}/ab-snapshot` | latest aggregate `ABSnapshot` |
|
|
155
|
+
*/
|
|
156
|
+
export declare const persistenceKeys: {
|
|
157
|
+
readonly session: (agent: string, sessionId: string) => string;
|
|
158
|
+
readonly sessionPrefix: (agent: string) => string;
|
|
159
|
+
readonly sessionEvents: (agent: string, sessionId: string, firstIndex: number) => string;
|
|
160
|
+
readonly sessionEventsPrefix: (agent: string, sessionId: string) => string;
|
|
161
|
+
readonly continuation: (agent: string, channelId: string, continuationKey: string) => string;
|
|
162
|
+
readonly evalRun: (agent: string, runId: string) => string;
|
|
163
|
+
readonly evalRunPrefix: (agent: string) => string;
|
|
164
|
+
readonly abSample: (agent: string, sessionId: string, at: string) => string;
|
|
165
|
+
readonly abSnapshot: (agent: string) => string;
|
|
166
|
+
};
|
|
167
|
+
export declare const PERSISTENCE_DEFAULT_RESTORE_MAX_SESSIONS = 1000;
|
|
168
|
+
export declare const PERSISTENCE_DEFAULT_RESTORE_MAX_AGE_MS: number;
|
|
169
|
+
export declare const PERSISTENCE_DEFAULT_RESTORE_MAX_TOTAL_BYTES = 1073741824;
|
|
170
|
+
/** {@link PersistencePolicy} with defaults applied. */
|
|
171
|
+
export interface ResolvedPersistencePolicy {
|
|
172
|
+
/** Event-chunk flush trigger: per turn, or debounced across turns. */
|
|
173
|
+
events: "turnEnd" | {
|
|
174
|
+
debounceMs: number;
|
|
175
|
+
};
|
|
176
|
+
restore: "off" | {
|
|
177
|
+
maxSessions: number;
|
|
178
|
+
maxAgeMs: number;
|
|
179
|
+
maxTotalBytes: number;
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
/** Apply {@link PersistencePolicy} defaults (exposed for tooling/tests). */
|
|
183
|
+
export declare function resolvePersistencePolicy(policy: PersistencePolicy | undefined): ResolvedPersistencePolicy;
|
|
184
|
+
//# sourceMappingURL=persistence.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"persistence.d.ts","sourceRoot":"","sources":["../src/persistence.ts"],"names":[],"mappings":"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"}
|