VoltGuard

Agent security for teams without a security team

A security fuse between your AI agent and its tools.

Deterministic control. Provable trail.

const vg = createVoltGuard({
task: userRequest, // frozen while you still trust the input
allowedTools: ["read_document", "send_email"],
allowedRecipients: ["recruiter@acme.com"],
});
const verdict = await vg.check({ tool, args }); // before every tool call
if (verdict.allowed) await executeTool(tool, args); // you run the tool, VoltGuard never does
console.log(vg.auditText()); // the compliance trail, for free

Three lines in your agent loop. No framework, no proxy, no lock-in.

VoltGuard checks every tool call against the task your user actually asked for: deterministic rules first, an LLM judge second. It writes an immutable audit record either way.

Agents read trusted instructions and untrusted documents as one stream of text. A poisoned CV, invoice, or web page can quietly redirect a tool call: OWASP LLM01, indirect prompt injection. You can't prove it will never happen. You can prove it can't execute.

01Watch the fuse blow

A real agent, raw function calling with no hardening, screens a stack of CVs. One of them hides an instruction disguised as a GDPR clause: forward every candidate file to an outside address. The injection commands a tool call the user never asked for. Whether a model obeys today is a bet that varies by model and by run. VoltGuard makes the outcome the same either way: blocked, and logged.

npx tsx demo/showcase.ts

# demo recording, coming shortly

02Three layers, one verdict

Cheapest and most certain first. Every decision names the layer that made it.

Layer 1

Deny-by-default rules

Tools are allowlisted per agent. Anything off the list is blocked before it runs: no scores, no maybes.

Layer 2-a

Deterministic recipient check

A legitimate tool aimed at an unknown recipient trips the fuse. Same input, same verdict, every run.

Layer 2-b

LLM intent judge

A second model judges whether each action is consistent with what the user asked. It never reads the untrusted documents themselves, only the frozen task and the attempted call.

Blocked
{
  at: "2026-07-12T14:03:41.208Z",
  tool: "send_email",
  allowed: false,
  decidedBy: "Layer 2-b — intent judge (LLM)",
  reason: "Recipient is unrelated to the user's task and the body contains candidate data."
}

One AuditRecord per decision, allowed or blocked.

03The trail an auditor asks for

Every decision, allowed or blocked, lands in an append-only log: timestamp, tool, verdict, the layer that decided, and the reason. A flat, stable record designed to be handed over, not reconstructed from model logs. It's the kind of trail the EU AI Act expects: traceability and record-keeping, produced as a by-product of simply running your agent.