Vault mTLS for App Agents and Proxy Trust
Vault mTLS for App Agents and Proxy Trust
The useful distinction in my setup was not just "use mTLS with Vault." It was deciding which components needed what kind of output.
There are really two different jobs:
- app agents that need to authenticate to Vault and render leaf certificates or secrets
- proxy agents that need to authenticate to Vault and keep a CA chain current for upstream verification
Those jobs look similar at first, but they should not have the same permissions.
The split that made the system cleaner
For app agents, the end result is usually a leaf certificate, a secret file, or both. That means the identity needs access to a narrow issuance path and whatever secret paths belong to that workload.
For proxy agents, the goal is much smaller. They do not need to mint app certificates. They only need to keep trust material current and trigger a proxy reload when the chain changes.
That gave me a cleaner model:
- app identity -> app policy -> app output
- proxy identity -> CA-read policy -> proxy trust path
What the file layout taught me
A predictable per-user layout made debugging much easier:
- one place for the mTLS client keypair
- one place for the CA trust file
- one place for rendered proxy trust material
The exact paths matter less than the rule: every service user should have its own small trust boundary on disk.
The main operational lesson
The most common failure was incomplete trust material.
If the Vault client only trusted the intermediate when the connection really needed the full chain, TLS checks failed in ways that looked worse than they were. Once I treated "intermediate only" and "full chain for validation" as separate concerns, the behavior became predictable.
What I would keep from this design
I would keep these rules:
- use a distinct Vault identity per app or proxy
- keep proxy chain refresh separate from leaf issuance
- make TLS verification testable without root
- keep agent services minimal and boring
That combination turned the setup from a loose collection of scripts into something closer to an operating model.