scanner docs insights pricing sign in

New: one command to protect every key

The fastest way to get started is now:

npx @vaultproof/init

This scans your .env, Shamir-splits each key locally, and rewrites your environment with one vp-proj- project ID. Zero code changes.

VaultProof Documentation

Everything you need to store, protect, and proxy your API keys and secrets with split-key security.

What is VaultProof?

VaultProof is a security layer for API keys and secrets. It splits your keys, encrypts the shares separately, and reassembles them only briefly in memory during a proxied API call. Your raw API key is never stored whole at rest on any server.

It is built for developers who work with third-party API keys -- OpenAI, Anthropic, Google AI, Together.ai, and more. If you have ever committed a key to GitHub, emailed a key to a teammate, or stored a key in plaintext in a .env file on a server, VaultProof solves that problem.

The problem is real: In 2024, GitHub detected 39 million leaked secrets in public repositories. API keys are the number one attack vector for credential theft. One leaked OpenAI key can cost you thousands of dollars in minutes.

Store

Split and encrypt API keys with split-key encryption. No one -- including us -- can see the full key.

Proxy

Make API calls through VaultProof. The key is reconstructed briefly in memory, then destroyed.

Audit

Every proxied call is logged with timestamp, endpoint, status code, and latency. Full audit trail.

Quick Start

Three ways to use VaultProof. The Proxy URL is the fastest -- run npx @vaultproof/init and every SDK works.

ToolWhat it isUse whenInstall
Proxy URL RECOMMENDED Change your base URL to route through VaultProof Any app using OpenAI, Anthropic, Google, or any AI SDK No install -- just change one line
npx @vaultproof/init One command that scans your .env, splits every key, and rewrites your environment Any project with a .env file containing API keys No install -- just run with npx
Dashboard Web UI at vaultproof.dev/app Visual key management, usage monitoring, team settings No install -- just open in browser

All three tools do the same thing under the hood: split your key, encrypt both shares with different keys, and proxy API calls so the full key is only assembled briefly in memory. The difference is the interface.

RECOMMENDED

Proxy URL -- 1-line change

The fastest way to use VaultProof. Keep your existing SDK, just change the base URL. All SDK features work -- streaming, retries, types, everything.

Setup (once)

  1. Run npx @vaultproof/init -- it scans your .env, splits each key, and rewrites your environment
  2. Your .env now has a vp-proj- project ID and per-provider *_BASE_URL entries
  3. Done -- your existing code works, key is protected
OpenAI (Node.js)
import OpenAI from 'openai'

const client = new OpenAI({
  apiKey: process.env.VAULTPROOF_PROJECT_ID,  // vp-proj- project ID
  baseURL: 'https://init.vaultproof.dev/p/openai/v1'
})

// Use normally -- all SDK features work (streaming, retries, types)
const res = await client.chat.completions.create({
  model: 'gpt-4',
  messages: [{ role: 'user', content: 'Hello' }]
})
Anthropic (Node.js)
import Anthropic from '@anthropic-ai/sdk'

const client = new Anthropic({
  apiKey: process.env.VAULTPROOF_PROJECT_ID,
  baseURL: 'https://init.vaultproof.dev/p/anthropic'
})
Python
import openai

client = openai.OpenAI(
    api_key="vp-proj-...",
    base_url="https://init.vaultproof.dev/p/openai/v1"
)
Groq (Node.js)
import Groq from 'groq-sdk'

const client = new Groq({
  apiKey: process.env.VAULTPROOF_PROJECT_ID,
  baseURL: 'https://init.vaultproof.dev/p/groq/openai/v1'
})
DeepSeek (Node.js)
import OpenAI from 'openai'

const client = new OpenAI({
  apiKey: process.env.VAULTPROOF_PROJECT_ID,
  baseURL: 'https://init.vaultproof.dev/p/deepseek/v1'
})
FOR ANY SDK

Init CLI -- one command, every SDK works

Run npx @vaultproof/init in any project. It scans your .env, splits each key, and adds per-provider *_BASE_URL entries for supported header-based providers. Your OpenAI-compatible and API-key SDKs can then route through VaultProof with their normal environment variables.

bash
# Protect every key in your .env at once
npx @vaultproof/init

# Protect a custom/internal API key from .env
npx @vaultproof/init custom

# Protect vault-only runtime secrets from .env
npx @vaultproof/init secrets add

# Run with vault-only secrets injected into the child process
npx @vaultproof/init run -- npm run dev

# Protect Ansible/Terraform network automation secrets
npx @vaultproof/init netops
npx @vaultproof/init netops run -- ansible-playbook site.yml

# Preview what will happen without making changes
npx @vaultproof/init --dry-run

# Check if you have any legacy vp_live_ references to clean up
npx @vaultproof/init --check-legacy
NO SDK NEEDED

Your existing SDKs work unchanged

After running npx @vaultproof/init, your .env contains per-provider *_BASE_URL entries that point at the VaultProof proxy. Most SDKs (OpenAI, Anthropic, Stripe, etc.) read their base URL from the environment, so your code works without any changes.

.env (after running npx @vaultproof/init)
# Original keys have been split and stored securely
VAULTPROOF_PROJECT_ID=vp-proj-a8Kj3mNp9xRt2wQz

