Speedmap Connect (MCP server)
The first identity MCP server designed so a NIN never enters an AI context window. Verify from Claude, ChatGPT, Cursor and VS Code.
Speedmap Connect is a Model Context Protocol server that lets AI assistants and agents run Speedmap checks on your behalf: a compliance officer reconciling KYC without leaving the chat, a developer wiring verification into an agent from the editor, a bulk job dispatched conversationally.
It uses the same API keys, entitlements, consent rules and billing as the REST API. What changes is what comes back: assertions only. Tools return verified, match, masked names and risk scores, never the NIN, BVN or identity record, so personal data does not land in a model's context, logs or training data.
The remote server speaks Streamable HTTP and is stateless: every request is a POST carrying your key, and no session is kept. Nothing to install.
Authenticate with your Speedmap key as a bearer token, Authorization: Bearer sk_test_.... Use a sandbox key while you evaluate: test data, no billing. Requests count against the same per-key rate limit as the REST API.
For clients that only run local (stdio) servers, the @speedmap/mcp package bridges to the remote server. It needs Node.js 20 or later and reads your key from SPEEDMAP_API_KEY:
SPEEDMAP_API_KEY=sk_test_... \
SPEEDMAP_MCP_URL=http://localhost:4000/mcp \
npx -y @speedmap/mcpclaude mcp add --transport http speedmap http://localhost:4000/mcp \
--header "Authorization: Bearer sk_test_..."Add the server to claude_desktop_config.json (Settings → Developer → Edit config), then restart Claude Desktop.
{
"mcpServers": {
"speedmap": {
"command": "npx",
"args": [
"-y",
"@speedmap/mcp"
],
"env": {
"SPEEDMAP_API_KEY": "sk_test_...",
"SPEEDMAP_MCP_URL": "http://localhost:4000/mcp"
}
}
}
}Turn on developer mode (Settings → Connectors → Advanced), then add a custom connector:
- Server URL:
http://localhost:4000/mcp - Authentication: API key, sent as a bearer token. Paste your
sk_test_key. - Enable the connector in a chat and ask it to verify a test identity.
Add the server to ~/.cursor/mcp.json for every project, or .cursor/mcp.json in one project.
{
"mcpServers": {
"speedmap": {
"url": "http://localhost:4000/mcp",
"headers": {
"Authorization": "Bearer sk_test_..."
}
}
}
}Add .vscode/mcp.json to your workspace. The inputs entry makes VS Code prompt for the key and store it securely instead of keeping it in the file.
{
"inputs": [
{
"type": "promptString",
"id": "speedmap-key",
"description": "Speedmap API key",
"password": true
}
],
"servers": {
"speedmap": {
"type": "http",
"url": "http://localhost:4000/mcp",
"headers": {
"Authorization": "Bearer ${input:speedmap-key}"
}
}
}
}Any client that supports remote MCP servers over Streamable HTTP works: point it at the URL above with the Authorization header. To check your setup from a terminal:
curl -X POST http://localhost:4000/mcp \
-H "Authorization: Bearer sk_test_..." \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'- Assertions only. No NIN, BVN or identity record is returned to the model. Results carry a
dashboard_urlwhere authorized staff can see more. - Purpose is constrained.
reasonis an enum of the 38 NIMC purpose codes in every tool schema. An agent cannot invent one, and the server instructions tell it to ask the user when the purpose is unclear. - Consent first. Tools that touch personal data require
consent_obtained: true, which the assistant may set only after the user confirms consent. Consent is checked before any provider is called, exactly as on the REST API. - Bulk never returns rows.
bulk_verifyreturns a job id and a dashboard link. A developer cannot pull 10,000 records into a chat. - Registry text is data, not instructions. Text from registries (company names, provider messages) is stripped of control and invisible characters and length-capped before it reaches the model.
- Errors do not leak. Tool errors carry Speedmap's own error code and a scrubbed message, never provider internals or identifiers.
- Sandbox and live are separate.
sk_test_keys use test data and are free;sk_live_keys reach the live registries (NIMC and NIBSS) and are billed.
Twelve tools. Verification tools return a short sentence for the model plus the same fields as structuredContent.
Verify a Nigerian NIN. Checks an NIN against NIMC. Never returns the identity record.
Returns: reference_id, product, status, match, field_matches, field_confidence, masked subject and summary, mode, dashboard_url.
Input
methodstringnin(raw NIN, financial institutions and government only) orshare_code. Defaults tonin.ninstring11-digit NIN, for method
nin.share_codestringNINAuth share code, for method
share_code.reasonstringrequiredOne of the 38 purpose codes. The assistant must ask if unsure.
consent_obtainedtruerequiredSet only after the user confirms the data subject consented.
first_namestringExpected first name.
last_namestringExpected last name.
date_of_birthstringExpected date of birth,
YYYY-MM-DD.
Verify a BVN. Match / no-match through NIBSS. No PII is returned.
Returns: reference_id, product, status, match, field_matches, field_confidence, masked subject and summary, mode, dashboard_url.
Input
bvnstringrequired11-digit BVN.
reasonstringrequiredOne of the 38 purpose codes. The assistant must ask if unsure.
consent_obtainedtruerequiredSet only after the user confirms the data subject consented.
first_namestringExpected first name.
last_namestringExpected last name.
date_of_birthstringExpected date of birth,
YYYY-MM-DD.
Verify a company (CAC / KYB). Looks up a CAC-registered company by RC number, TIN or exact name.
Returns: Company name, status, type and registration date in summary, plus the fields above. Directors and shareholders need the REST API.
Input
rc_numberstringRC or BN number, e.g.
RC1234567.tinstringTax identification number.
company_namestringExact registered name.
expected_namestringName to check against the register.
Verify a bank account name. NIBSS name enquiry on a 10-digit NUBAN.
Returns: Masked account name, bank name and name_match.
Input
account_numberstringrequired10-digit NUBAN.
bank_codestringrequiredCBN bank code, e.g.
058. Seelist_banks.expected_namestringName you expect on the account.
Face liveness and match. Passive liveness on a selfie, optionally compared with the BVN photo.
Returns: Pass/fail and confidence scores only.
Input
image_urlstringrequiredHTTPS URL of the selfie.
bvnstringCompare against the photo on this BVN.
reasonstringrequiredOne of the 38 purpose codes. The assistant must ask if unsure.
Fraud risk signals. One risk score from SIM swap, BVN changes and the watchlist.
Returns: risk_score, risk_level and factors.
Input
phonestringMobile number.
bvnstring11-digit BVN.
reasonstringrequiredOne of the 38 purpose codes. The assistant must ask if unsure.
consent_obtainedtruerequiredSet only after the user confirms the data subject consented.
Start a bulk job. Queues many checks of one product. Results are never returned into the conversation.
Returns: job_id, status, total and dashboard_url.
Input
productstringrequirednin,bvn,phone,business,accountorsignals.itemsarrayrequired1 to 10,000 request bodies, as for the REST API.
namestringJob label.
Bulk job progress. Progress and outcome counts. Never rows.
Returns: The bulk job: status, processed, total, progress, counts.
Input
job_idstringrequiredFrom
bulk_verify.
Get a verification. Fetches an earlier check, e.g. to resolve a pending one.
Returns: reference_id, product, status, match, masked subject and summary, dashboard_url.
Input
reference_idstringrequiredStarts with
spm_.
Request consent. Creates a consent request the person approves by link, email or USSD.
Returns: consent_id, status, authorization_url, ussd_code, expires_at.
Input
identifier_typestringrequiredbvnornin.identifierstringrequired11-digit BVN or NIN.
categoriesstringY/N mask, default
YYNN.channelstringredirect,emailorussd. Defaultredirect.emailstringFor the email channel.
reasonstringrequiredOne of the 38 purpose codes. The assistant must ask if unsure.
List purpose codes. The 38 NIMC purpose codes accepted as reason.
Returns: One key: label line per code.
No input.
List bank codes. Bank names and CBN codes for verify_account.
Returns: One code: name line per bank.
No input.
Example prompts
With a sandbox key, try:
- "Verify NIN share code SPM001 for a loan application and check the surname is Griffin."
- "Is RC1234567 an active company?"
- "Check whether account 0123456789 at GTBank belongs to Clarke Griffin before we pay her."
- "Run a fraud check on BVN 22222222225 with phone 08099990000."
The machine-readable manifest is at /.well-known/mcp.json.
Questions? Email developers@speedmap.ng. This page is also available as Markdown.