SIGIL Registry API

Community-curated DID resolution, scanner patterns, and security policies for the SIGIL Protocol — live at registry.sigil-protocol.org.

Status
Verified Patterns
Security Policies
fra Region (EU 🇪🇺)
TLS 1.3 Transport

Overview

The SIGIL Registry is a public REST API serving three distinct purposes:

Surface Description Auth required
DID Registry Register and resolve did:sigil: identifiers to Ed25519 public keys per SIGIL Spec §7. None for reads; challenge-response for writes (planned)
Scanner Patterns Community-submitted regex patterns for detecting PII, credentials, and secrets in MCP tool responses. Ed25519 signature (author's did:sigil:) for writes
Security Policies Community-submitted risk classifications for MCP tool names (e.g. execute_sql → critical). Ed25519 signature for writes

Base URL

https://registry.sigil-protocol.org   # production (Frankfurt, EU)
http://localhost:3100                 # local development

All responses are JSON. The API is CORS-permissive for browser-based integrations.

Authentication

Read endpoints (GET) require no authentication. Write endpoints (POST /patterns, POST /policies, votes) require an Ed25519 signature from a registered did:sigil: private key.

ℹ️

This prevents anonymous spam while keeping the registry publicly readable. Every submission is permanently linked to a verifiable identity.

The canonical message to sign depends on the endpoint — see Signing Submissions below.

Quick Start

Fetch the verified pattern bundle

curl https://registry.sigil-protocol.org/patterns/bundle | jq '.patterns[].name'

Look up security policies for a specific tool

curl "https://registry.sigil-protocol.org/policies?tool_name=execute_sql"

Resolve a DID

curl https://registry.sigil-protocol.org/resolve/did:sigil:mymolt_user_01

DID Registry

GET /resolve/:did
Resolve a did:sigil: identifier to its Ed25519 public key and metadata. Revoked DIDs remain resolvable for 24h per SIGIL Spec §11.3.
curl https://registry.sigil-protocol.org/resolve/did:sigil:mymolt_user_01

# Response
{
  "did": "did:sigil:mymolt_user_01",
  "status": "active",
  "public_key": "MCowBQYDK2VdAyEA...",
  "namespace": "mymolt",
  "label": "MyMolt User 01",
  "created_at": "2026-02-21T12:00:00Z",
  "updated_at": "2026-02-21T12:00:00Z"
}
POST /register
Register a new did:sigil: identifier with an Ed25519 public key. DID must start with did:sigil:.
curl -X POST https://registry.sigil-protocol.org/register \
  -H "Content-Type: application/json" \
  -d '{
    "did": "did:sigil:my_agent_01",
    "public_key": "MCowBQYDK2VdAyEA...",
    "namespace": "my_agent",
    "label": "My Agent v1"
  }'

# Response 201
{
  "did": "did:sigil:my_agent_01",
  "status": "active",
  "message": "DID registered successfully"
}
POST /revoke/:did
Revoke a DID. The key remains resolvable for 24h so in-flight signed messages can still be verified.
curl -X POST https://registry.sigil-protocol.org/revoke/did:sigil:my_agent_01

# Response 200
{
  "did": "did:sigil:my_agent_01",
  "status": "revoked",
  "message": "DID revoked. Key remains resolvable for 24h per SIGIL Spec §11.3."
}

Scanner Patterns

Community-submitted regex patterns for detecting PII, credentials, secrets, and financial data in MCP tool responses. All verified patterns are included in the bundle endpoint consumed by the SIGIL Rust crate and SDKs.

Categories

Category Description Examples
secret Private keys, database URLs, passwords PEM key, DB connection string
credential API keys, tokens, OAuth secrets AWS key, OpenAI key, JWT
pii EU personal data (GDPR Art. 4) Email, phone, national ID
financial Payment data (PCI-DSS, PSD2) IBAN, credit card number
GET /patterns
List all active scanner patterns. Sorted by votes then downloads.
Query param Type Description
category string Filter: secret | pii | credential | financial
verified bool Filter by maintainer-verified status
limit int Max results (default 50, max 200)
offset int Pagination offset
# All verified credential patterns
curl "https://registry.sigil-protocol.org/patterns?category=credential&verified=true"