# Per-provider proxy URLs (SDKs read these automatically)
OPENAI_BASE_URL=https://init.vaultproof.dev/p/openai/v1
OPENAI_API_KEY=vp-proj-a8Kj3mNp9xRt2wQz
ANTHROPIC_BASE_URL=https://init.vaultproof.dev/p/anthropic
ANTHROPIC_API_KEY=vp-proj-a8Kj3mNp9xRt2wQz
app.js (no changes needed -- your code stays the same)
import OpenAI from 'openai'

// The SDK reads OPENAI_BASE_URL and OPENAI_API_KEY from env
const client = new OpenAI()

const res = await client.chat.completions.create({
  model: 'gpt-4',
  messages: [{ role: 'user', content: 'Hello!' }]
})
FOR YOUR TERMINAL

CLI -- run from the command line

The CLI has a few focused commands. Run it from any project directory.

terminal
# Scan .env, split every key, rewrite environment
$ npx @vaultproof/init

# Add an unsupported or internal API key from .env
$ npx @vaultproof/init custom

# Store database URLs, JWT secrets, and webhook secrets
$ npx @vaultproof/init secrets add

# Start a process with vault-only secrets injected
$ npx @vaultproof/init run -- npm run dev

# Protect and run network automation secrets
$ npx @vaultproof/init netops
$ npx @vaultproof/init netops run -- ansible-playbook site.yml

# Preview what will happen without making changes
$ npx @vaultproof/init --dry-run

# Check for legacy vp_live_ references in your project
$ npx @vaultproof/init --check-legacy
FOR YOUR BROWSER

Dashboard -- visual web interface

Use the dashboard to view your projects, monitor proxy usage, and manage settings.

  1. Go to vaultproof.dev/app and create an account or log in
  2. Run npx @vaultproof/init in your project to create a project and protect your keys
  3. Your vp-proj- project ID and protected keys appear in the dashboard
  4. Monitor proxy call logs, per-provider usage, and rate limit status
PRODUCTION SETUPS

CI/CD + Kubernetes

VaultProof works well in pipelines and clusters because the runtime only needs a public vp-proj- identifier plus per-provider proxy URLs.

Required runtime env vars
VAULTPROOF_PROJECT_ID=vp-proj-...
OPENAI_API_KEY=vp-proj-...
OPENAI_BASE_URL=https://init.vaultproof.dev/p/openai/v1
GitHub Actions
env:
  VAULTPROOF_PROJECT_ID: ${{ secrets.VAULTPROOF_PROJECT_ID }}
  OPENAI_API_KEY: ${{ secrets.VAULTPROOF_PROJECT_ID }}
  OPENAI_BASE_URL: https://init.vaultproof.dev/p/openai/v1
Kubernetes
kubectl create secret generic app-env \
  --from-literal=VAULTPROOF_PROJECT_ID=vp-proj-... \
  --from-literal=OPENAI_API_KEY=vp-proj-... \
  --from-literal=OPENAI_BASE_URL=https://init.vaultproof.dev/p/openai/v1

Server-side callers: if your jobs/pods do not send browser Origin headers, do not enable strict origin enforcement for that project.

How It Works

A deep dive into the cryptographic pipeline that protects your keys.

3.1 Key Storage Flow

When you run npx @vaultproof/init, here is exactly what happens for each key found in your .env:

The CLI scans your .env

The CLI reads .env, .env.local, .env.production, and .env.development. It identifies API keys by shape (prefix and length) against a growing provider catalog.

Shamir Secret Sharing splits the key locally

Each key is split into exactly 2 shares using Shamir's Secret Sharing over GF(256). Each share alone is mathematically useless — knowing one share reveals zero information about the original key. The splitting happens in your terminal; the plaintext key is never transmitted.

Share 1 is encrypted and uploaded

Share 1 is sent to the VaultProof worker over HTTPS. The worker encrypts it with AES-256-GCM using a key derived from the server-side master key via HKDF-SHA256. A unique salt and IV are generated per encryption. The encrypted ciphertext is stored in Supabase.

Share 2 is uploaded separately

Share 2 is stored as a separate base64 blob in Supabase. Either share alone reveals nothing about the key — this is a mathematical guarantee of the Shamir scheme, not a software assumption.

Your .env is rewritten

The original key values in your .env are replaced with your vp-proj- project ID, and per-provider *_BASE_URL lines are added pointing at the VaultProof proxy. A timestamped backup of your original .env is created first.

One project ID for everything

You receive a single vp-proj- identifier. This is not a secret — it is safe to commit, share, and put in CI variables. It tells the proxy which stored shares to reconstruct for each provider.

Key point: The plaintext API key never leaves your machine. The VaultProof server receives only Shamir shares, which are mathematically useless individually. The server encrypts Share 1 with its own master key; Share 2 is stored separately. Reconstruction requires both.

3.2 Proxy Call Flow

When your SDK makes an API call through the VaultProof proxy (via the *_BASE_URL in your .env), the key is temporarily reconstructed:

Your SDK sends a request to the proxy

Your OpenAI/Anthropic/Stripe SDK reads the *_BASE_URL from the environment and sends its request to init.vaultproof.dev/p/<provider>/... instead of the provider directly. Your vp-proj- project ID is in the Authorization: Bearer header.

Project authenticated, rate limit checked

The worker validates the project ID and checks rate limits via a strongly-consistent Durable Object counter. Invalid or rate-limited requests are rejected before any database work.

Shares fetched and decrypted

