@sema-agent/core
Version:
Stateless, task-oriented AI agent core
44 lines (43 loc) • 3.4 kB
TypeScript
import type { MaybeCompactOptions } from "../auto-compaction.js";
import type { TaskSpec } from "../types.js";
import type { Prepared, RunnerDepsSeat } from "./contracts.js";
/**
* The cost-optimization compaction options threaded into BOTH `maybeCompact` call
* sites (within-task turn boundary + `finish()`). All three fields come from `RunnerDeps` (a trusted
* FUNCTION seam — never `TaskSpec`, which is serializable/durable-resumable/untrusted-caller). The
* Runner OWNS the consecutive-reuse counter (`prepared.compactionReuseRef`) so the
* `maxConsecutiveProviderReuse` drift guard spans the whole task across both sites: it FEEDS the current
* count in as `consecutiveProviderReuse`, and {@link recordCompactionReuse} updates it from the result.
* The provider half is absent when no provider is wired (byte-identical to the prior behavior at every
* call site); the #1036 `onCommitted` effect sink rides unconditionally, which is why the
* function itself always returns an object.
*/
export declare function seamCCompactionOptions(runner: RunnerDepsSeat, prepared: Prepared): Pick<MaybeCompactOptions, "summaryProvider" | "onCompaction" | "maxConsecutiveProviderReuse" | "consecutiveProviderReuse" | "onCommitted">;
/** Resolve the pre/postCompact lifecycle callbacks (whole-slot `spec.hooks ??
* deps.hooks`, same resolution as the stop hook) and wrap each in a SWALLOW+TRACE shell before
* threading them into maybeCompact. The wrapper owns the observability half of the R3 MED contract
* (maybeCompact swallows defensively too, but has no sink): a throwing callback is reported via
* `onError(phase:"hook")` and treated as absent; a `block` returned under a "forced" trigger is
* reported as ignored (maybeCompact enforces the ignore — blocking a compaction the provider/trim
* layer already demanded would kill the run). */
export declare function compactionHookOptions(runner: RunnerDepsSeat, spec: TaskSpec, sessionId: string, trigger: "auto" | "manual" | "forced",
/** The leg's identity envelope, spread onto both compaction contexts by the wrappers
* below (the compaction module builds its contexts below the runner and cannot know the leg;
* the wrapper is the runner's seam). Every runner call site supplies `prepared.hookIdentity`;
* optional only so a context built without a leg stays honestly identity-less. */
identity?: import("../hooks.js").HookInvocationIdentity,
/** The leg's already-validated seat bound (`Prepared.hookTimeoutMs`) and its abort signal. Optional
* for the same reason `identity` is — a wrapper built without a prepared leg still works, on the
* default bound and with no signal. The signal is what keeps a hung compaction hook from holding a
* CANCELLED run's turn boundary for the whole deadline (the seat's post-abort grace). */
seatBound?: {
timeoutMs: number;
signal?: AbortSignal;
}): Pick<MaybeCompactOptions, "trigger" | "preCompact" | "postCompact">;
/** Fold a finished compaction's `reused` flag into the run-scoped consecutive-reuse
* counter: a reused (provider) summary increments it, a real (LLM) summary resets it to 0. A no-op
* compaction (`compacted:false`) leaves the counter untouched. No-op when no provider is wired. */
export declare function recordCompactionReuse(runner: RunnerDepsSeat, prepared: Prepared, comp: {
compacted: boolean;
reused?: boolean;
}): void;