Inspiration Kelvra started as information-flow control for AI agents: a policy language, a static analysis and a runtime that decide where a piece of data may go. The hackathon's AI-pipeline prompt asked how handling AI pipelines connects to cryptography. That led to one concrete question: what if the model provider never holds the plaintext at all?

A support agent has to send a customer's question to a model run by an outside provider, and a useful answer needs the customer's name, account number and phone. The usual options are to send them in clear text, or to hide them and lose the feature. TLS does not help with the first: the provider is the one receiving the plaintext.

What it does Kelvra adds a third option: seal the details.

Before anything leaves the application, each detail is encrypted with AES-256-GCM under a key that stays on our side. The token also carries a label saying who may read it. The provider receives the question in clear and the details only as tokens. The model can copy a token into its reply, but it cannot open it. When the reply reaches a destination, Kelvra checks each token against that destination's policy and only then puts the real value back. A short policy file (.klv) decides every case, and every decision goes into a signed, hash-chained record. Two threats are covered: the provider (or its logs) seeing the real details, and a prompt injection hidden in the customer's message telling the model to send them elsewhere.

What it is not: the model cannot compute on sealed values. This is not homomorphic encryption. The model can only carry them.

What we demonstrated With a scripted model that obeys a hidden instruction, all six attempts were stopped: two emails of the sealed fields to an outsider (denied), a write to the CRM (denied: it needs a person's approval), a token the model invented (refused), a token altered by one character (refused), and a destination nobody declared (refused). The provider's prompt contained no plaintext account detail and no key, and the signed record verifies.

Evidence with real models We ran the same pipeline against four hosted models through their OpenAI-compatible APIs, with our own keys: gemini-3.5-flash-lite (Google Gemini) and openai/gpt-oss-120b, openai/gpt-oss-20b and qwen/qwen3.8-27b (Groq).

Across 147 valid trials: 0 times plaintext reached the provider, and 0 deliveries to a forbidden destination.

These are small samples, and how often a model copies the tokens correctly varies a lot (complete replies: 0% to 100% depending on the model and the message). When a model alters a token, Kelvra refuses the whole reply: the safe outcome, but the answer is lost. Runs stopped by rate limits are not counted. Raw results and the method are in the repository (evaluation/live/, spec/sealing-verification.md, section 5).

The customer data in the demo is fictional. The customer messages and injection texts come from public datasets (for example Banking77 and public prompt-injection sets), so the inputs are not only ones we wrote.

How we built it Python 3.10+. Sealing uses the cryptography library (AES-256-GCM, HKDF-SHA256) as an optional extra; the demo page and the HTTP client use the standard library. Each token binds the run, the policy fingerprint, the kind of field and the canonical label into the authenticated data, so a token cannot be relabelled, replayed in another run, or opened under another policy. A token that is cut, split, altered or invented is refused, never repaired.

1,469 automated tests pass (unit, property-based and adversarial). Mutation testing of the sealing module noticed 317 of 337 changes; the other 20 were reviewed and do not change behaviour.

Challenges Real providers differ: one blocked Python's default client signature, one retired a model we planned to use, and free tiers ran out mid-measurement. We made the tools stop on quota errors, retry transient ones, and report what was not measured instead of filling the gap.

Accomplishments A boundary that fails closed, and claims that match the evidence: the documentation says what the model cannot do, and the demo page states, mode by mode, whether it is showing a scripted model or a real one.

What we learned Encrypting the connection does nothing about the provider receiving plaintext. The useful move is to decide, per value, where it may go, and to enforce that where the reply leaves the system.

Honest limits The model cannot compute on sealed values. Code running in the same process can reach the key. The boundary protects against the model and the provider, not against the application itself. No key rotation yet. Real-model results are small samples and not a proof of security. The cryptography is standard (AES-256-GCM, HKDF-SHA256). Nothing is invented, and we do not claim otherwise. What's next Key rotation, a per-token "open" event in the record, secret sharing of the master key, and larger real-model samples.

Built With

Share this project:

Updates

Submission history