The worker fetches both encrypted shares from Supabase in a single query. Share 1 is decrypted with AES-256-GCM using the server-side master key. Share 2 is read as-is. Warm requests hit an in-memory cache (30s TTL) and skip the database round trip.

Key reconstructed via Shamir combine

The two shares are combined using Lagrange interpolation over GF(256). The original API key now exists in worker memory. This takes less than 0.1ms.

API call made to the real provider

The worker forwards your request to the real provider (OpenAI, Anthropic, Stripe, etc.) with the reconstructed key in the appropriate auth header. Streaming (SSE) is supported.

Key zeroed from memory

Immediately after the outbound request is issued, the reconstructed key buffer is overwritten with zeros. The key existed in RAM for the duration of one fetch() call — typically under 1ms. It never touches disk, logs, or persistent storage.

Response forwarded to you

The provider's response is passed through to your application with an explicit allowlist of safe response headers. Upstream headers like Set-Cookie are stripped to prevent cross-domain attacks.

3.3 What Happens in a Breach

VaultProof is designed so that compromising any single component does not expose your API keys:

Scenario What Attacker Gets Can They Reconstruct Keys?
Database breached Encrypted Share 1 (AES-256-GCM ciphertext) + Share 2 (raw Shamir share). Without the server-side master key, Share 1 is indistinguishable from random data. Share 2 alone reveals nothing about the key. No
Server master key leaked Can decrypt Share 1. But without Share 2 (which lives in a separate database row), a single share reveals nothing. Shamir's scheme is information-theoretically secure: one share of a 2-of-2 split is pure noise. No
Project ID leaked The vp-proj- identifier is public by design. An attacker can make proxy calls against your rate limit (60/min) but cannot retrieve the shares or the reconstructed key. The proxy returns the provider's response, not the key. No
Database + server master key Decrypted Share 1 + Share 2. Both shares available. Yes — requires both

Two independent secrets must both be compromised simultaneously to reconstruct any API key: (1) the database contents (both Share 1 and Share 2) and (2) the server-side encryption key (needed to decrypt Share 1). These are stored in different systems with different access controls.

3.4 Split-Key Encryption Explained

The simple version

Think of it like tearing a photo in half. Each half looks like random noise -- you cannot tell what the photo is from either piece alone. Only when you put both halves together do you see the picture. VaultProof tears your API key into two pieces of cryptographic noise. Each piece is then locked in a separate safe with a separate key. To see the photo again, you need to open both safes.

The technical version

VaultProof uses a cryptographic secret sharing scheme to split each API key into two shares. Each share is independently indistinguishable from random data -- possessing only one share gives an attacker zero information about the original key.

Reconstruction requires both shares. Without both, every possible value of the original key is equally likely. The splitting and reconstruction algorithms are implemented in the open-source @vaultproof/shamir package, which you can audit independently.

3.5 Cryptographic Proofs

For authorization, VaultProof uses cryptographic proofs that verify three things without revealing any sensitive data:

1. Ownership

You own the key slot you are requesting access to. The proof verifies your vault commitment hash matches without revealing the key material.

2. Authorization

The requesting application has been granted access to this key slot. The proof checks the app grant without exposing the grant chain.

3. Freshness

The request is fresh and not replayed. Each proof includes a unique nullifier that is stored server-side. If the same nullifier appears twice, the request is rejected.

Note: When using the SDK, ZK proof generation is handled automatically. The SDK generates proofs client-side before each proxy call.

Packages

VaultProof ships 2 npm packages. Most developers only need @vaultproof/init.

@vaultproof/init The only package most developers need

One command that scans your .env, splits every API key locally using split-key encryption, uploads encrypted shares, and rewrites your environment with a vp-proj- project ID and per-provider *_BASE_URL entries. No SDK import needed -- your existing SDKs read the new base URL from the environment and route through VaultProof automatically.

run
npx @vaultproof/init
@vaultproof/shamir Internal -- rarely needed directly

The split-key encryption engine. Bundled inside @vaultproof/init. Only install this directly if you want raw key splitting without VaultProof infrastructure.

No SDK import needed. After running npx @vaultproof/init, your existing OpenAI, Anthropic, Stripe, and other SDKs work unchanged. They read the *_BASE_URL from your environment and route through VaultProof automatically.

Proxy URL Reference

The recommended way to use VaultProof. Route any AI SDK through VaultProof by changing one URL.

URL Pattern

pattern
https://init.vaultproof.dev/p/{provider}/{path}

Replace {provider} with the provider name and {path} with the original API path. VaultProof forwards the request exactly (method, body, headers, query string).

Supported Providers

The init catalog currently includes 250 provider signatures. Common proxy-ready examples:

