by icoretech
Enables AI agents and automation to securely access Vaultwarden or Bitwarden vault items—including passwords, TOTPs, notes, attachments, and sends—through the official Bitwarden CLI without re‑implementing client‑side cryptography.
Warden MCP provides an MCP server that bridges AI agents with Vaultwarden/Bitwarden vaults. It proxies requests from agents to the Bitwarden CLI (bw), allowing secure search, read, creation, update, move, and deletion of vault items while keeping cryptographic handling inside the official CLI.
npx:
npx -y @icoretech/warden-mcp@latest --stdio
BW_HOST – URL of the Vaultwarden/Bitwarden instanceBW_CLIENTID / BW_CLIENTSECRET or BW_USER / BW_PASSWORDKEYCHAIN_ALLOW_ENV_FALLBACK=true for single‑tenant HTTP mode--stdio) or the HTTP/SSE endpoint (http://localhost:3005/sse?v=2).keychain_get_password, keychain_create_login, keychain_search_items, etc., as defined in the tool reference.reveal:true is explicitly requested; optional read‑only and no‑reveal modes.KEYCHAIN_BW_HOME_ROOT.ghcr.io/icoretech/warden-mcp) with non‑root user and persistent volume support./healthz, /metricsz).TOOL_PREFIX and TOOL_SEPARATOR.X‑BW‑* headers.Q: Do I need to install the Bitwarden CLI separately?
A: No. The server bundles a vetted @bitwarden/cli version. You can also point BW_BIN to a custom binary or install it globally.
Q: How are credentials protected in HTTP mode?
A: They travel in custom X‑BW‑* headers; you should bind the server to localhost, use TLS, or place it behind an authenticated reverse proxy.
Q: Can I run the server in a Docker container? A: Yes. Use the official image:
docker run --rm -p 127.0.0.1:3005:3005 -v warden-mcp-data:/data ghcr.io/icoretech/warden-mcp:latest
Q: What if I need read‑only access only?
A: Set READONLY=true or KEYCHAIN_READONLY=true to hide mutating tools and reject write calls.
Q: How do I disable secret revelation?
A: Enable NOREVEAL=true or KEYCHAIN_NOREVEAL=true; all tools will return redacted values unless the client explicitly overrides.
Q: Is there a way to limit memory usage?
A: Adjust KEYCHAIN_MAX_HEAP_USED_MB; set to 0 to disable the fuse.
Q: Where are the per‑profile Bitwarden states stored?
A: Under ${HOME}/bw‑profiles by default (KEYCHAIN_BW_HOME_ROOT). Secure this directory.
Q: Are there any known limitations? A: Search does not cover custom field values; SSH keys are stored as secure notes; export/import features are intentionally omitted.
Q: How can I contribute?
A: Run npm run lint and appropriate test commands, then open a PR. See CONTRIBUTING.md for details.
Vaultwarden / Bitwarden MCP server for credential-aware AI agents.
warden-mcp lets MCP clients search, create, update, move, and read
Vaultwarden or Bitwarden vault items through the official Bitwarden CLI (bw).
It is built for agents and automation that need credentials, TOTP codes, secure
notes, attachments, Sends, folders, organizations, and collections without
re-implementing Bitwarden client-side crypto.
Use it when an agent needs to log in to real systems during a browser or admin workflow, but you do not want passwords hardcoded in prompts, config files, or one-off scripts.
Use stdio mode when a local MCP host launches the server directly. It is the simplest and most portable setup for desktop agents.
Prerequisites:
Run the server:
BW_HOST=https://vaultwarden.example.com \
BW_CLIENTID=user.xxxxx \
BW_CLIENTSECRET=xxxxx \
BW_PASSWORD='your-master-password' \
npx -y @icoretech/warden-mcp@latest --stdio
Username login also works:
BW_HOST=https://vaultwarden.example.com \
BW_USER=user@example.com \
BW_PASSWORD='your-master-password' \
npx -y @icoretech/warden-mcp@latest --stdio
If the package is useful, star the repository so other agent builders can find it.
Most local hosts should use stdio. The examples below use API-key auth; replace
BW_CLIENTID and BW_CLIENTSECRET with BW_USER if you prefer username login.
claude mcp add-json warden '{"command":"npx","args":["-y","@icoretech/warden-mcp@latest","--stdio"],"env":{"BW_HOST":"https://vaultwarden.example.com","BW_CLIENTID":"user.xxxxx","BW_CLIENTSECRET":"xxxxx","BW_PASSWORD":"your-master-password"}}'
codex mcp add warden \
--env BW_HOST=https://vaultwarden.example.com \
--env BW_CLIENTID=user.xxxxx \
--env BW_CLIENTSECRET=xxxxx \
--env BW_PASSWORD='your-master-password' \
-- npx -y @icoretech/warden-mcp@latest --stdio
Codex TOML config:
[mcp_servers.warden]
command = "npx"
args = ["-y", "@icoretech/warden-mcp@latest", "--stdio"]
startup_timeout_sec = 30
[mcp_servers.warden.env]
BW_HOST = "https://vaultwarden.example.com"
BW_CLIENTID = "user.xxxxx"
BW_CLIENTSECRET = "xxxxx"
BW_PASSWORD = "your-master-password"
startup_timeout_sec = 30 gives npx enough time for a cold first launch.
{
"mcpServers": {
"warden": {
"command": "npx",
"args": ["-y", "@icoretech/warden-mcp@latest", "--stdio"],
"env": {
"BW_HOST": "https://vaultwarden.example.com",
"BW_CLIENTID": "user.xxxxx",
"BW_CLIENTSECRET": "xxxxx",
"BW_PASSWORD": "your-master-password"
}
}
}
}
Common locations:
| Host | Config file |
|---|---|
| Cursor | ~/.cursor/mcp.json or .cursor/mcp.json |
| Claude Desktop | ~/Library/Application Support/Claude/claude_desktop_config.json |
| Codex | ~/.codex/config.toml |
reveal: true and the client explicitly asks for itX-BW-* headersstructuredContentbw auth/session flows, not only mocked SDK behaviorwarden-mcp shells out to bw and keeps profile state under
KEYCHAIN_BW_HOME_ROOT. In HTTP mode, profile selection and credentials come
from request headers. In stdio mode, credentials are loaded from BW_* env vars
when the process starts.
The HTTP server exposes:
| Endpoint | Purpose |
|---|---|
GET /healthz |
liveness check; does not validate vault credentials |
GET /metricsz |
session and runtime guardrail metrics |
/sse?v=2 |
MCP Streamable HTTP endpoint |
HTTP mode is useful when one service should serve multiple clients or multiple vault profiles.
Start the server:
npx -y @icoretech/warden-mcp@latest
Verify liveness:
curl -fsS http://localhost:3005/healthz
MCP tool calls must include these headers unless env fallback is explicitly enabled:
| Header | Meaning |
|---|---|
X-BW-Host |
HTTPS origin only, for example https://vaultwarden.example.com |
X-BW-Password |
master password used to unlock the vault |
X-BW-ClientId |
Bitwarden API key client id |
X-BW-ClientSecret |
Bitwarden API key client secret |
X-BW-User or X-BW-Username |
username/email alternative to API key login |
X-BW-Unlock-Interval |
optional unlock interval in seconds; default 300 |
Example HTTP MCP config for hosts that support custom headers:
{
"mcpServers": {
"warden": {
"url": "http://localhost:3005/sse?v=2",
"headers": {
"X-BW-Host": "https://vaultwarden.example.com",
"X-BW-ClientId": "user.xxxxx",
"X-BW-ClientSecret": "xxxxx",
"X-BW-Password": "your-master-password"
}
}
}
}
Some browser-hosted MCP clients can connect to an HTTP/SSE endpoint but cannot
send custom X-BW-* headers. For those clients, run a single-tenant HTTP server
with env fallback:
BW_HOST=https://vaultwarden.example.com \
BW_CLIENTID=user.xxxxx \
BW_CLIENTSECRET=xxxxx \
BW_PASSWORD='your-master-password' \
KEYCHAIN_ALLOW_ENV_FALLBACK=true \
npx -y @icoretech/warden-mcp@latest
Only use KEYCHAIN_ALLOW_ENV_FALLBACK=true behind a trusted network boundary.
Every client that can reach the endpoint inherits the configured vault identity.
For hosted clients that require HTTPS, put a reverse proxy, private tunnel, VPN,
or equivalent protected endpoint in front of warden-mcp, then connect to:
https://warden-mcp.example.com/sse?v=2
docker run --rm \
-p 127.0.0.1:3005:3005 \
-v warden-mcp-data:/data \
ghcr.io/icoretech/warden-mcp:latest
The production image runs as the non-root node user with uid/gid 1000, sets
HOME=/data, and stores Bitwarden profile state under /data/bw-profiles by
default. If you use a bind mount, make it writable by uid/gid 1000.
warden-mcp requires Node.js 22.x and npm 10.x when running from npm or source.
The Docker image includes the supported Node runtime.
The server resolves bw in this order:
BW_BIN, when set@bitwarden/cli dependencybw from PATHThe bundled @bitwarden/cli version is currently 2026.8.0. This project keeps
that version vetted instead of blindly tracking every upstream release, because
auth and unlock behavior can change in ways that break automation.
If bw is missing, install the CLI explicitly or point BW_BIN to a known
binary:
npm install -g @bitwarden/cli@2026.8.0
BW_BIN=/absolute/path/to/bw npx -y @icoretech/warden-mcp@latest --stdio
There is no built-in authentication layer in v1. Protect the transport before you expose it.
WARDEN_MCP_HOST=127.0.0.1, Docker
-p 127.0.0.1:3005:3005, a firewall, VPN, or an authenticated reverse proxyX-BW-* headers carry vault credentialsKEYCHAIN_ALLOW_ENV_FALLBACK=true
makes server-side vault credentials available to headerless clientsREADONLY=true or
KEYCHAIN_READONLY=true hides mutating tools and rejects direct write callsNOREVEAL=true or
KEYCHAIN_NOREVEAL=true forces all secret-returning tools to stay redactedKEYCHAIN_DEBUG_BW or
KEYCHAIN_DEBUG_HTTP unless actively troubleshootingKEYCHAIN_BW_HOME_ROOT, which stores
local bw profile state/metricsz if needed - it is unauthenticated for scraper
compatibility and exposes runtime/session countersRedacted fields include login passwords, TOTP seeds/codes, card numbers and codes, identity SSNs/passport/license numbers, hidden custom fields, SSH private keys stored through the secure-note convention, signed attachment URLs, and password history entries.
| Variable | Default | Purpose |
|---|---|---|
PORT |
3005 |
HTTP listen port |
WARDEN_MCP_HOST |
all interfaces | HTTP bind host |
WARDEN_MCP_STDIO |
false |
force stdio mode without --stdio |
MCP_APP_NAME |
keychain-mcp |
advertised MCP server name |
TOOL_PREFIX |
keychain |
public tool namespace |
TOOL_SEPARATOR |
_ |
public tool separator; set . for legacy clients |
KEYCHAIN_BW_HOME_ROOT |
${HOME}/bw-profiles |
root for per-profile bw state |
KEYCHAIN_ALLOW_ENV_FALLBACK |
false |
allow HTTP calls to inherit server BW_* env |
KEYCHAIN_SYNC_ON_WRITE |
true |
run bw sync before write operations |
READONLY / KEYCHAIN_READONLY |
false |
hide and reject mutating tools |
NOREVEAL / KEYCHAIN_NOREVEAL |
false |
force reveal: false server-side |
KEYCHAIN_TEXT_COMPAT_MODE |
unset | set structured_json for text-only clients |
KEYCHAIN_SESSION_MAX_COUNT |
32 |
max tracked HTTP sessions |
KEYCHAIN_SESSION_TTL_MS |
900000 |
inactive session TTL |
KEYCHAIN_SESSION_SWEEP_INTERVAL_MS |
60000 |
session cleanup interval |
KEYCHAIN_MAX_HEAP_USED_MB |
1536 |
memory fuse; set 0 to disable |
KEYCHAIN_METRICS_LOG_INTERVAL_MS |
0 |
periodic metrics logging; 0 disables |
KEYCHAIN_TEXT_COMPAT_MODE=structured_json mirrors supported
structuredContent into plain text. That helps MCP clients that only pass
content[] to the model, but any revealed secret will also appear in the text
transcript.
Tool names default to keychain_*. Change the prefix with TOOL_PREFIX and the
separator with TOOL_SEPARATOR.
Start with these:
keychain_status - inspect raw bw statuskeychain_sync - pull latest vault data with bw synckeychain_search_items - find items by name, URI, username, folder,
collection, or typekeychain_get_item - read a full item by id, redacted by defaultkeychain_get_username, keychain_get_password, keychain_get_totp - fetch
common login values; password and TOTP require reveal: truekeychain_create_login, keychain_update_item,
keychain_move_item_to_organization - common write pathsFull tool groups:
| Group | Tools |
|---|---|
| Vault/session | keychain_status, keychain_sync, keychain_sdk_version, keychain_encode, keychain_generate, keychain_generate_username |
| Items | keychain_search_items, keychain_get_item, keychain_update_item, keychain_create_login, keychain_create_logins, keychain_set_login_uris, keychain_create_note, keychain_create_card, keychain_create_identity, keychain_create_ssh_key, keychain_delete_item, keychain_delete_items, keychain_restore_item |
| Folders | keychain_list_folders, keychain_create_folder, keychain_edit_folder, keychain_delete_folder |
| Organizations and collections | keychain_list_organizations, keychain_list_collections, keychain_list_org_collections, keychain_create_org_collection, keychain_edit_org_collection, keychain_delete_org_collection, keychain_move_item_to_organization |
| Attachments | keychain_create_attachment, keychain_delete_attachment, keychain_get_attachment |
| Sends | keychain_send_list, keychain_send_template, keychain_send_get, keychain_send_create, keychain_send_create_encoded, keychain_send_edit, keychain_send_remove_password, keychain_send_delete, keychain_receive |
Direct bw get helpers |
keychain_get_username, keychain_get_password, keychain_get_totp, keychain_get_notes, keychain_get_uri, keychain_get_exposed, keychain_get_folder, keychain_get_collection, keychain_get_organization, keychain_get_org_collection, keychain_get_password_history |
Notes:
keychain_create_logins creates several independent login items in one call
and reports per-item failures without aborting the whole batchkeychain_set_login_uris replaces or merges a login item's URI list without
editing the entire item payloadkeychain_delete_items supports bulk soft-delete or hard-delete by idkeychain_get_item exposes safe attachment metadata, including id,
fileName, and size, while redacting signed download URLskeychain_get_attachment accepts an attachment id or an unambiguous filename
and returns { filename, bytes, contentBase64 }keychain_send_get returns owned Send metadata and text content; use
keychain_receive with a Send accessUrl to receive shared Sends or download
file Send bytesAMBIGUOUS_LOOKUP with visible candidate ids;
retry with the exact item idUse Docker Compose when you need the full Vaultwarden-backed stack.
cp .env.example .env
make up
make up starts local Vaultwarden, an HTTPS proxy for bw, bootstraps a test
account, and runs the MCP server in the foreground.
Useful commands:
| Command | Purpose |
|---|---|
npm run dev |
watch-mode server from source |
npm run build |
compile TypeScript to dist/ |
npm run start |
run the compiled server |
npm run lint |
Biome autofix plus tsc --noEmit |
npm run test |
build, then run all compiled tests |
npm run test:integration |
build, then run compose-backed integration tests |
npm run test:coverage |
build, then run Node test coverage |
make test |
run the compose-backed Vaultwarden integration path |
make test-org |
run the organization-focused compose stack |
make down |
stop the local compose stack |
For a quick live MCP smoke against local Vaultwarden, see agent-instructions/testing.md.
Vaultwarden is the continuously proven target in CI. Official Bitwarden compatibility is intended, but it is not continuously proven without a real Bitwarden tenant.
@bitwarden/cli upgrades are treated as compatibility decisions. The suite
checks direct bw auth behavior, SDK behavior, and MCP integration behavior
against a local Vaultwarden instance before a CLI bump should ship.
bw list items --search, and therefore keychain_search_items, does not
reliably search inside custom field valuesbw supports
native SSH key item creationbw features such as export/import are intentionally not exposedkeychain_get_exposed@icoretech/warden-mcpghcr.io/icoretech/warden-mcpIssues and PRs are welcome. Run npm run lint and the relevant test command
before opening a PR; use make test when behavior depends on real Vaultwarden
or bw interaction.
Please log in to share your review and rating for this MCP.
Explore related MCPs that share similar capabilities and solve comparable challenges
by chaitin
A self‑hosted web application firewall and reverse proxy that protects web applications from attacks and exploits by filtering, monitoring, and blocking malicious HTTP/S traffic.
by snyk
Scans installed AI agent components, MCP servers, and skill files for prompt‑injection, tool poisoning, toxic flows, hard‑coded secrets and other supply‑chain risks.
by OpenOSINT
Provides an AI‑driven OSINT workflow that lets users query a natural‑language REPL, CLI, web UI, or MCP server, automatically selecting and chaining 18 reconnaissance tools to collect, pivot, verify, and report public‑source intelligence.
by 2akouwu
Provides deterministic verification of AI‑generated claims against binary artifacts, ensuring every structural or behavioral assertion is grounded in the actual file and preserving verified state across context resets.
by safedep
Provides enterprise‑grade open source software supply chain security by scanning source code, dependencies, containers and SBOMs, detecting vulnerabilities and malicious packages, and enforcing policy as code.
by tufantunc
Provides controlled SSH access for LLM agents with command classification, policy‑based authorization, human‑in‑the‑loop approval, and immutable audit logging.
by semgrep
Offers an MCP server that lets LLMs, agents, and IDEs run Semgrep scans to detect security vulnerabilities in source code.
by KeyValueSoftwareSystems
Enables adversary emulation for AI agents, LLM applications, and MCP servers, letting teams test their AI systems against realistic attack scenarios.
by PortSwigger
Enables Burp Suite to communicate with AI clients via the Model Context Protocol, providing an MCP server and bundled stdio proxy.
{
"mcpServers": {
"warden": {
"command": "npx",
"args": [
"-y",
"@icoretech/warden-mcp@latest",
"--stdio"
],
"env": {
"BW_HOST": "https://vaultwarden.example.com",
"BW_CLIENTID": "user.xxxxx",
"BW_CLIENTSECRET": "xxxxx",
"BW_PASSWORD": "<YOUR_MASTER_PASSWORD>"
}
}
}
}claude mcp add warden npx -y @icoretech/warden-mcp@latest --stdio