Skip to main content
Need an enterprise-grade solution? Infisical offers managed Agent Vault with enterprise support, SLAs, and advanced features. Book a demo with us to learn more.
A credential store describes where a vault’s credentials live. Every vault has exactly one credential store, chosen at create time and switchable later (see Switching a vault’s credential store). There are two kinds:
  • Built-in (default): Credentials live in Agent Vault’s local SQLite database, encrypted at rest with the data encryption key (DEK). Operators add, edit, and delete credentials through the CLI, HTTP API, or browser UI. Agents request new credentials via proposals.
  • Infisical: Credentials live in an Infisical instance. Agent Vault polls Infisical at a per-vault cadence, caches the encrypted snapshot locally, and serves it to proxied requests. The cached values are encrypted with the same DEK as built-in credentials, so the at-rest threat model is identical. Local mutations are rejected; Infisical is the source of truth.

How injection works

Injection is unchanged across kinds. The proxy reads from the local credentials table and decrypts with the DEK at request time. For Infisical-backed vaults, the sync worker (not the proxy) is what populates that table from upstream. A referenced key with no static row falls through to the dynamic-secret resolver (see Dynamic secrets) before erroring as missing.

Choosing a kind at create time

# Built-in (default)
agent-vault vault create my-app

# Infisical-backed
agent-vault vault create my-app \
  --credential-store=infisical \
  --infisical-project-id=abc123 \
  --infisical-environment=dev \
  --infisical-path=/stripe \
  --poll-interval-seconds=60
The create handler probes Infisical first. If the project, environment, or path doesn’t resolve, or if the machine identity can’t read it, the request fails with a clear error and the vault is not created. On success, the vault row, the credential-store config, the initial encrypted secret snapshot, and your admin grant are all committed in a single SQL transaction. To inspect a vault’s credential store later:
agent-vault vault credential-store show my-app

Switching a vault’s credential store

A vault admin or instance owner can switch the store backing an existing vault, keeping its services, grants, proposals, and logs. The two directions behave differently:
  • Built-in → Infisical (connect): Agent Vault probes Infisical first (same validation as create). On success it overwrites the vault’s built-in credentials with the fetched snapshot and starts polling. Any credentials previously stored locally are replaced. Like external-store vault creation, this direction is instance-owner only because the broker’s machine identity, not the caller’s, authorizes the upstream fetch.
  • Infisical → built-in (disconnect): the external source is disconnected and polling stops. The last synced secrets are kept in place as ordinary built-in credentials, now editable through the CLI, API, and UI. Nothing is deleted. A vault admin or instance owner can do this.
Because connecting overwrites local credentials and disconnecting changes the source of truth, both directions require a typed confirmation (the vault name) in the UI and CLI.
# Connect an existing vault to Infisical (overwrites built-in credentials)
agent-vault vault credential-store set my-app \
  --kind=infisical \
  --infisical-project-id=abc123 \
  --infisical-environment=dev \
  --infisical-path=/stripe \
  --poll-interval-seconds=60

# Disconnect Infisical, keeping the synced secrets as built-in credentials
agent-vault vault credential-store set my-app --kind=builtin
In the browser, open the vault’s Settings → Edit settings and change the Credential store field in the drawer. The Infisical option is available only when the server has INFISICAL_URL configured. HTTP: PATCH {AGENT_VAULT_ADDR}/v1/vaults/{name}/credential-store with {"kind":"builtin"} or {"kind":"infisical","config":{...},"poll_interval_seconds":N}. Disconnecting (builtin) needs vault admin or instance owner; connecting (infisical) needs instance owner.

Upstream key naming

Agent Vault requires credential keys to match ^[A-Z][A-Z0-9_]*$ (UPPER_SNAKE_CASE). The same rule applies to keys fetched from Infisical: any non-conforming key (e.g., database-url, stripeKey) fails the whole sync with external_store_invalid_key and the vault keeps serving its previous snapshot until the key is renamed upstream. There is no partial sync. Rename the secret in Infisical, then retry.