# Response
{
  "count": 10,
  "offset": 0,
  "patterns": [{
    "id": "550e8400-e29b-...",
    "name": "aws_access_key_id",
    "category": "credential",
    "pattern": "(AKIA|ABIA|ACCA|ASIA)[0-9A-Z]{16}",
    "severity": "critical",
    "replacement_hint": "[SIGIL-VAULT: AWS_KEY_ID]",
    "verified": true,
    "votes_up": 0
  }]
}
GET /patterns/bundle
Download a compiled bundle of all verified patterns for SDK consumption. Increments the download counter on all returned patterns. This is the endpoint used by sigil-protocol Rust crate's RemoteScanner::from_registry().
curl https://registry.sigil-protocol.org/patterns/bundle

# Response — minimal format optimised for SDK parsing
{
  "version": "1",
  "generated_at": "2026-02-21T22:02:17Z",
  "count": 24,
  "patterns": [{
    "name": "aws_access_key_id",
    "category": "credential",
    "pattern": "(AKIA|ABIA|ACCA|ASIA)[0-9A-Z]{16}",
    "severity": "critical",
    "replacement_hint": "[SIGIL-VAULT: AWS_KEY_ID]"
  }, ...]
}
POST /patterns
Submit a new community scanner pattern. Requires a registered did:sigil: and a valid Ed25519 signature. New patterns are verified=false until reviewed by a SIGIL maintainer.
# 1. Build the canonical message to sign:
#    "sigil-registry:pattern:{name}:{category}:{regex}:{author_did}"

# 2. Sign it with your did:sigil: private key (Ed25519)

# 3. Submit
curl -X POST https://registry.sigil-protocol.org/patterns \
  -H "Content-Type: application/json" \
  -d '{
    "name": "stripe_secret_key",
    "description": "Stripe live secret key (sk_live_ prefix)",
    "category": "credential",
    "pattern": "sk_live_[0-9a-zA-Z]{24}",
    "replacement_hint": "[SIGIL-VAULT: STRIPE_KEY]",
    "severity": "critical",
    "author_did": "did:sigil:your_namespace_01",
    "signature": "<base64url Ed25519 signature>"
  }'

# Response 201
{
  "id": "550e8400-...",
  "name": "stripe_secret_key",
  "status": "pending_review",
  "message": "Pattern submitted. It will appear in the bundle once verified by a SIGIL maintainer."
}
POST /patterns/:id/vote
Vote on a pattern. Each did:sigil: can vote once per pattern. Requires Ed25519 signature.
# Sign: "sigil-registry:vote:pattern:{id}:{up|down}:{voter_did}"

curl -X POST https://registry.sigil-protocol.org/patterns/550e8400-.../vote \
  -H "Content-Type: application/json" \
  -d '{
    "voter_did": "did:sigil:your_namespace_01",
    "vote": "up",
    "signature": "<base64url Ed25519 signature>"
  }'

Submissions are permanently linked to your did:sigil: identity via Ed25519 signature. Your private key never leaves this browser.

Security Policies

Community-curated risk classifications for MCP tool names. These mirror the built-in SecurityPolicy::default() rules in the sigil-protocol Rust crate and are used by SIGIL Guard-level servers to auto-enforce tool risk gates.

GET /policies
List all security policies. Most-voted and verified policies appear first.
Query param Type Description
tool_name string Filter by exact MCP tool name
risk_level string low | medium | high | critical
verified bool Only show maintainer-verified policies
# Find the risk classification for execute_sql
curl "https://registry.sigil-protocol.org/policies?tool_name=execute_sql&verified=true"