ProviderProxy Base URLUpstream
openai https://init.vaultproof.dev/p/openai/v1 https://api.openai.com
anthropic https://init.vaultproof.dev/p/anthropic https://api.anthropic.com
google https://init.vaultproof.dev/p/google https://generativelanguage.googleapis.com
minimax https://init.vaultproof.dev/p/minimax/v1 https://api.minimax.io
voyage https://init.vaultproof.dev/p/voyage/v1 https://api.voyageai.com
jina https://init.vaultproof.dev/p/jina https://api.jina.ai
ai21 https://init.vaultproof.dev/p/ai21/studio/v1 https://api.ai21.com
assemblyai https://init.vaultproof.dev/p/assemblyai https://api.assemblyai.com
together https://init.vaultproof.dev/p/together/v1 https://api.together.xyz
mistral https://init.vaultproof.dev/p/mistral/v1 https://api.mistral.ai
cohere https://init.vaultproof.dev/p/cohere https://api.cohere.com
groq https://init.vaultproof.dev/p/groq/openai/v1 https://api.groq.com
perplexity https://init.vaultproof.dev/p/perplexity https://api.perplexity.ai
fireworks https://init.vaultproof.dev/p/fireworks/inference/v1 https://api.fireworks.ai
deepseek https://init.vaultproof.dev/p/deepseek/v1 https://api.deepseek.com
deepl https://init.vaultproof.dev/p/deepl https://api-free.deepl.com
deepl-pro https://init.vaultproof.dev/p/deepl-pro https://api.deepl.com
replicate https://init.vaultproof.dev/p/replicate https://api.replicate.com
gitlab https://init.vaultproof.dev/p/gitlab/api/v4 https://gitlab.com
launchdarkly https://init.vaultproof.dev/p/launchdarkly/api/v2 https://app.launchdarkly.com
snyk https://init.vaultproof.dev/p/snyk/rest https://api.snyk.io
honeycomb https://init.vaultproof.dev/p/honeycomb https://api.honeycomb.io

Providers with account-specific upstreams, like Weaviate and Grafana, are supported by init when their service URL is present in your .env. For unsupported or internal HTTP APIs, run npx @vaultproof/init custom.

How Authentication Works

  1. Send your vp-proj- project ID in Authorization: Bearer or in the provider API-key header your SDK already uses
  2. VaultProof identifies your project and finds the stored key for that provider
  3. The key is reconstructed from encrypted shares briefly in memory, used to call the upstream API, then zeroed
  4. The response (including SSE streaming) is forwarded back to you transparently

SSE streaming works transparently. The proxy forwards chunked responses as they arrive. Your SDK's streaming helpers, retry logic, and type safety all work exactly as they would against the real API.

Examples

curl
curl https://init.vaultproof.dev/p/openai/v1/models \
  -H "Authorization: Bearer vp-proj-..."
Node.js (OpenAI SDK)
import OpenAI from 'openai'

const client = new OpenAI({
  apiKey: process.env.VAULTPROOF_PROJECT_ID,
  baseURL: 'https://init.vaultproof.dev/p/openai/v1'
})

const res = await client.chat.completions.create({
  model: 'gpt-4',
  messages: [{ role: 'user', content: 'Hello' }]
})
Python (openai library)
import openai

client = openai.OpenAI(
    api_key="vp-proj-...",
    base_url="https://init.vaultproof.dev/p/openai/v1"
)

res = client.chat.completions.create(
    model="gpt-4",
    messages=[{"role": "user", "content": "Hello"}]
)

Integration Reference

No SDK import needed. After running npx @vaultproof/init, your existing SDKs route through VaultProof automatically via environment variables.

How It Works

  1. Run npx @vaultproof/init -- scans your .env, splits each key, rewrites the file
  2. Your .env now contains a vp-proj- project ID and per-provider *_BASE_URL entries
  3. Your SDKs read the environment -- OpenAI, Anthropic, Stripe, and others all support *_BASE_URL env vars
  4. API calls route through VaultProof -- the proxy authenticates via Authorization: Bearer vp-proj-... or the provider API-key header, reconstructs your key briefly in memory, calls the provider, then zeros the key
.env (after init)
VAULTPROOF_PROJECT_ID=vp-proj-a8Kj3mNp9xRt2wQz
OPENAI_API_KEY=vp-proj-a8Kj3mNp9xRt2wQz
OPENAI_BASE_URL=https://init.vaultproof.dev/p/openai/v1
ANTHROPIC_API_KEY=vp-proj-a8Kj3mNp9xRt2wQz
ANTHROPIC_BASE_URL=https://init.vaultproof.dev/p/anthropic

Per-Key Limits

PUT /sdk/keys/:keyId/limits

Update per-key call limits. Set daily and monthly caps to control API usage. When a limit is reached, calls are either blocked (HTTP 429) or allowed with an alert email, depending on the blockOnLimit setting.

ParameterTypeRequiredDescription
dailyLimit number | null No Max calls per day. Set to null to remove the limit.
monthlyLimit number | null No Max calls per month. Set to null to remove the limit.
blockOnLimit boolean No If true, calls return 429 when limit is hit. If false, calls continue but an alert email is sent.

Returns:

{ status: "updated", dailyLimit: 500, monthlyLimit: 10000, blockOnLimit: true }

Rate limit response (HTTP 429)

{ error: "Daily call limit reached", limit: 500, used: 500, resets: "midnight UTC" }

Supported Providers

The catalog includes 250 signatures. This table shows common proxy-ready providers and their auth style.

