MCP server that lets AI agents use NIGHTGATE, the Midnight blockchain attestation layer: anchor documents, prove zero-knowledge predicates over hidden fields, manage disclosure grants, verify everything against live contract state, and poll async jobs. Wallet lifecycle (connect, send, deploy) is deliberately not exposed.
- Node.js >= 20
- A running NIGHTGATE instance (>= 0.15.0 for the full tool set; 0.14.0 works without the equality/membership tools)
The fastest way is the official Docker image; no Node setup, no host app
(published from the NIGHTGATE repo on every release, details in its
docs/docker.md):
docker run -d --name nightgate -p 4004:4004 \
-e ENCRYPTION_KEY=$(openssl rand -hex 32) \
-e NIGHTGATE_HTTP_PASSWORD=change-me \
-v nightgate-data:/data \
ghcr.io/odatano/nightgate:latestThat container targets Midnight preprod by default, serves with HTTP basic
auth (nightgate / your password), persists its database in the
nightgate-data volume, and proves in-process (wasm), so no proof server
is needed to start. Point this MCP server at it with:
NIGHTGATE_BASE_URL=http://localhost:4004
NIGHTGATE_USERNAME=nightgate
NIGHTGATE_PASSWORD=change-meFor agent operation, create a scoped grant once (as the operator, e.g. via
curl against createAgentGrant) and hand the returned ngat_... token to
the agent as NIGHTGATE_TOKEN; the write tools are then limited to the
grant's allowlist, budget and pinned session.
Alternatively any CAP app using the @odatano/nightgate plugin works,
e.g. the NIGHTGATE repo itself via npm run dev.
npm install
npm run buildConfiguration is environment-driven:
| Variable | Default | Purpose |
|---|---|---|
NIGHTGATE_BASE_URL |
http://localhost:4004 |
NIGHTGATE host app |
NIGHTGATE_USERNAME / NIGHTGATE_PASSWORD |
unset | Basic auth (CAP dev/mocked auth) |
NIGHTGATE_TOKEN |
unset | ngat_... agent-grant token (sent as x-agent-token, combinable with basic auth) or a plain bearer token |
NIGHTGATE_SERVICE_PATH |
/api/v1/nightgate |
OData service path |
NIGHTGATE_TIMEOUT_MS |
30000 |
Per-request timeout |
claude mcp add nightgate \
--env NIGHTGATE_BASE_URL=http://localhost:4004 \
--env NIGHTGATE_USERNAME=alice \
-- node /path/to/NIGHTGATE-MCP/dist/index.jsOr in a project .mcp.json:
{
"mcpServers": {
"nightgate": {
"command": "node",
"args": ["/path/to/NIGHTGATE-MCP/dist/index.js"],
"env": {
"NIGHTGATE_BASE_URL": "http://localhost:4004",
"NIGHTGATE_USERNAME": "alice"
}
}
}
}| Tool | What it does |
|---|---|
verify_attestation |
Live-state check that a payload hash is attested in an AttestationVault (crawler-free, optional content-root check, optional cross-network read) |
verify_predicate |
Live-state check that a ZK claim was recorded true on-chain, id-free: numeric predicates, bytesEquality (+ expectedDigest) and setMembership (+ setRoot) |
verify_predicate_attestation |
Verify a server-issued predicate attestation by its row id |
verify_document |
Verify an anchored document by document id + sha256 |
prepare_document_proof |
Canonicalize a document into payloadHash + Merkle contentRoot + per-field proof inputs, numeric and kind: "bytes" string fields (synchronous, NIGHTGATE >= 0.14.0; bytes kind >= 0.15.0) |
prepare_membership_set |
Build the canonical allow-list set tree: setRoot for verifiers, inclusion path for provers (synchronous, NIGHTGATE >= 0.15.0) |
attest_agent_output |
Anchor agent-output provenance (canonical envelope, third-party verifiable; async job, NIGHTGATE >= 0.14.0) |
anchor_document |
Anchor a document content hash on-chain (async job) |
prove_field_predicate |
ZK proof that a hidden document field satisfies a threshold, without revealing it (async job) |
prove_field_equality |
ZK proof that a string field carries exactly the value behind a public digest (async job, NIGHTGATE >= 0.15.0) |
prove_field_membership |
ZK proof that a hidden string field is one of a public allow-list, without revealing which (async job, NIGHTGATE >= 0.15.0) |
prove_field_predicates_batch |
Up to 8 field claims on one document in ONE transaction, any mix of numeric / equality / membership (async job) |
grant_disclosure / revoke_disclosure |
Attester-only on-chain disclosure ACL (async jobs) |
get_job_status |
Poll an async NIGHTGATE job until succeeded/failed |
All verification tools return verified: false as a clean negative rather
than an error when the attestation or proof is absent. Write tools require
a connected wallet session (sessionId); creating sessions stays outside
MCP by design.
npm run integrationRuns an in-memory MCP client against the server: asserts the tool set, schemas, and argument validation. Optional live round-trip:
NIGHTGATE_LIVE=1 NIGHTGATE_BASE_URL=... NIGHTGATE_USERNAME=... \
NIGHTGATE_TEST_CONTRACT=<vault address> NIGHTGATE_TEST_PAYLOAD_HASH=<64 hex> \
npm run integrationApache-2.0