mcp-sanity-check
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., "@mcp-sanity-checkscan staged changes for any secrets"
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.
mcp-sanity-check
A dependency-light CLI that scans a repository's tracked files for owner identifiers and secrets, then exits non-zero if it finds any. Drop it into CI or a pre-push hook and private data cannot ship into a public repo.
What problem it solves
When you maintain a fleet of MCP servers (or any set of personal automation repos) that you plan to publish publicly, a single slip can embed your home IP, email, device hostname, or an API key in the Git history forever. mcp-sanity-check is the last gate before a push or a CI merge — it scans every tracked file and blocks the operation if anything personal is found.
The tool ships with no owner identifiers baked in, so the scanner itself can live in a public repo without leaking anyone's data. Your specific strings (emails, account IDs, home-LAN IPs, device names) stay in ~/.config/mcp-sanity/identifiers.json on your machine and are never committed anywhere.
Related MCP server: credential-free
Install
One-liner via npx (no install needed):
npx -y github:nidamen/mcp-sanity-check-mcp --path /path/to/repoOr install globally:
npm install -g mcp-sanity-check
mcp-sanity-check --path /path/to/repoOr run from a local checkout:
node bin/mcp-sanity-check.mjs --path /path/to/repoRequires Node >= 18. Zero runtime dependencies.
MCP client configuration
This tool runs as a stdio MCP server. Add it to your MCP client config:
{
"mcpServers": {
"mcp-sanity-check": {
"command": "npx",
"args": ["-y", "github:nidamen/mcp-sanity-check-mcp"],
"env": {}
}
}
}To use your private identifier list, set the MCP_SANITY_IDENTIFIERS environment variable to the path of your identifiers.json:
{
"mcpServers": {
"mcp-sanity-check": {
"command": "npx",
"args": ["-y", "github:nidamen/mcp-sanity-check-mcp"],
"env": {
"MCP_SANITY_IDENTIFIERS": "/Users/you/.config/mcp-sanity/identifiers.json"
}
}
}
}CLI usage
mcp-sanity-check [--path <dir>] [--staged] [--range <a..b>] [--json] [--quiet] [--no-color]Flag | Description |
| Directory to scan. Default: current working directory. |
| Scan only staged (index) added lines. For use in a pre-commit hook. |
| Scan only lines added in the given git commit range. Used by pre-push. |
| Emit a machine-readable JSON report. Values are still masked. |
| Suppress per-hit lines; print only the summary. |
| Disable ANSI color. Also honored via the |
Exit codes: 0 = clean, 1 = one or more hits found, 2 = usage error (bad path, etc.).
Complete tool reference
This is a CLI tool, not an MCP tool-calling server. The scanner exposes one capability: scan a directory and report leaks.
mcp-sanity-check (CLI / binary)
Purpose: Scan a repository for owner identifiers and secrets and exit non-zero if any are found.
Modes:
Mode | Trigger flag | What is scanned |
Full scan | (no flag, default) | All git-tracked files, or full directory walk if not a git repo |
Staged scan |
| Only added lines in the git index ( |
Range scan |
| Only added lines in the given commit range |
Input parameters:
Parameter | Type | Required | Default | Description |
| string | No |
| Absolute or relative path to the repo root |
| boolean | No | false | Enable staged-lines-only mode |
| string | No | null | Git commit range string ( |
| boolean | No | false | Emit JSON instead of colored text |
| boolean | No | false | Suppress per-hit lines |
| boolean | No | false | Disable ANSI color codes |
Returns (human mode):
✓ mcp-sanity-check: clean (42 files scanned)or on a hit:
✗ mcp-sanity-check: 2 potential leak(s) found
SECRET config.env:3 github-personal-access-token (ghp_) -> ghp_****...ab
IDENTIFIER src/client.js:7 owner-identifier:you@example.com -> you@****
BLOCKED: 2 hit(s) across 42 files. Remove the values above, ...Returns (JSON mode, --json):
{
"ok": false,
"filesScanned": 42,
"hitCount": 2,
"mode": "full",
"hits": [
{
"file": "config.env",
"line": 3,
"class": "secret",
"pattern": "github-personal-access-token (ghp_)",
"masked": "ghp_****...ab"
}
]
}Fields in each hit object:
Field | Type | Description |
| string | Relative path of the file containing the hit |
| number | 1-indexed line number |
| string |
|
| string | Human-readable name of the rule that matched |
| string | First 4 + last 2 chars of the value; middle replaced with |
What gets flagged
Owner identifiers
Loaded at runtime from (in priority order):
Path in
$MCP_SANITY_IDENTIFIERSenvironment variable (points to a JSON file).~/.config/mcp-sanity/identifiers.json(default private config location).identifiersarray in the scanned repo's.sanity-patterns.json.
The JSON file must be an object with an identifiers array of strings:
{ "identifiers": ["your@email.com", "192.168.1.50", "myhostname", "acct-id-xyz"] }This file is never committed anywhere. It lives only on your machine.
Generic PII (public CI backstop)
Even without a private identifier list, the scanner catches:
Pattern name | What it matches |
| Any |
| 10.x.x.x, 192.168.x.x, 172.16-31.x.x addresses |
|
|
| Six colon-separated hex octets |
Obvious documentation placeholders (you@example.com, 192.168.1.1, /home/user, aa:bb:cc:dd:ee:ff, etc.) are excluded so docs and examples do not trip the backstop.
Secret patterns
Pattern name | Shape matched |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
The high-entropy rule fires only when the assigned value is 40+ characters, base64-ish, and clears a Shannon-entropy threshold (H >= 3.5 bits/char, 12+ distinct characters). This keeps false positives low on long-but-repetitive strings.
All matched values are masked in output: the first 4 and last 2 characters are shown; everything in between is replaced with *.
Private config: ~/.config/mcp-sanity/
The directory ~/.config/mcp-sanity/ is the one place the owner's specific identifiers live. It is:
Never committed (it sits outside any repo).
Never referenced by path in any tracked file.
Loaded at runtime by the scanner binary on the machine where the private list is needed.
Structure:
~/.config/mcp-sanity/
identifiers.json <- {"identifiers": ["your@email.com", "192.168.1.50", ...]}How a repo opts in
Option 1: CI workflow
Copy .github/workflows/sanity-check.yml from this repo into the target repo. It runs on every push and PR using ubuntu-latest + Node 20, fetches the full history, and fails the build on any hit.
It can also be called as a reusable workflow:
jobs:
sanity:
uses: nidamen/mcp-sanity-check/.github/workflows/sanity-check.yml@mainOption 2: Pre-push git hook
Install hooks/pre-push so leaks are blocked before they ever reach the remote. The hook scans only the outgoing commit range, so it is fast.
# Per-repo:
cp /path/to/mcp-sanity-check/hooks/pre-push /path/to/your-repo/.git/hooks/pre-push
chmod +x /path/to/your-repo/.git/hooks/pre-push
# Shared across all repos (global hooks dir):
mkdir -p ~/.git-hooks
cp /path/to/mcp-sanity-check/hooks/pre-push ~/.git-hooks/pre-push
chmod +x ~/.git-hooks/pre-push
git config --global core.hooksPath ~/.git-hooksThe hook resolves the scanner via (in order): $MCP_SANITY_CHECK env var (full path to the .mjs), mcp-sanity-check on PATH, or npx mcp-sanity-check.
To bypass intentionally (not recommended): git push --no-verify.
Per-repo tuning: .sanity-patterns.json
Place a .sanity-patterns.json file at the scanned repo's root to extend or relax the defaults:
{
"identifiers": ["ACME_INTERNAL_CODENAME", "another-owner-string"],
"allow": ["EXAMPLE_PLACEHOLDER"],
"allowFiles": ["docs/sample-output.txt", "test/fixtures/"]
}Key | Type | Effect |
| string array | Added to the runtime identifier list. Case-insensitive substring match. |
| string array | If a flagged line contains any allow-string, the hit is dropped. For known false positives and sample data. |
| string array | File-path substrings: any file whose relative path contains one of these is skipped entirely. Use sparingly, only for files that legitimately define or document the patterns. |
Quick usage examples
Check a repo before publishing:
mcp-sanity-check --path ~/code/my-mcp-serverRun in CI (no color, machine output):
mcp-sanity-check --path . --no-color --json | tee scan-report.jsonCheck only what you are about to commit:
mcp-sanity-check --stagedTests
npm test
# or
node test/run.mjsThe suite creates dirty fixtures in a temp directory (planted identifiers and secrets never live in tracked source), confirms the scanner catches them, confirms the values are masked in output, confirms the allow-list suppresses false positives, and confirms a clean directory exits zero.
Limitations
Scans text files only. Files larger than 5 MB and files with a NUL byte in the first 4 KB are skipped.
Binary file types (images, archives, compiled objects, fonts, audio, video, SQLite, lock files) are skipped by extension.
The high-entropy rule can still produce false positives on long deterministic strings (base64-encoded config blobs, encoded protobuf payloads). Use
allowin.sanity-patterns.jsonto suppress these.Generic PII patterns (email, RFC1918 IP, home path, MAC) are designed to catch leaks in public CI where the private identifier list is unavailable; they may fire on legitimate example values that are not in the placeholder list. Add them to
allowas needed.--stagedand--rangemodes scan only added lines in the diff, not the full file state. A pre-existing leak in unchanged lines is not caught until a full--pathscan is run.Entropy check thresholds (H >= 3.5, distinct >= 12) were tuned empirically; an unusually low-entropy real secret may not be caught by the high-entropy rule (but would still be caught if it matches a named pattern).
License
MIT
This server cannot be installed
Maintenance
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Latest Blog Posts
- 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/nidamen/mcp-sanity-check'
If you have feedback or need assistance with the MCP directory API, please join our Discord server