Refreshing on demand

The periodic syncer keeps the vault fresh on its own (default 60s; configured at create with --poll-interval-seconds). For “I just rotated a secret upstream” cases, force an immediate refresh:
  • CLI: agent-vault vault credential-store sync <name>.
  • Web UI: click Manual sync on the vault’s Credentials tab.
  • HTTP: POST {AGENT_VAULT_ADDR}/v1/vaults/{name}/sync (any vault member). Returns the post-refresh credential_store summary; a 409 means another refresh is already in flight.
The poll interval is set at create time. To change cadence on an existing Infisical-backed vault, re-run vault credential-store set <name> --kind=infisical with the desired --poll-interval-seconds (this re-probes and re-syncs from the same source).

Dynamic secrets

When a vault is Infisical-backed, Agent Vault also exposes any Infisical dynamic secrets configured at the vault’s secret_path. Dynamic secrets are not static key/value pairs: Agent Vault asks Infisical to mint a short-lived lease (which provisions an ephemeral resource, e.g. a temporary database user), and each field the lease returns becomes a usable credential. Unlike static secrets, dynamic-secret leases are minted lazily, at request time rather than on the poll loop. The first proxied request that needs a dynamic credential mints a lease; the values are cached in memory and reused until the lease nears expiry, at which point Agent Vault renews it (or re-mints if renewal fails). Leased values are never written to the local credentials table; only lease metadata (the lease ID, needed to revoke) is persisted.

Credential key naming

A dynamic secret named db-postgres returning fields username, password, and port is exposed as the credential keys DB_POSTGRES_USERNAME, DB_POSTGRES_PASSWORD, and DB_POSTGRES_PORT. The pattern is <DYNAMIC_SECRET_NAME>_<FIELD>, upper-snake-cased. Reference these keys in a service’s auth or substitutions exactly like any other credential:
agent-vault service set my-db \
  --vault=my-app \
  --host=db.internal \
  --auth=basic \
  --username=DB_POSTGRES_USERNAME \
  --password=DB_POSTGRES_PASSWORD
Listing a vault’s credentials shows dynamic-secret fields as ordinary rows tagged type: dynamic (in the CLI, web UI, and API), alongside static credentials. To enumerate the concrete field keys, listing mints a lease for each dynamic secret (provisioning the real ephemeral resource); the lease is cached and reused by the proxy, so listing and use share one lease. Because minting provisions upstream resources, enumeration is gated to vault member+ callers; proxy-role agents only ever lease on actual proxied use of a wired service. Dynamic rows are read-only here (they cannot be edited or deleted, since the source is Infisical).

Lease lifecycle

Leases are revoked best-effort when a vault disconnects from or reconfigures its Infisical store, when a vault is deleted, and on server shutdown. Leases that survive a restart (their in-memory values are gone) are swept and revoked on the next startup. If a revoke call fails, Infisical’s own lease TTL is the backstop. Dynamic secrets reuse the vault’s existing Infisical connection (project_id, environment, secret_path) and lease TTL (the dynamic secret’s configured default), so there are no extra environment variables or flags to set.

Outage behavior

If a sync to Infisical fails (network blip, auth-token rotation, upstream 5xx), Agent Vault keeps serving the last good snapshot. The vault’s last_sync_status flips to error and the short error message surfaces in the CLI and UI, but proxied requests continue to work with stale credentials. There is no automatic fail-closed window. Unsetting INFISICAL_URL and restarting Agent Vault leaves existing Infisical-backed vaults intact: the syncer never starts, but every vault keeps serving its cached snapshot indefinitely. Writes still 409. To force-clear secret residue, delete the vault: vaults deletes cascade to credentials, credential-store rows, and request logs through SQLite foreign keys.

Set-up

Setting INFISICAL_URL plus one auth-method env-var group enables Infisical-backed vaults at the instance level. See Environment variables: Infisical credential store for the full list of supported auth methods and the detection priority order.