ProviderValueBase URLAuth Header
OpenAI 'openai' api.openai.com Authorization: Bearer
Azure OpenAI 'azure-openai' AZURE_OPENAI_ENDPOINT api-key
Anthropic 'anthropic' api.anthropic.com x-api-key + anthropic-version
Google AI 'google' generativelanguage.googleapis.com x-goog-api-key
MiniMax 'minimax' api.minimax.io Authorization: Bearer
Voyage AI 'voyage' api.voyageai.com Authorization: Bearer
Jina AI 'jina' api.jina.ai Authorization: Bearer
AI21 'ai21' api.ai21.com Authorization: Bearer
AssemblyAI 'assemblyai' api.assemblyai.com Authorization
Together.ai 'together' api.together.xyz Authorization: Bearer
Mistral 'mistral' api.mistral.ai Authorization: Bearer
Cohere 'cohere' api.cohere.com Authorization: Bearer
Groq 'groq' api.groq.com Authorization: Bearer
Perplexity 'perplexity' api.perplexity.ai Authorization: Bearer
Fireworks 'fireworks' api.fireworks.ai Authorization: Bearer
DeepSeek 'deepseek' api.deepseek.com Authorization: Bearer
DeepL API Free 'deepl' api-free.deepl.com Authorization: DeepL-Auth-Key
DeepL API Pro 'deepl-pro' api.deepl.com Authorization: DeepL-Auth-Key
DigitalOcean 'digitalocean' api.digitalocean.com Authorization: Bearer
Netlify / Render / Heroku 'netlify', 'render', 'heroku' platform APIs Authorization: Bearer
Fastly 'fastly' api.fastly.com Fastly-Key
HCP Terraform / Pulumi 'terraform-cloud', 'pulumi' IaC APIs Bearer / token
Jira / Zendesk / Freshdesk 'jira', 'zendesk', 'freshdesk' account-specific URL Authorization: Basic
Twilio / Chargebee 'twilio', 'chargebee' api.twilio.com / site URL Authorization: Basic
Adyen 'adyen' ADYEN_API_URL X-API-Key
npm Registry 'npm-registry' registry.npmjs.org Authorization: Bearer
Qdrant / Meilisearch / Typesense / Elasticsearch 'qdrant', 'meilisearch', 'typesense', 'elasticsearch' account-specific URL API key header / Bearer / ApiKey
Railway / Fly.io 'railway', 'fly' platform APIs Authorization: Bearer
CircleCI / Buildkite / Semgrep / SonarQube Cloud 'circleci', 'buildkite', 'semgrep', 'sonarcloud' CI and code security APIs Bearer / service token header
Better Stack / LogSnag / Raygun / Doppler 'betterstack', 'logsnag', 'raygun', 'doppler' observability and secret ops APIs Authorization: Bearer
Segment / Plausible / Webflow 'segment', 'plausible', 'webflow' analytics and CMS APIs Basic / Bearer
Svix / Knock / Browserbase 'svix', 'knock', 'browserbase' workflow and agent APIs Bearer / X-BB-API-Key
Hume AI / RunPod 'hume', 'runpod' model and GPU APIs X-Hume-Api-Key / Bearer
Paystack / Lemon Squeezy 'paystack', 'lemonsqueezy' payment APIs Authorization: Bearer
Okta / Stytch 'okta', 'stytch' identity APIs SSWS / Basic
Replicate 'replicate' api.replicate.com Authorization: Bearer
GitLab 'gitlab' gitlab.com PRIVATE-TOKEN
LaunchDarkly 'launchdarkly' app.launchdarkly.com Authorization
Snyk 'snyk' api.snyk.io Authorization: token
Honeycomb 'honeycomb' api.honeycomb.io X-Honeycomb-Team

Providers with account-specific upstreams, like Azure OpenAI, Jira, Zendesk, Freshdesk, Qdrant, Meilisearch, Typesense, Elasticsearch, Weaviate, and Grafana, are supported by init when their service URL is present in your .env. For unsupported or internal HTTP APIs, run npx @vaultproof/init custom.

Which keys to store

Key typeStore?Notes
API secret keys Yes OpenAI, Anthropic, Stripe secret key, AWS secret access key, etc.
OAuth client secrets Yes Google OAuth, GitHub OAuth client secrets. Use the proxy at runtime.
Service account JSON Yes GCP service accounts, Firebase admin keys. Store the entire JSON string.
Database passwords Yes SMTP passwords, Redis auth tokens, database credentials.
PEM / SSH private keys Yes Multi-line keys work. The splitting algorithm handles newlines and special characters.
Publishable / public keys No Stripe publishable key, Supabase anon key, Firebase API key. These are public by design.
Short-lived OAuth tokens No User access tokens, JWTs, STS temporary credentials. These expire too quickly.

Keys with IP restrictions

Some providers let you restrict API keys to specific IP addresses. How this interacts with VaultProof depends on which method you use:

  • Proxy URL — The API call is routed through VaultProof's server. Remove the IP restriction on your provider key and rely on VaultProof's per-key rate limits and budget caps instead.

Connect Widget

Deprecated. The @vaultproof/connect React widget is no longer needed. The new system uses npx @vaultproof/init to protect keys at the environment level -- no widget required. Existing integrations will continue to work but new projects should use the init flow instead.

CLI Reference

One command to protect every API key in your project. No global install needed -- run with npx.

Commands

npx @vaultproof/init PRIMARY

Scans your .env (and .env.local, .env.production, .env.development), identifies API keys by prefix and length against a growing provider catalog, splits each key locally using split-key encryption, uploads encrypted shares, and rewrites your environment with a vp-proj- project ID and per-provider *_BASE_URL entries. A timestamped backup of your original .env is created first.

terminal
$ npx @vaultproof/init

Scanning .env...
  Found 3 API keys: openai, anthropic, stripe
  Splitting keys locally...
  Uploading encrypted shares...
  Rewriting .env...

Done. Your .env now uses vp-proj-a8Kj3mNp9x
  Backup saved: .env.backup.1712345678
npx @vaultproof/init custom

