← Back to PRs

#12839: feat(vault): add vault proxy mode for credential isolation

by sfo2001 open 2026-02-09 19:55 View on GitHub →
docs gateway cli agents size: XL trusted-contributor
## Summary - Add vault proxy infrastructure that keeps model API keys out of the gateway process by routing requests through an nginx reverse proxy sidecar that injects credentials from an age-encrypted vault file - Add `openclaw vault` CLI (init, status, add, remove, list, migrate) for managing age-encrypted secrets with a provider registry mapping providers to proxy ports - Extend vault proxy support to web search providers (Brave, Perplexity, Grok/xAI) and add Groq, Mistral, xAI, Brave, Perplexity to the provider registry ## Details **Architecture:** Two Docker networks enforce isolation — the gateway has no route to the internet and no access to plaintext keys. The vault sidecar decrypts `vault.age` at startup, renders an nginx config with credentials, and proxies requests to upstream APIs. **Config:** `vault.enabled` + `vault.proxies` in `openclaw.json`. When active, `normalizeProviders()` rewrites `baseUrl` to the proxy URL and substitutes a placeholder API key. **CLI:** `openclaw vault init` generates an age keypair; `vault add/remove` manage individual secrets with automatic proxy configuration for known providers; `vault migrate` moves plaintext `apiKey` values from config into the encrypted vault. **Security:** - `--proxy-host` validated against hostname regex to prevent SSRF - `--json --reveal` risk documented in vault.md - Vault file written with mode 0600, atomic rename ## Test plan - [x] 143 tests pass across 8 test files - [x] Proxy resolution, baseUrl rewriting, schema validation (commit 1) - [x] CLI subcommands: init, add, remove, list, migrate, status (commit 2) - [x] Web search execute-path tests: Brave, Perplexity, Grok route through vault proxy with auth headers omitted (commit 3) - [x] Hostname validation rejects SSRF payloads (`attacker.com/path#`, `-bad-host`, empty) - [x] `buildDefaultProxyMap()` and `findProviderBySecretName()` helper coverage - [ ] Manual: deploy with docker-compose.vault.yml, verify gateway cannot reach upstream APIs directly ## Use of AI - Idea / Architecture myself ; code / tests and documentation generated with [Claude Code](https://claude.com/claude-code) <!-- greptile_comment --> <h2>Greptile Overview</h2> <h3>Greptile Summary</h3> This PR introduces a “vault proxy” mode intended to keep provider API keys out of the gateway process. It adds: - A new `vault` config section (`vault.enabled`, `vault.proxies`, `vault.file`, `vault.publicKey`) and schema validation. - Vault proxy integration in model auth and provider normalization: when a proxy mapping exists, provider `baseUrl` is rewritten to the proxy URL and auth resolution returns a fixed placeholder key. - Web-search provider support for routing through the vault proxy, omitting auth headers when proxied. - A new `openclaw vault` CLI for initializing an age-encrypted vault file and managing secrets / migrating plaintext `apiKey` values. The changes primarily touch the agent configuration pipeline (`ensureOpenClawModelsJson` → `normalizeProviders`), auth resolution (`resolveApiKeyForProvider`, `resolveModelAuthMode`), and tool execution paths for web search. The CLI and vault operations live under `src/cli/vault-cli.ts` and `src/vault/operations.ts` and are registered via the sub-CLI registry. <h3>Confidence Score: 3/5</h3> - This PR is close to mergeable but has a likely CLI registration bug that can break the `openclaw` CLI entrypoint when the vault subcommand is loaded. - Main logic paths look coherent and are covered by tests, but `registerVaultCli()` appears to register a `vault` command that is already declared in the sub-CLI registry. That duplication commonly causes Commander to throw or behave unexpectedly in real runs, and current tests don’t exercise the full CLI registration flow. - src/cli/vault-cli.ts, src/cli/program/register.subclis.ts, src/agents/tools/web-search.ts <!-- greptile_other_comments_section --> <!-- /greptile_comment -->

Most Similar PRs