UNPKG

@sema-agent/core

Version:

Stateless, task-oriented AI agent core

161 lines (160 loc) • 8.84 kB
import { parseScopeKey } from "./memory-engine/scope-contract.js"; import { thrownText } from "./thrown-value.js"; function codedError(code, message) { const e = new Error(message); e.code = code; return e; } export function foldAdmissionFreeze(input) { return input.delegated ? (input.inherited ?? []) : input.inherited; } export function readDurableOrgAdmission(row) { return { scopes: row.admittedOrgScopes ?? [], writeScope: row.admittedOrgWriteScope ?? null }; } const ORG_SHAPE = /^org:/; function orgScopesOf(spec) { if (spec.scopeContract !== "v2") return { readOrg: [], writeOrg: null }; const readOrg = spec.scopes.filter((s) => parseScopeKey(s).kind === "org"); const writeOrg = spec.writeScope !== null && parseScopeKey(spec.writeScope).kind === "org" ? spec.writeScope : null; return { readOrg, writeOrg }; } export async function admitMemoryScopes(input) { const { memorySpec, principal, admission, deploymentScopes, parentAdmittedOrgScopes } = input; const governed = admission !== undefined || deploymentScopes.size > 0 || input.priorOwnVerdict !== undefined || input.governedProvenance || input.orgMemoryDenied || (parentAdmittedOrgScopes !== undefined && parentAdmittedOrgScopes.length > 0); if (governed && memorySpec.scopeContract !== "v2") { const shaped = [...memorySpec.scopes, ...(memorySpec.writeScope !== null ? [memorySpec.writeScope] : [])].find((s) => ORG_SHAPE.test(s)); if (shaped !== undefined) { throw codedError("memory.admission_denied", `memory scope "${shaped}" is org-shaped but the task did not opt into the v2 scope contract ` + `(memory.scopeContract: "v2") — on a deployment with org-memory admission configured, org scopes ` + `outside the contract are refused (fail-closed), not mounted as opaque keys.`); } } const { readOrg, writeOrg } = orgScopesOf(memorySpec); const allOrg = [...readOrg, ...(writeOrg !== null && !readOrg.includes(writeOrg) ? [writeOrg] : [])]; if (allOrg.length === 0) { return { scopes: [...memorySpec.scopes], writeScope: memorySpec.writeScope, admittedOrgScopes: [], droppedDeploymentScopes: [], writeScopeNarrowed: false, ownVerdict: undefined, }; } const priorOwn = input.priorOwnVerdict; const applySessionFreeze = (proj) => { let { admitted, scopes, writeScope, dropped, writeScopeNarrowed } = proj; if (priorOwn !== undefined) { const outsideRequest = admitted.filter((s) => !deploymentScopes.has(s) && !priorOwn.scopes.includes(s)); if (outsideRequest.length > 0) { throw codedError("memory.admission_denied", `org memory scope(s) ${outsideRequest.map((s) => `"${s}"`).join(", ")} are outside this session's frozen ` + `admission verdict (recorded at suspend) — a session's org grant can only narrow across suspend/resume.`); } const frozenOut = admitted.filter((s) => !priorOwn.scopes.includes(s)); if (frozenOut.length > 0) { dropped = [...dropped, ...frozenOut]; admitted = admitted.filter((s) => priorOwn.scopes.includes(s)); scopes = scopes.filter((s) => !frozenOut.includes(s)); } if (writeScope !== null && writeOrg !== null && writeScope === writeOrg && priorOwn.writeScope !== writeScope) { writeScope = null; writeScopeNarrowed = true; } } return { scopes, writeScope, admittedOrgScopes: admitted, droppedDeploymentScopes: dropped, writeScopeNarrowed, ownVerdict: { scopes: admitted, writeScope: writeScope !== null && writeOrg !== null && writeScope === writeOrg ? writeScope : null }, }; }; const stampedOrigins = memorySpec.scopeOrigins; const originOf = (scope) => stampedOrigins !== undefined ? (stampedOrigins[scope] === "deployment" ? "deployment" : "request") : deploymentScopes.has(scope) ? "deployment" : "request"; const requests = allOrg.map((scope) => ({ scope, origin: originOf(scope) })); const requestOrigin = requests.filter((r) => r.origin === "request"); if (input.orgMemoryDenied && requestOrigin.length > 0) { throw codedError(input.complianceDegraded ? "config.compliance_required" : "config.compliance_denied", `org memory scope(s) ${requestOrigin.map((r) => `"${r.scope}"`).join(", ")} are denied for this principal by the ` + `compliance posture (capability "org_memory_mount"${input.complianceDegraded ? "; posture resolver failing, fail-closed" : ""}).`); } if (parentAdmittedOrgScopes !== undefined) { const exceeding = requestOrigin.filter((r) => !parentAdmittedOrgScopes.includes(r.scope)); if (exceeding.length > 0) { throw codedError("memory.admission_denied", `delegated child requests org memory scope(s) ${exceeding.map((r) => `"${r.scope}"`).join(", ")} outside the ` + `parent's frozen admission verdict — a child plane can only narrow the parent's org grant, never exceed it.`); } } if (admission === undefined) { if (requestOrigin.length > 0) { throw codedError("memory.admission_required", `org memory scope(s) ${requestOrigin.map((r) => `"${r.scope}"`).join(", ")} come from the request side but this ` + `deployment has no memory-scope admission resolver (RunnerDeps.memoryScopeAdmission) — refused fail-closed. ` + `Deployment-pinned org scopes belong in RunnerDeps.deploymentMemoryScopes.`); } return applySessionFreeze({ admitted: allOrg, scopes: [...memorySpec.scopes], writeScope: memorySpec.writeScope, dropped: [], writeScopeNarrowed: false, }); } if (requestOrigin.length > 0 && principal === undefined) { throw codedError("memory.admission_denied", `org memory scope(s) ${requestOrigin.map((r) => `"${r.scope}"`).join(", ")} require an authenticated ` + `TaskSpec.principal for admission — a principal-less request cannot be admitted to a tenant plane.`); } let verdict; try { verdict = await admission({ principal, requested: requests, requestedWriteScope: writeOrg !== null ? { scope: writeOrg, origin: originOf(writeOrg) } : null, }); } catch (err) { const hinted = err.retryAfterMs; const e = codedError("memory.admission_required", `memory-scope admission resolver failed (${thrownText(err)}) — refused fail-closed.`); if (typeof hinted === "number" && Number.isFinite(hinted) && hinted > 0) e.retryAfterMs = hinted; throw e; } if (!verdict.ok) { throw codedError("memory.admission_denied", `org memory admission denied: ${verdict.reason}`); } const unrequested = verdict.scopes.filter((s) => !allOrg.includes(s)); if (unrequested.length > 0 || (verdict.writeScope !== null && verdict.writeScope !== writeOrg)) { throw codedError("memory.admission_denied", `memory-scope admission verdict granted unrequested scope(s) ` + `${[...unrequested, ...(verdict.writeScope !== null && verdict.writeScope !== writeOrg ? [String(verdict.writeScope)] : [])].map((s) => `"${s}"`).join(", ")} — ` + `admission can only narrow a request, never extend it; treating the verdict as a resolver fault.`); } const refusedRequest = requestOrigin.filter((r) => !verdict.scopes.includes(r.scope)); if (refusedRequest.length > 0) { throw codedError("memory.admission_denied", `org memory scope(s) ${refusedRequest.map((r) => `"${r.scope}"`).join(", ")} were not admitted — the whole ` + `prepare is refused (two-state verdict; partial admission is never applied silently).`); } const dropped = requests.filter((r) => r.origin === "deployment" && !verdict.scopes.includes(r.scope)).map((r) => r.scope); const admitted = allOrg.filter((s) => !dropped.includes(s)); const scopes = memorySpec.scopes.filter((s) => !dropped.includes(s)); let writeScope = memorySpec.writeScope; let writeScopeNarrowed = false; if (writeOrg !== null) { if (verdict.writeScope === writeOrg && !dropped.includes(writeOrg)) { writeScope = writeOrg; } else { writeScope = null; writeScopeNarrowed = true; } } return applySessionFreeze({ admitted, scopes, writeScope, dropped, writeScopeNarrowed }); }