unlock-mcp
Read-only MCP server for inspecting Unlock Protocol on-chain state — no writes, signing, or private keys.
Check membership: Verify whether a wallet holds a valid (non-expired) key for a specific Unlock Protocol lock, returning expiration, tokenId, lock name, and network.
Get lock details: Read a lock's public shape directly from the chain — name, symbol, PublicLock version, key price/currency, expiration duration, max keys, and total keys sold.
List keys: Enumerate all keys a wallet holds across locks on a network via Unlock's subgraph, optionally including expired/cancelled keys, sorted by expiration and capped at 100.
Read-only & live: All values are fetched at call time; malformed or non-lock addresses return clear classification results rather than raw errors.
Network support: Currently configured for Base, with RPC fallback chains and environment-variable overrides for RPC and subgraph endpoints.
Click on "Install Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@unlock-mcpDoes 0x1234...abcd have a valid key for lock 0xabcd...efgh on Base?"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
unlock-mcp
Read-only MCP server exposing Unlock Protocol on-chain state. No private keys, no signing, no write calls — every tool only reads from the chain.
Install
Claude Desktop
Add to your claude_desktop_config.json:
{
"mcpServers": {
"unlock": {
"command": "npx",
"args": ["-y", "unlock-mcp"]
}
}
}Claude Code
claude mcp add unlock -- npx -y unlock-mcpLocal development
If you're working on the server itself, point either of the above at a local checkout instead:
{
"mcpServers": {
"unlock": {
"command": "node",
"args": ["/absolute/path/to/unlock-mcp/dist/index.js"]
}
}
}Related MCP server: Vaultfire MCP Server
Tools
unlock_check_membership
Checks whether a wallet holds a valid (non-expired) key for an Unlock Protocol lock.
Input | Type | Required | Description |
|
| yes | The PublicLock contract to check |
|
| yes | The wallet to check for a key |
| string | no | Defaults to |
Returns whether the wallet holds a valid key, and if so its expiration (ISO timestamp and a relative form like "in 2 years"), the tokenId, the lock name, and the network.
keyExpirationTimestampFor changed signature across PublicLock versions — locks below
publicLockVersion 10 take a key owner address, version 10 and up take a tokenId. The
tool reads publicLockVersion() and calls whichever form the lock actually implements.
Distinct, plain-language results are returned for: a lock address that isn't a contract, a contract that isn't a PublicLock, a wallet with no key, and a wallet with an expired or valid key. These are all normal results, not errors — a definitive answer about the chain isn't a tool failure. The tool only reports an error for cases it genuinely can't answer: an unreachable/rate-limited RPC endpoint, or malformed input. No raw RPC error or revert reason is ever passed through.
Every value is read live from the chain at call time — including name() — so it
reflects current on-chain state, not a block explorer's indexed snapshot (a lock's
name is only set once at deploy time in most explorer UIs, but can change on-chain
afterward; this tool always reads the current value).
unlock_get_lock
Reads a lock's public shape directly from the chain via RPC (not the subgraph — this is point-in-time state, and the RPC path already exists).
Input | Type | Required | Description |
|
| yes | The PublicLock contract to read |
| string | no | Defaults to |
Returns name, symbol, address, network, PublicLock version, key price (amount, raw
value, and currency — the token's own symbol/decimals for an ERC-20, or the chain's
native currency if the lock's tokenAddress() is the zero address), expiration
duration in both seconds and human-readable form, max number of keys, and total keys
sold (totalSupply(), a running counter of every key ever created — not the current
valid supply).
expirationDuration and maxNumberOfKeys each use a max-uint256 sentinel for
"unlimited" (never-expiring keys, or no cap on keys respectively) — the tool reports
those explicitly as unlimited: true rather than surfacing the raw sentinel as a
number.
Lock managers are deliberately not included: PublicLock exposes no enumerable
getter for that role (it uses a plain OpenZeppelin AccessControl role, not
AccessControlEnumerable) — only isLockManager(address), a point check against an
address you'd already have to know. Getting the actual list would mean either
replaying RoleGranted/RoleRevoked logs from deployment (not a cheap RPC read) or
asking the subgraph, which this tool intentionally avoids so it stays pure on-chain
state. Same three classification results as unlock_check_membership apply here for
a bad address: not a contract, not a PublicLock, or a working lock.
unlock_list_keys
Lists every key a wallet holds across locks on a network, via Unlock's subgraph — enumerating a wallet's keys across all locks isn't something RPC can do without already knowing which locks to look at.
Input | Type | Required | Description |
|
| yes | The wallet to list keys for |
| string | no | Defaults to |
| boolean | no | Include expired/cancelled keys too (default |
Returns, per key: lock address, lock name, tokenId, expiration (ISO timestamp, or
"never" for a lifetime key), and whether it's currently valid. Results are sorted by
expiration descending and capped at 100, with a note in the response if the cap was
hit. A wallet holding no keys is a normal empty result, not an error.
Networks
Chains are configured as data in src/networks.ts — adding one is a new object, not a
code change. Only Base is configured today.
The Base Unlock factory address was cross-checked against
unlock-protocol/unlock
(packages/networks/src/networks/base.ts) directly, since @unlock-protocol/networks
on npm hasn't been republished since 0.0.25 (Dec 2024). As of this check, the two
still agree — no divergence found.
RPC endpoints
Each network has a primary RPC and one or more fallbacks, tried in order — a failure
on one (timeout, connection error, rate limit) automatically retries on the next. Base
defaults to Unlock's own public RPC (rpc.unlock-protocol.com), falling back to the
public Base RPC (mainnet.base.org).
To override the endpoints tried for a given network, set
UNLOCK_MCP_RPC_URL_<NETWORK> (uppercased network name), e.g.:
UNLOCK_MCP_RPC_URL_BASE=https://your-rpc.example.comThe override is tried first; the built-in defaults remain as fallbacks behind it.
Subgraph endpoint
unlock_list_keys reads from Unlock's public subgraph, one endpoint per network
(no fallback chain, since there's only one). To override it for a given network, set
UNLOCK_MCP_SUBGRAPH_URL_<NETWORK> (uppercased network name), e.g.:
UNLOCK_MCP_SUBGRAPH_URL_BASE=https://your-subgraph.example.comDevelopment
npm install
npm run build
npm testMaintenance
Related MCP Servers
FlicenseAqualityBmaintenanceA server that exposes blockchain data (balances, tokens, NFTs, contract metadata) via the Model Context Protocol, enabling AI agents and tools to access and analyze blockchain information contextually.1844- AlicenseAqualityCmaintenanceProvides on-chain trust verification for AI agents through the Vaultfire Protocol, enabling read-only trust checks and write operations like agent registration and partnership bonds across multiple blockchains.7121MIT

Noves MCP Serverofficial
AlicenseBqualityDmaintenanceEnables AI assistants to access and explain blockchain data across 100+ networks using natural language, without requiring authentication.923MIT- AlicenseAqualityBmaintenanceThe only MCP server that gives AI agents native access to Stacks, Celo, and Base — from a single npm package.5391MIT
Related MCP Connectors
Provide AI agents and automation tools with contextual access to blockchain data including balance…
Read-only on-chain intelligence for AI agents on Base: balances, tokens, gas, tx status.
Read-only on-chain intel for AI agents on Base: balances, tokens, gas, tx status. No API keys.
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/wkalidev/unlock-mcp'
If you have feedback or need assistance with the MCP directory API, please join our Discord server