UNPKG

@sema-agent/core

Version:

Stateless, task-oriented AI agent core

55 lines (54 loc) • 4.69 kB
import type { PermissionResult } from "./tool-policy.js"; export declare const refusedOutOfContract: (message: string) => PermissionResult; /** Is `d` a refusal the engine itself minted (by object identity — a look-alike `deny` a caller built is not one)? The receipt's * answer is one of two things (the engine's refusal or its detached copy), and this tells them apart. */ export declare const isEngineRefusal: (d: unknown) => boolean; /** A decision's `decisionReason` — the closed set; the type is derived FROM this list, so a word added to either side is a * compile error rather than a drift between the type and the screen. Module-private (the package publishes the type). * `skill`: an active skill's list spoke — the allow layer's skill member cleared the call (`allowed-tools`), or this * run's deny row refused it (`disallowed-tools`); distinct from `rule` (a deployment policy) and `persisted_rule` (a * person's stored row) because the authority is the skill the run activated. `deployment_rule` / `request_rule`: an entry * of the deployment's `RunnerDeps.allowedTools` / of this run's `TaskSpec.allowedTools` cleared the call (the allow layer's * two entry-list members) — one word per author, so "who said this needs no asking" is read off the decision. */ declare const DECISION_REASONS: readonly ["rule", "mode", "hook", "safety", "classifier", "persisted_rule", "sandbox", "org_rule", "org_unavailable", "read_only", "skill", "deployment_rule", "request_rule"]; export type DecisionReason = (typeof DECISION_REASONS)[number]; export declare const RETIRED_WINDOW_MEMBER_DENY_MESSAGE: string; export declare const carriesRetiredWindow: (fallback: unknown) => boolean; /** * The VALUE screen over the engine's one-read record of a decision (never a second read of the caller's object): every * closed-set member holds a member of its set or is absent (`action` present), and the retired window is absent. The refusal * names the member and the set, one code for every arm. `undefined` is the receipt's spelling of absence. */ export declare function screenContractValues(contract: Record<string, unknown>, opts?: { skip?: ReadonlySet<string>; optional?: ReadonlySet<string>; }): PermissionResult | undefined; /** * The receipt of the records a decision nests, into the one-read record itself: each record that is PRESENT is received by * {@link receiveContract} (the decision's own function — an ordinary object, own enumerable data members, a prototype member * refused by name) and must hold every required member; a present value that is not an object, or a record missing a required * member, is refused by path. The engine's copy replaces the caller's record in `contract`, so no station reads the caller's * again. Returns the refusal, or `undefined` when every record is in contract. */ export declare function receiveNestedRecords(contract: Record<string, unknown>): PermissionResult | undefined; /** The nested records of an engine receipt, by path — frozen with the receipt, so a receipt handed back unread is the receipt. */ export declare function nestedRecordsOf(receipt: object): object[]; /** One level of the receipt, the same for the decision and each record it nests. The carrier is an ORDINARY object — it and * every object on its prototype chain are looked at for being a Proxy before any descriptor is asked for (a Proxy's traps are * the caller's code; the look invokes none of them) — so the receipt runs none of the carrier's code: a contract member is * absent or an own enumerable DATA property, its value taken off the descriptor (no read at all). Anything else refuses the * carrier, the member named by `path`: an accessor (never invoked), and a member the prototype or a non-enumerable property * supplies, unless the nearest descriptor holding it spells absence (an `undefined` data property). Descriptors are looked up * as OWN entries of the descriptor map, so a polluted `Object.prototype` names no member. Members outside the contract are * not looked at — but a retired one (`retired`) is refused by name when the carrier carries it by that same law. */ /** The receipt's own answers carry a `kind` discriminant as an own property: narrowing never asks the prototype chain (`in`) for a * word, so a polluted `Object.prototype` cannot answer for the receipt either. */ export type Received = { kind: "held"; held: Record<string, unknown>; } | { kind: "refused"; refused: PermissionResult; }; export declare function receiveContract(carrier: object, members: readonly string[], path: string, retired?: Readonly<Record<string, string>>): Received; export {};