Protect an unsupported or internal HTTP API key already present in your .env. The CLI prompts for the provider slug, upstream base URL, auth header name, and header template, then rewrites the selected key to use your vp-proj- project ID.

terminal
$ npx @vaultproof/init custom

Possible custom/internal keys:
  1. INTERNAL_API_KEY from .env

  Provider slug: internal
  Upstream base URL: https://api.example.com
  Auth header: Authorization
  Header template: Bearer {key}

Done. INTERNAL_API_KEY now routes through https://init.vaultproof.dev/p/internal
npx @vaultproof/init secrets add

Protect runtime secrets that are not outbound HTTP API keys, including database URLs, Redis URLs, JWT/session secrets, encryption keys, OAuth client secrets, and webhook signing secrets. The CLI stores split shares and rewrites plaintext values to vaultproof:// placeholders.

terminal
$ npx @vaultproof/init secrets add

Possible vault-only secrets:
  1. DATABASE_URL from .env
  2. JWT_SECRET from .env

Done. Use npx @vaultproof/init run -- npm run dev
npx @vaultproof/init run -- <command>

Fetch vault-only secrets with your authenticated VaultProof session and inject them into a child process environment without writing plaintext back to .env.

terminal
$ npx @vaultproof/init run -- npm run dev

Injecting 2 vault-only secrets for vp-proj-a8Kj3mNp9xRt2wQz.
npx @vaultproof/init netops

Protect network automation secrets in Ansible inventories, group_vars, host_vars, .env, terraform.tfvars, and *.auto.tfvars. Ansible values are rewritten to lookup('env', ...); Terraform secrets are supplied through TF_VAR_....

terminal
$ npx @vaultproof/init netops
$ npx @vaultproof/init netops run -- ansible-playbook site.yml
npx @vaultproof/init --dry-run

Preview what init will do without making any changes. Shows which keys would be split and what your .env would look like after.

terminal
$ npx @vaultproof/init --dry-run

Dry run -- no changes will be made
  Would split: OPENAI_API_KEY (openai)
  Would split: ANTHROPIC_API_KEY (anthropic)
  Would split: STRIPE_SECRET_KEY (stripe)
  Would add: OPENAI_BASE_URL, ANTHROPIC_BASE_URL, STRIPE_BASE_URL
  Would set: VAULTPROOF_PROJECT_ID=vp-proj-...
npx @vaultproof/init --check-legacy

Scan your project for any remaining references to the old vp_live_ / vp_test_ system. Reports files and line numbers so you can clean them up.

terminal
$ npx @vaultproof/init --check-legacy

Checking for legacy references...
  No legacy references found. You're all set.

Environment Variables

After running npx @vaultproof/init, your .env contains:

VariableDescription
VAULTPROOF_PROJECT_ID Your vp-proj- project ID. Public, safe to commit. Tells the proxy which stored shares to reconstruct.
OPENAI_API_KEY Set to your vp-proj- ID (the OpenAI SDK reads this for auth).
OPENAI_BASE_URL https://init.vaultproof.dev/p/openai/v1 -- routes SDK calls through the proxy.
ANTHROPIC_BASE_URL https://init.vaultproof.dev/p/anthropic -- same pattern for each provider.

The same pattern applies for every provider: {PROVIDER}_API_KEY is set to the project ID, and {PROVIDER}_BASE_URL points at the proxy.

Detected Providers

The init command automatically detects these env vars and splits the keys they contain:

ProviderEnv Variable
openaiOPENAI_API_KEY
anthropicANTHROPIC_API_KEY
stripeSTRIPE_SECRET_KEY
awsAWS_SECRET_ACCESS_KEY
googleGOOGLE_API_KEY
groqGROQ_API_KEY
mistralMISTRAL_API_KEY
twilioTWILIO_AUTH_TOKEN
sendgridSENDGRID_API_KEY
githubGITHUB_TOKEN

Dashboard

Web interface for managing keys, viewing logs, and monitoring usage at vaultproof.dev/app.

Overview Page

Your home screen after login. At a glance you see:

  • Total keys stored -- active key count across all providers
  • API calls this month -- total proxied requests with trend indicator
  • Usage chart -- daily call volume for the past 30 days
  • Key health -- per-key error rates and last-used timestamps
  • Recent activity -- last 10 proxy calls with status

Keys Page

Full key management interface:

  • Add Key -- paste a key, select provider, add a label. Key splitting happens in-browser.
  • Test Key -- one-click test that makes a lightweight proxy call to verify the key works.
  • Rotate -- replace the stored shares with a new API key without changing the key slot ID.
  • Revoke -- permanently destroy both shares. Irreversible.
  • Code snippets -- copy-paste SDK and cURL examples for each key.

Logs Page

Complete audit trail of every proxied API call:

  • Search -- filter by key, provider, status code, date range
  • Details -- timestamp, endpoint, method, status, latency (ms)
  • Export CSV -- download logs for external analysis or compliance

Settings Page

Account and security configuration:

  • Profile -- email and account details
  • Password -- change password (requires current password)
  • Projects -- create, list, and manage vp-proj- project IDs
  • Plan -- view current tier (Free/Starter/Pro/Enterprise) and usage limits

API Reference

Base URL: https://init.vaultproof.dev

