@sema-agent/core
Version:
Stateless, task-oriented AI agent core
140 lines (139 loc) • 5.91 kB
JavaScript
const GATE = "src/core/runner/prepare-gate-stations.ts";
const CHAIN = "src/core/runner/prepare-policy-chain.ts";
const LANES = "src/core/gate-lanes.ts";
const POLICY = "src/core/tool-policy.ts";
const OFFER = "src/core/runner/permission-rule-lanes.ts";
const PARK = "src/core/runner/prepare-park-ask.ts";
const HANDLERS = "src/core/runner/run-harness-handlers.ts";
const STATIONS = "src/core/runner/call-hook-stations.ts";
const any = (file) => ({ kind: "any", file });
const wire = (file) => ({ kind: "wire", file });
const spelling = (file) => ({ kind: "spelling", file });
const seat = (rank, file) => ({ kind: "seat", rank, file });
export const NAME_READINGS = {
"gate.compliance": any(GATE),
"gate.egress": any(GATE),
"gate.peerMessage": any(GATE),
"gate.markSources": any(GATE),
"gate.shellSeat": seat("tier", GATE),
"gate.sandboxBoundary.egress": any(CHAIN),
"gate.sandboxBoundary.hand": wire(CHAIN),
"gate.preToolUse": wire("src/core/hooks.ts"),
"fold.readStation": seat("member", "src/tools/fs/shell-read-check.ts"),
"lanes.contentQuestionClass": any(LANES),
"lanes.readOnlyShellAllow": wire(LANES),
"lanes.modeFileCommand": wire(LANES),
"lanes.contentAskRoute": wire(LANES),
"lanes.orgContentAskExemption": wire(LANES),
"lanes.persistedEditSkip": wire(LANES),
"lanes.persistedLaneSkip": wire(LANES),
"lanes.allowLayerQuestionSkip": wire(LANES),
"lanes.sandboxQuestionSkip": wire(LANES),
"policy.nameLists": any(POLICY),
"policy.shellToolsList": any(POLICY),
"policy.projectionReplay": any(POLICY),
"policy.sessionRules": any("src/core/runner/session-rule-policy.ts"),
"policy.sessionRules.effect": wire("src/core/runner/session-rule-policy.ts"),
"allowEntry.names": any("src/core/allow-entry.ts"),
"skillGrant.binding": wire("src/core/skill-grant.ts"),
"gate.skillActivationSeat": wire(GATE),
"policy.permissionRules": any("src/core/permission-rules.ts"),
"policy.persistedGrammar": any("src/core/permission-rule-model.ts"),
"policy.durableQuestion": any("src/core/ask-question.ts"),
"policy.sensitivePathGuardedByName": any("src/core/sensitive-path-policy.ts"),
"floor.protectivePathTarget": seat("member", "src/core/tool-registry.ts"),
"mode.planRosterRow": wire("src/core/mode-policy.ts"),
"offer.laneTool": wire(OFFER),
"offer.orgQuestionExemption": wire(OFFER),
"offer.marks": seat("tier", OFFER),
"offer.marks.egress": any(OFFER),
"park.riskDescriptor": seat("tier", PARK),
"park.syncFirstRoute": wire(PARK),
"report.riskAxes": seat("tier", CHAIN),
"report.riskAxes.egress": any(CHAIN),
"report.riskAxes.negatives": seat("member", CHAIN),
"report.markSources": any(CHAIN),
"verify.wroteThisRun": wire(HANDLERS),
"verify.wroteThisRunSeed": wire("src/core/runner/run-attachment-seats.ts"),
"event.toolStartEnd": spelling(HANDLERS),
"hook.postToolUse": wire(STATIONS),
"hook.postToolUseFailure": wire(STATIONS),
"hook.postToolBatch": spelling(HANDLERS),
"stats.subagentToolCounter": spelling("src/agents/subagent.ts"),
"activity.sink": spelling(HANDLERS),
"reconcile.orphanEffect": spelling("src/core/session-reconcile.ts"),
"inherited.questionFloat": wire(CHAIN),
"park.contentKindProjection": wire("src/core/checkpoint-store.ts"),
"resume.contentAskRow": wire("src/core/runner/decide-continuation.ts"),
"resume.editRecheckQuestionSkip": wire("src/core/runner/resume-apply.ts"),
"resume.questionArgsShown": wire("src/core/runner/run-leg.ts"),
"budget.exemptResult": wire("src/core/tool-result-budget.ts"),
"compaction.compactableResult": wire("src/core/context-edit.ts"),
};
export function ruleNamesOf(call) {
const names = call.face?.names;
return names !== undefined && names.includes(call.toolName) ? names : [call.toolName];
}
function readingOf(site, kind) {
const r = NAME_READINGS[site];
if (r.kind !== kind)
throw new Error(`tool-name reading: site ${JSON.stringify(site)} is a ${r.kind} site, read through the ${kind} port`);
return r;
}
export function heldBy(site, set, call) {
readingOf(site, "any");
return ruleNamesOf(call).some((n) => set.has(n));
}
export function heldValues(site, map, call) {
readingOf(site, "any");
const out = [];
for (const n of ruleNamesOf(call)) {
const v = map.get(n);
if (v !== undefined)
out.push(v);
}
return out;
}
export function wireOf(site, call) {
readingOf(site, "wire");
return call.toolName;
}
const DEPLOYMENT_MARK = "deployment";
const TIER_RANK = { never: 1, maybe: 2, always: 3 };
function seatAt(name, value) {
return {
name,
value,
read: (table) => table.get(name),
holds: (set) => set.has(name),
};
}
export function seatOf(site, table, call) {
const r = readingOf(site, "seat");
const names = ruleNamesOf(call);
const valueAt = (n) => (typeof table.get === "function" ? table.get(n) : table.has(n) ? true : undefined);
if (r.kind === "seat" && r.rank === "tier") {
let best;
for (const n of names) {
const v = valueAt(n);
if (v === undefined)
continue;
if (best === undefined || TIER_RANK[v] > TIER_RANK[best.value])
best = { name: n, value: v };
}
if (best === undefined)
return undefined;
const chosen = seatAt(best.name, best.value);
const tierSeat = {
...chosen,
shellGated: (shellGated, markSources) => shellGated.has(chosen.name) && !names.some((n) => markSources.get(n)?.has(DEPLOYMENT_MARK) === true),
};
return tierSeat;
}
for (const n of names) {
const v = valueAt(n);
if (v !== undefined)
return seatAt(n, v);
}
return undefined;
}