Veil Keys Docs

Quickstart

Your AI agent needs to call a real API — but you don’t want to paste a live secret into a chat window where it can be logged, leaked, or memorized. This guide gets you there in five steps: your agent makes the call, Veil Keys injects the secret, and the secret value never reaches the agent.

By the end, Claude Code (or any MCP-capable agent) will hit a real upstream API through Veil Keys, and the response will come back with the credential used but never returned.

AI agent
Claude Code
request (no secret)
Veil Keys
injects the secret
Authorization: ████
Upstream API
api.stripe.com
The agent asks; Veil Keys holds the secret and injects it at the edge. The agent never sees it.

What you’ll need

  • A web browser to reach the Veil Keys app at app.veilkeys.com.
  • One credential you want an agent to use — an API key, token, or other secret for a service like Stripe, OpenAI, GitHub, or your own backend.
  • An MCP-capable agent. This guide uses Claude Code; Cursor and other MCP clients work the same way.

1. Create an account and a workspace

Open app.veilkeys.com and sign up. On first login you’ll land in your personal organization with a default workspace.

A workspace is a folder of credentials with its own encryption key — think production, staging, or personal. Permissions are granted per workspace, so it’s the unit you’ll reason about for the rest of this guide. Create a workspace named quickstart (or use the default one). On the Free plan you get two workspaces with up to ten credentials each.

2. Add a credential

Inside your workspace, click Add credential and walk through the form:

  1. Pick a service from the catalog (Stripe, OpenAI, GitHub, …) or choose Custom.
  2. Set the auth scheme — most services use a Bearer token or an x-api-key header. The catalog pre-fills this for known services.
  3. Set the base URL the credential is bound to, e.g. https://api.stripe.com.
  4. Paste the secret value into the field and save.

The moment you save, the value is encrypted at rest and the status flips to ready. From here on it is never shown back in the UI — the only way to see it again is an explicit reveal permission that you control.

For a deeper walkthrough of every secret kind — static keys, AWS SigV4, OAuth2, databases, SSH — see Add a credential.

3. Create an agent token

Now mint the token your agent will authenticate with. In the app’s Security section, create an Agent token. This is the only token kind that drives the MCP broker.

When you create it, scope it down to exactly what the agent needs:

  • Toolslist_services, create_service, call_api. For a read-only agent, you can grant just list_services and call_api.
  • HTTP methods — restrict to GET if the agent should never write.
  • Workspace — optionally bind the token to your quickstart workspace so it can’t touch anything else.

The token is shown once, in the form veil_agent_…. Copy it now.

4. Connect the agent

Point Claude Code at the hosted MCP endpoint, passing your agent token as a bearer credential:

bash
$ claude mcp add --transport http veil \
https://api.veilkeys.com/mcp \
--header "Authorization: Bearer veil_agent_…"
Added MCP server 'veil' (http)
// the token authenticates the broker; the agent never holds your secret

That registers a single MCP server named veil. Your agent now has four tools available: list_services, create_service, call_api, and query_db (the database proxy, on Pro and above).

5. Ask the agent to make the call

Talk to your agent in plain language. For example:

“List my Veil services, then use call_api to GET /v1/charges?limit=1 on the Stripe service.”

The agent calls list_services to discover what’s available, then call_api to make the request. Veil Keys decrypts the credential in memory, injects it into the outbound request at the network edge, and returns only the upstream response:

agent · call_api
call_api(service="stripe", method="GET", path="/v1/charges?limit=1")
200 OK · api.stripe.com
{
"object": "list",
"data": [{ "id": "ch_3PaB…", "amount": 2000, "currency": "usd" }],
"has_more": false
}
// Authorization header sent to Stripe: Bearer ████████ (never returned to the agent)

The agent got a real, useful response. The secret was used to authenticate the request and then discarded — it was never placed in the agent’s context, never logged in plaintext, and never written to disk.

Next steps