# Response
{
  "count": 1,
  "policies": [{
    "id": "...",
    "tool_name": "execute_sql",
    "risk_level": "high",
    "requires_trust": "High",
    "requires_confirmation": true,
    "rationale": "DROP, DELETE, or UPDATE without WHERE can cause irreversible data loss...",
    "verified": true
  }]
}
POST /policies
Submit a new tool risk policy. Multiple policies per tool name are allowed — community votes surface the best one.
# Sign: "sigil-registry:policy:{tool_name}:{risk_level}:{requires_trust}:{author_did}"

curl -X POST https://registry.sigil-protocol.org/policies \
  -H "Content-Type: application/json" \
  -d '{
    "tool_name": "call_external_llm",
    "risk_level": "high",
    "requires_trust": "High",
    "requires_confirmation": false,
    "rationale": "Sends user context to an external model. Data exfiltration risk.",
    "author_did": "did:sigil:your_namespace_01",
    "signature": "<base64url Ed25519 signature>"
  }'

Submissions are permanently linked to your did:sigil: identity via Ed25519 signature. Your private key never leaves this browser.

SDK Integration

Rust — sigil-protocol crate

Enable the registry feature to get RemoteScanner, which fetches the latest verified patterns at startup and falls back to built-in patterns if the network is unreachable.

# Cargo.toml
sigil-protocol = { version = "0.1.4", features = ["registry"] }
use sigil_protocol::RemoteScanner;
use sigil_protocol::SensitivityScanner;

// Downloads latest verified patterns from registry.sigil-protocol.org
// Falls back to built-in patterns if registry is unreachable (5s timeout)
let scanner = RemoteScanner::from_registry().await?;

println!("Loaded {} rules from: {:?}", scanner.rule_count(), scanner.source());

// Use anywhere a SensitivityScanner is needed
if let Some(hit) = scanner.scan("key=AKIAIOSFODNN7EXAMPLE") {
    println!("Sensitive content: {hit}");
    // → "Sensitive content: [SIGIL-VAULT: AWS_KEY_ID]"
}

// Self-hosted or local dev registry
let scanner = RemoteScanner::from_url("http://localhost:3100/patterns/bundle").await?;

Raw HTTP — any language

# Python
import requests, re

bundle = requests.get("https://registry.sigil-protocol.org/patterns/bundle").json()
patterns = [(p["name"], re.compile(p["pattern"])) for p in bundle["patterns"]]

def scan(text):
    for name, regex in patterns:
        if regex.search(text):
            return name
    return None

Signing Submissions

All write operations (submit pattern, submit policy, vote) require an Ed25519 signature from the registered private key corresponding to your did:sigil:. The registry verifies the signature using the public key stored in the DID table.

Canonical message formats

Operation Message to sign
Submit pattern sigil-registry:pattern:{name}:{category}:{regex}:{author_did}
Submit policy sigil-registry:policy:{tool_name}:{risk_level}:{requires_trust}:{author_did}
Vote sigil-registry:vote:{pattern|policy}:{target_id}:{up|down}:{voter_did}

Example — signing in Rust

use ed25519_dalek::{SigningKey, Signer};
use base64::{engine::general_purpose::URL_SAFE_NO_PAD, Engine};

// Load your did:sigil: private key
let signing_key = SigningKey::from_bytes(&your_32_byte_private_key);

// Build canonical message
let name = "stripe_secret_key";
let msg = format!("sigil-registry:pattern:{name}:credential:sk_live_...:did:sigil:my_ns_01");

// Sign and base64url-encode
let sig = signing_key.sign(msg.as_bytes());
let sig_b64 = URL_SAFE_NO_PAD.encode(sig.to_bytes());
⚠️

Your private key never leaves your machine. The registry only sees the public key (registered in the DID table) and the signature. If your key is compromised, immediately revoke the DID and re-register with a new keypair.

Error Reference

Status Error Cause
400 Validation error Invalid category, severity, or tool_name format
400 Invalid vote Vote must be "up" or "down"
401 Invalid signature Signature does not verify against the author's public key
403 Author DID not registered The author_did is not in the DID registry or is revoked
404 Not found DID or resource ID not found
409 Conflict DID already registered, pattern name taken, or already voted
422 Validation error Invalid regex pattern (tested before storing)