The current worker in this repo exposes project-management routes under /api/v1/init/projects and provider proxy routes under /p/:slug/*. Management routes return JSON. Proxy routes forward the upstream provider response body directly.

Health

GET /health

Simple worker health check.

{ "status": "ok", "service": "vaultproof-init" }

Projects

Authenticated with Authorization: Bearer <supabase jwt>.

POST /api/v1/init/projects

Create a new project and receive a public vp-proj-... identifier.

// Request
{
  "name": "Production",
  "allowed_origins": "https://app.example.com,https://staging.example.com",
  "strict_origin": true
}

// Response (201)
{
  "id": "uuid",
  "vp_proj_id": "vp-proj-abc123...",
  "name": "Production",
  "created_at": "2026-04-14T..."
}
GET /api/v1/init/projects

List all projects for the current user.

GET /api/v1/init/projects/:id

Fetch one project by row ID.

PUT /api/v1/init/projects/:id

Update project metadata and origin-lock settings.

{
  "name": "Production",
  "allowed_origins": "https://app.example.com",
  "strict_origin": true
}
DELETE /api/v1/init/projects/:id

Soft-revoke a project and all keys under it.

GET /api/v1/init/projects/stats/overview

Return summary stats for projects, keys, and providers.

Project Keys

Keys are uploaded as Shamir shares. Share 1 is encrypted by the worker; Share 2 is stored separately.

POST /api/v1/init/projects/:id/keys

Store or update a provider key under a project.

{
  "provider": "openai",
  "slug": "openai",
  "share1": "base64...",
  "share2": "base64...",
  "env_var": "OPENAI_API_KEY",
  "upstream_base_url": "https://api.openai.com",
  "auth_header_name": "Authorization",
  "auth_header_template": "Bearer {key}",
  "extra_headers": { "OpenAI-Beta": "assistants=v2" }
}
GET /api/v1/init/projects/:id/keys

List active keys under a project.

DELETE /api/v1/init/projects/:id/keys/:keyId

Revoke a specific stored key.

PUT /api/v1/init/projects/:id/keys/:keyId/rotate

Rotate an existing key with a new pair of shares.

{
  "share1": "base64...",
  "share2": "base64..."
}

Proxy

Authenticated with Authorization: Bearer vp-proj-... or a supported provider API-key header. Responses are forwarded from the provider, not wrapped by VaultProof.

ANY /p/:slug/*

Universal provider proxy. The worker looks up the stored upstream config for :slug, reconstructs the real key in memory, injects auth headers, and forwards the request upstream.

curl https://init.vaultproof.dev/p/openai/v1/chat/completions \
  -H "Authorization: Bearer vp-proj-..." \
  -H "Content-Type: application/json" \
  -d '{"model":"gpt-4.1-mini","messages":[{"role":"user","content":"Hello"}]}'
ANY /v1/*

Stripe compatibility path. Requests to /v1/* are proxied through the stored stripe key configuration.

Common Error Codes

CodeMeaningCommon Cause
400 Bad Request Invalid upstream config, missing required fields, or malformed JSON
401 Unauthorized Missing or invalid Supabase JWT, or invalid vp-proj-... token
403 Forbidden Origin lock rejected the request
404 Not Found Missing project, key, or route
429 Rate Limited Per-project, per-user, or per-IP limits were exceeded
500 Internal Error Share reconstruction failed or the upstream provider returned an unexpected failure

Scanner

The init CLI includes a local env-file scanner as part of the migration flow.

Privacy: The init scanner runs locally on your machine. It reads env files, detects supported provider keys or selected custom keys, and only uploads encrypted Shamir shares after you confirm.

CLI Scanner

Run one of these commands from your project directory:

commands
npx @vaultproof/init --dry-run
npx @vaultproof/init custom
npx @vaultproof/init secrets add
npx @vaultproof/init run -- npm run dev
npx @vaultproof/init netops
npx @vaultproof/init netops run -- ansible-playbook site.yml
npx @vaultproof/init --yes
npx @vaultproof/init --check-legacy
npx @vaultproof/init doctor
  • .env, .env.local, .env.production, and .env.development
  • Provider-specific key patterns from the bundled provider catalog
  • Custom/internal HTTP API keys when you run custom
  • Vault-only runtime secrets like database URLs, JWT secrets, and webhook secrets when you run secrets add
  • Ansible and Terraform network automation secrets when you run netops
  • Legacy vp_live_ references when you run --check-legacy
  • Worker, auth, and proxy reachability when you run doctor

Detection

The current init catalog covers providers such as:

OpenAI, Anthropic, Groq Stripe, Resend, SendGrid OpenRouter, DeepSeek, xAI, DeepL Azure OpenAI, Twilio, Adyen Netlify, Render, Heroku Jira, Zendesk, Freshdesk GitHub, Notion, Linear Qdrant, Turso, Meilisearch Railway, Fly.io, CircleCI Better Stack, Doppler, Segment Provider-specific env var hints

Detection is driven by the provider catalog, not a broad source-code crawl. The init flow is intentionally focused on env-file migration and rewrite.

Current Scope

The init CLI currently focuses on env-file migration. It does not scan your full source tree, CI configs, or git history in this repo. The goal is to replace plaintext secrets in the files your app actually loads at runtime.

Dashboard Scanner

A separate hosted scanner is available in the dashboard at vaultproof.dev/app/scanner for remote repository workflows.

  • Repo-level scanning workflows live separately from the init CLI
  • Use the local init scanner when your priority is rewriting plaintext env secrets quickly

Frequently Asked Questions

Common questions from developers evaluating VaultProof.

"Can VaultProof see my API keys?"

No -- and this is by design, not by policy. Your API key is split into two shares before it is stored. Share 1 is encrypted with a server-side key. Share 2 is stored separately. Neither share alone contains any information about the original key. The full key is only assembled briefly in memory during a proxy call, then immediately wiped. There is no "admin mode" that can view stored keys.

"What if I lose my project ID?"

Project IDs (vp-proj-) are not secret -- they are safe to commit and share. You can find your project ID in the dashboard at any time. If you need a new one, run npx @vaultproof/init again. Your stored keys are tied to your account, not to a specific project ID.

"What if VaultProof goes down?"

If the VaultProof server is unavailable, proxied API calls will fail because the key cannot be reconstructed. However, your API keys at the provider (OpenAI, Anthropic, etc.) are completely unaffected. VaultProof does not modify, rotate, or delete your provider keys. You can always use your original API keys directly if needed. We recommend keeping a backup of critical keys in a secure location for disaster recovery.

"Is this open source?"

Parts of VaultProof are published in this repository and as npm packages, including the init CLI, worker, dashboard, and Shamir package. Check the repo and package metadata for the current licensing and availability of each component.

"What providers are supported?"

The current init catalog includes 250 provider signatures, including OpenAI, Azure OpenAI, Anthropic, Google/Gemini, DeepL, MiniMax, Voyage AI, Jina AI, AI21, AssemblyAI, Hume AI, RunPod, Browserbase, Stripe, Chargebee, Adyen, Twilio, Telnyx, Vonage, MessageBird, Plivo, Paystack, Lemon Squeezy, Groq, xAI, OpenRouter, DeepSeek, Mistral, Together, Fireworks, Resend, SendGrid, Linear, Notion, Figma, Asana, ClickUp, monday.com, Todoist, Coda, Shortcut, GitHub, GitLab, Bitbucket, Jira, Zendesk, Freshdesk, ActiveCampaign, Klaviyo, Iterable, Braze, OneSignal, Novu, Netlify, Render, Heroku, Railway, Fly.io, DigitalOcean, Linode, Vultr, Hetzner, Scaleway, Fastly, HCP Terraform, Pulumi, npm Registry, CircleCI, Buildkite, Semgrep, SonarQube Cloud, Qdrant, Turso, Meilisearch, Typesense, Elasticsearch, Directus, Strapi, Hygraph, DatoCMS, Contentstack, Storyblok, Better Stack, Grafana, Honeycomb, Raygun, LogSnag, Snyk, Doppler, HashiCorp Vault, 1Password Connect, Opsgenie, Statuspage, LaunchDarkly, Split.io, Flagsmith, Segment, Plausible, Webflow, Svix, Knock, Brave Search, Apify, fal.ai, Serper, Make, n8n, Axiom, InfluxDB, Rollbar, BugSnag, Codecov, BrowserStack, Auth0, FusionAuth, Aiven, CockroachDB Cloud, DataStax Astra, Redis Cloud, ClickHouse Cloud, Razorpay, Mollie, GoCardless, Mercado Pago, Wise, Shippo, EasyPost, ShipEngine, Front, Help Scout, Calendly, Typeform, Productboard, Dropbox, Box, Pinata, DeepInfra, Baseten, Cartesia, Unstructured, Luma AI, Portkey, Scale AI, Braintrust, Eden AI, VirusTotal, IPinfo, Apollo, Buttondown, Close, Greenhouse Harvest, Xendit, Midtrans, Coinbase Commerce, Lokalise, Crowdin, Sendbird, Mux, bunny.net, Prerender.io, ImageKit, SambaNova, NVIDIA NIM, FriendliAI, Hyperbolic, Vapi, Retell AI, Rev AI, Speechmatics, Gladia, Soniox, Resemble AI, Infobip, Mailchimp Marketing, Fauna, Zilliz Cloud, Pipedream, Attio, Recurly, Phrase Strings, Transifex, RevenueCat, Qovery, Northflank, Koyeb, Deno Deploy, Supabase, Neon, and more. For proxying, each stored key carries its own validated upstream URL and auth-header template, so the worker can support provider-specific routing without hardcoding every API path.

"How is this different from 1Password or HashiCorp Vault?"

1Password and HashiCorp Vault store secrets and give them back to you in plaintext when you need them. Your application then uses the key directly, meaning it exists in your app's memory, potentially in logs, and definitely in network traffic. VaultProof never gives you the key back. Instead, it makes the API call for you using the reconstructed key, which only exists briefly in VaultProof's memory during the call. Your application never touches the raw key after initial storage.

"What about HIPAA / SOC 2?"

Compliance certifications (SOC 2, HIPAA) are planned but not yet obtained. The current architecture (encryption at rest, TLS in transit, audit logging, access controls) is designed with compliance in mind. Contact us at team@vaultproof.dev for compliance inquiries.

"Does VaultProof add latency to my API calls?"

Yes, but it is minimal. The overhead is the time to decrypt both shares and reconstruct the key (a few milliseconds) plus one additional network hop (edge to backend). For most LLM API calls, which take 500ms-5s to complete, VaultProof adds less than 50ms of overhead -- typically under 2% of the total request time.

"Can I use VaultProof in production?"

Yes. VaultProof runs on a global edge network (330+ cities worldwide) with multi-region database replication. Use your vp-proj- project ID in both production and development -- the proxy handles routing to the correct stored keys for each provider.