mcpnuke 6.22.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- mcpnuke-6.22.0/.cursor/rules/mcpnuke-checks.mdc +68 -0
- mcpnuke-6.22.0/.cursor/rules/mcpnuke-development.mdc +87 -0
- mcpnuke-6.22.0/.cursor/rules/mcpnuke-tests.mdc +58 -0
- mcpnuke-6.22.0/.cursor/skills/mcpnuke-add-check/SKILL.md +179 -0
- mcpnuke-6.22.0/.cursor/skills/mcpnuke-add-patterns/SKILL.md +99 -0
- mcpnuke-6.22.0/.cursor/skills/mcpnuke-add-transport/SKILL.md +118 -0
- mcpnuke-6.22.0/.cursor/skills/mcpnuke-extend-dvmcp/SKILL.md +102 -0
- mcpnuke-6.22.0/.cursor/skills/mcpnuke-run-tests/SKILL.md +91 -0
- mcpnuke-6.22.0/.github/ISSUE_TEMPLATE/bug_report.yml +52 -0
- mcpnuke-6.22.0/.github/ISSUE_TEMPLATE/config.yml +5 -0
- mcpnuke-6.22.0/.github/ISSUE_TEMPLATE/detection_report.yml +63 -0
- mcpnuke-6.22.0/.github/PULL_REQUEST_TEMPLATE.md +16 -0
- mcpnuke-6.22.0/.github/dependabot.yml +10 -0
- mcpnuke-6.22.0/.github/workflows/mcp-security-scan.yml +211 -0
- mcpnuke-6.22.0/.github/workflows/oss-targets.yml +53 -0
- mcpnuke-6.22.0/.github/workflows/publish.yml +137 -0
- mcpnuke-6.22.0/.github/workflows/tests.yml +227 -0
- mcpnuke-6.22.0/.gitignore +81 -0
- mcpnuke-6.22.0/.gitleaks.toml +42 -0
- mcpnuke-6.22.0/.gitmodules +3 -0
- mcpnuke-6.22.0/.python-version +1 -0
- mcpnuke-6.22.0/.trufflehog-exclude-paths +3 -0
- mcpnuke-6.22.0/AGENTS.md +148 -0
- mcpnuke-6.22.0/CHANGELOG.md +2221 -0
- mcpnuke-6.22.0/CODE_OF_CONDUCT.md +128 -0
- mcpnuke-6.22.0/CONTRIBUTING.md +295 -0
- mcpnuke-6.22.0/LICENSE +21 -0
- mcpnuke-6.22.0/PKG-INFO +372 -0
- mcpnuke-6.22.0/QUICKSTART.md +685 -0
- mcpnuke-6.22.0/README.md +323 -0
- mcpnuke-6.22.0/ROADMAP.md +271 -0
- mcpnuke-6.22.0/SECURITY.md +89 -0
- mcpnuke-6.22.0/deploy/Dockerfile +25 -0
- mcpnuke-6.22.0/docs/ai-analysis.md +167 -0
- mcpnuke-6.22.0/docs/checks.md +341 -0
- mcpnuke-6.22.0/docs/ci-cd-guide.md +312 -0
- mcpnuke-6.22.0/docs/cli-reference.md +214 -0
- mcpnuke-6.22.0/docs/false-positive-baseline.md +169 -0
- mcpnuke-6.22.0/docs/kubernetes.md +87 -0
- mcpnuke-6.22.0/docs/lanes.md +52 -0
- mcpnuke-6.22.0/docs/methodology.md +190 -0
- mcpnuke-6.22.0/docs/oss-target-baseline.md +192 -0
- mcpnuke-6.22.0/docs/scan-modes.md +42 -0
- mcpnuke-6.22.0/docs/spec-surface.md +163 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-04-26-by-lane-reporting.md +333 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-05-03-general-purpose-enhancements-design.md +394 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-08-false-positive-harness-design.md +186 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-08-lab-baselines-design.md +101 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-08-policy-from-proved-chains-design.md +156 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-08-priority-actions-design.md +186 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-08-priority-actions-slice-c.md +26 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-09-error-reflection-severity-design.md +185 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-09-oss-target-fp-harness-design.md +193 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-10-stdio-transport-awareness-design.md +193 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-11-distribution-design.md +140 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-25-mcp-spec-surface-gap-map-design.md +111 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-25-routing-header-binding-design.md +50 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-26-handshake-error-honesty-design.md +30 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-26-protected-resource-metadata-design.md +57 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-26-taxonomy-field-honesty-design.md +29 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-27-ci-dogfood-design.md +40 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-27-stdio-rate-limit-design.md +29 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-27-t22-t23-coverage-design.md +37 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-28-honesty-mypy-design.md +28 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-30-full-taxonomy-expansion-design.md +100 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-08-31-multi-hop-chain-replay-enhancements-design.md +106 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-09-01-multi-hop-chain-depth-design.md +203 -0
- mcpnuke-6.22.0/docs/superpowers/specs/2026-09-14-cross-server-chain-design.md +112 -0
- mcpnuke-6.22.0/install.sh +177 -0
- mcpnuke-6.22.0/mcpnuke/__init__.py +14 -0
- mcpnuke-6.22.0/mcpnuke/__main__.py +272 -0
- mcpnuke-6.22.0/mcpnuke/_docsgen.py +297 -0
- mcpnuke-6.22.0/mcpnuke/_runner_entry.py +55 -0
- mcpnuke-6.22.0/mcpnuke/checks/__init__.py +859 -0
- mcpnuke-6.22.0/mcpnuke/checks/_lane_helpers.py +65 -0
- mcpnuke-6.22.0/mcpnuke/checks/actuator_probe.py +229 -0
- mcpnuke-6.22.0/mcpnuke/checks/agentic_loop.py +176 -0
- mcpnuke-6.22.0/mcpnuke/checks/ai_guardrail_probe.py +143 -0
- mcpnuke-6.22.0/mcpnuke/checks/anon_budget_exhaust.py +182 -0
- mcpnuke-6.22.0/mcpnuke/checks/base.py +102 -0
- mcpnuke-6.22.0/mcpnuke/checks/behavioral.py +446 -0
- mcpnuke-6.22.0/mcpnuke/checks/chaining.py +345 -0
- mcpnuke-6.22.0/mcpnuke/checks/command_injection_broad.py +213 -0
- mcpnuke-6.22.0/mcpnuke/checks/config_dump.py +85 -0
- mcpnuke-6.22.0/mcpnuke/checks/config_tampering.py +79 -0
- mcpnuke-6.22.0/mcpnuke/checks/credential_in_schema.py +40 -0
- mcpnuke-6.22.0/mcpnuke/checks/dpop_enforcement.py +263 -0
- mcpnuke-6.22.0/mcpnuke/checks/error_leakage.py +120 -0
- mcpnuke-6.22.0/mcpnuke/checks/execution.py +90 -0
- mcpnuke-6.22.0/mcpnuke/checks/exfil_flow.py +225 -0
- mcpnuke-6.22.0/mcpnuke/checks/inference_backend.py +757 -0
- mcpnuke-6.22.0/mcpnuke/checks/injection.py +297 -0
- mcpnuke-6.22.0/mcpnuke/checks/input_sanitization.py +290 -0
- mcpnuke-6.22.0/mcpnuke/checks/insecure_agent_comms.py +97 -0
- mcpnuke-6.22.0/mcpnuke/checks/jwt_boundary.py +245 -0
- mcpnuke-6.22.0/mcpnuke/checks/jwt_validation.py +220 -0
- mcpnuke-6.22.0/mcpnuke/checks/k8s_chain_probe.py +69 -0
- mcpnuke-6.22.0/mcpnuke/checks/list_cache.py +135 -0
- mcpnuke-6.22.0/mcpnuke/checks/llm_analysis.py +865 -0
- mcpnuke-6.22.0/mcpnuke/checks/model_routing.py +111 -0
- mcpnuke-6.22.0/mcpnuke/checks/permissions.py +109 -0
- mcpnuke-6.22.0/mcpnuke/checks/prompt_injection_t01.py +188 -0
- mcpnuke-6.22.0/mcpnuke/checks/prompt_leakage.py +33 -0
- mcpnuke-6.22.0/mcpnuke/checks/protected_resource_metadata.py +229 -0
- mcpnuke-6.22.0/mcpnuke/checks/rate_limit.py +89 -0
- mcpnuke-6.22.0/mcpnuke/checks/remote_package_exec.py +140 -0
- mcpnuke-6.22.0/mcpnuke/checks/resource_poisoning.py +121 -0
- mcpnuke-6.22.0/mcpnuke/checks/response_credentials.py +80 -0
- mcpnuke-6.22.0/mcpnuke/checks/routing_header_binding.py +100 -0
- mcpnuke-6.22.0/mcpnuke/checks/schema_overdisclosure.py +147 -0
- mcpnuke-6.22.0/mcpnuke/checks/scope_pollution.py +164 -0
- mcpnuke-6.22.0/mcpnuke/checks/sdk_cache_tamper.py +338 -0
- mcpnuke-6.22.0/mcpnuke/checks/shadow_mcp_server.py +57 -0
- mcpnuke-6.22.0/mcpnuke/checks/shell_injection.py +193 -0
- mcpnuke-6.22.0/mcpnuke/checks/ssrf_probe.py +136 -0
- mcpnuke-6.22.0/mcpnuke/checks/supply_chain.py +33 -0
- mcpnuke-6.22.0/mcpnuke/checks/taxonomy_coverage.py +729 -0
- mcpnuke-6.22.0/mcpnuke/checks/teleport.py +258 -0
- mcpnuke-6.22.0/mcpnuke/checks/teleport_labs.py +295 -0
- mcpnuke-6.22.0/mcpnuke/checks/temporal_consistency.py +88 -0
- mcpnuke-6.22.0/mcpnuke/checks/theft.py +56 -0
- mcpnuke-6.22.0/mcpnuke/checks/tool_output_poisoning.py +161 -0
- mcpnuke-6.22.0/mcpnuke/checks/tool_probes.py +468 -0
- mcpnuke-6.22.0/mcpnuke/checks/tool_response_injection.py +161 -0
- mcpnuke-6.22.0/mcpnuke/checks/transport.py +77 -0
- mcpnuke-6.22.0/mcpnuke/checks/webhook_persistence.py +78 -0
- mcpnuke-6.22.0/mcpnuke/cli.py +895 -0
- mcpnuke-6.22.0/mcpnuke/cli_steps.py +711 -0
- mcpnuke-6.22.0/mcpnuke/core/__init__.py +13 -0
- mcpnuke-6.22.0/mcpnuke/core/auth.py +517 -0
- mcpnuke-6.22.0/mcpnuke/core/cache_hints.py +19 -0
- mcpnuke-6.22.0/mcpnuke/core/chain_args.py +243 -0
- mcpnuke-6.22.0/mcpnuke/core/chain_replay.py +733 -0
- mcpnuke-6.22.0/mcpnuke/core/chain_templates.py +106 -0
- mcpnuke-6.22.0/mcpnuke/core/constants.py +105 -0
- mcpnuke-6.22.0/mcpnuke/core/enumerator.py +317 -0
- mcpnuke-6.22.0/mcpnuke/core/llm.py +547 -0
- mcpnuke-6.22.0/mcpnuke/core/llm_ollama.py +552 -0
- mcpnuke-6.22.0/mcpnuke/core/llm_prompts.py +344 -0
- mcpnuke-6.22.0/mcpnuke/core/models.py +140 -0
- mcpnuke-6.22.0/mcpnuke/core/oast.py +266 -0
- mcpnuke-6.22.0/mcpnuke/core/protocol.py +74 -0
- mcpnuke-6.22.0/mcpnuke/core/session.py +379 -0
- mcpnuke-6.22.0/mcpnuke/core/taxonomy.py +140 -0
- mcpnuke-6.22.0/mcpnuke/core/transports/__init__.py +5 -0
- mcpnuke-6.22.0/mcpnuke/core/transports/base.py +78 -0
- mcpnuke-6.22.0/mcpnuke/core/transports/http.py +196 -0
- mcpnuke-6.22.0/mcpnuke/core/transports/sse.py +192 -0
- mcpnuke-6.22.0/mcpnuke/core/transports/stdio.py +145 -0
- mcpnuke-6.22.0/mcpnuke/core/transports/toolserver.py +285 -0
- mcpnuke-6.22.0/mcpnuke/core/trust.py +68 -0
- mcpnuke-6.22.0/mcpnuke/data/public_targets.txt +33 -0
- mcpnuke-6.22.0/mcpnuke/data/taxonomy/lanes.yaml +618 -0
- mcpnuke-6.22.0/mcpnuke/data/tool_names.txt +105 -0
- mcpnuke-6.22.0/mcpnuke/diff.py +254 -0
- mcpnuke-6.22.0/mcpnuke/k8s/Dockerfile +22 -0
- mcpnuke-6.22.0/mcpnuke/k8s/__init__.py +10 -0
- mcpnuke-6.22.0/mcpnuke/k8s/discovery.py +348 -0
- mcpnuke-6.22.0/mcpnuke/k8s/fingerprint.py +221 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/cronjob.yaml +58 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/job.yaml +55 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/kustomization.yaml +17 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/namespace.yaml +7 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/rbac-impersonate.yaml +30 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/rbac.yaml +40 -0
- mcpnuke-6.22.0/mcpnuke/k8s/manifests/serviceaccount.yaml +9 -0
- mcpnuke-6.22.0/mcpnuke/k8s/scanner.py +592 -0
- mcpnuke-6.22.0/mcpnuke/patterns/__init__.py +25 -0
- mcpnuke-6.22.0/mcpnuke/patterns/credentials.py +293 -0
- mcpnuke-6.22.0/mcpnuke/patterns/probes.py +398 -0
- mcpnuke-6.22.0/mcpnuke/patterns/rules.py +181 -0
- mcpnuke-6.22.0/mcpnuke/patterns/tokens.py +32 -0
- mcpnuke-6.22.0/mcpnuke/policy/__init__.py +6 -0
- mcpnuke-6.22.0/mcpnuke/policy/generator.py +259 -0
- mcpnuke-6.22.0/mcpnuke/policy/nullfield.py +120 -0
- mcpnuke-6.22.0/mcpnuke/policy/rules.py +146 -0
- mcpnuke-6.22.0/mcpnuke/profile.py +123 -0
- mcpnuke-6.22.0/mcpnuke/py.typed +0 -0
- mcpnuke-6.22.0/mcpnuke/reporting/__init__.py +35 -0
- mcpnuke-6.22.0/mcpnuke/reporting/by_lane.py +224 -0
- mcpnuke-6.22.0/mcpnuke/reporting/console.py +188 -0
- mcpnuke-6.22.0/mcpnuke/reporting/coverage_report.py +231 -0
- mcpnuke-6.22.0/mcpnuke/reporting/diff.py +124 -0
- mcpnuke-6.22.0/mcpnuke/reporting/files.py +22 -0
- mcpnuke-6.22.0/mcpnuke/reporting/json_out.py +178 -0
- mcpnuke-6.22.0/mcpnuke/reporting/lab_coverage.py +89 -0
- mcpnuke-6.22.0/mcpnuke/reporting/owasp.py +229 -0
- mcpnuke-6.22.0/mcpnuke/reporting/priority.py +410 -0
- mcpnuke-6.22.0/mcpnuke/reporting/sarif.py +168 -0
- mcpnuke-6.22.0/mcpnuke/reporting/taxonomy_coverage.py +179 -0
- mcpnuke-6.22.0/mcpnuke/scanner.py +358 -0
- mcpnuke-6.22.0/mcpnuke/server/__init__.py +16 -0
- mcpnuke-6.22.0/mcpnuke/server/app.py +109 -0
- mcpnuke-6.22.0/mcpnuke/server/models.py +96 -0
- mcpnuke-6.22.0/mcpnuke/server/runner.py +207 -0
- mcpnuke-6.22.0/mcpnuke/subcommands.py +205 -0
- mcpnuke-6.22.0/profiles/camazotz.json +946 -0
- mcpnuke-6.22.0/profiles/dvmcp.json +26 -0
- mcpnuke-6.22.0/profiles/example.json +49 -0
- mcpnuke-6.22.0/pyproject.toml +138 -0
- mcpnuke-6.22.0/quickstart.sh +206 -0
- mcpnuke-6.22.0/scan +22 -0
- mcpnuke-6.22.0/scripts/check-tag-version.sh +52 -0
- mcpnuke-6.22.0/scripts/secret-scan.sh +93 -0
- mcpnuke-6.22.0/tests/__init__.py +1 -0
- mcpnuke-6.22.0/tests/conftest.py +40 -0
- mcpnuke-6.22.0/tests/fixtures/scans/dvmcp_challenge_shapes.json +287 -0
- mcpnuke-6.22.0/tests/fixtures/scans/proved_multihop_policy.json +14 -0
- mcpnuke-6.22.0/tests/fixtures/scans/proved_outranks_capability_spam.json +322 -0
- mcpnuke-6.22.0/tests/oss_targets/__init__.py +1 -0
- mcpnuke-6.22.0/tests/oss_targets/runner.py +56 -0
- mcpnuke-6.22.0/tests/oss_targets/snapshots/server-everything.json +155 -0
- mcpnuke-6.22.0/tests/oss_targets/snapshots/server-fetch.json +45 -0
- mcpnuke-6.22.0/tests/oss_targets/snapshots/server-filesystem.json +315 -0
- mcpnuke-6.22.0/tests/oss_targets/snapshots/server-git.json +315 -0
- mcpnuke-6.22.0/tests/oss_targets/snapshots/server-memory.json +35 -0
- mcpnuke-6.22.0/tests/oss_targets/targets.py +79 -0
- mcpnuke-6.22.0/tests/owasp_lab/__init__.py +5 -0
- mcpnuke-6.22.0/tests/owasp_lab/server.py +129 -0
- mcpnuke-6.22.0/tests/owasp_lab/tools.py +103 -0
- mcpnuke-6.22.0/tests/reference_target/__init__.py +5 -0
- mcpnuke-6.22.0/tests/reference_target/server.py +177 -0
- mcpnuke-6.22.0/tests/reference_target/stdio_server.py +108 -0
- mcpnuke-6.22.0/tests/reference_target/tools.py +72 -0
- mcpnuke-6.22.0/tests/reference_target/tools_runtime.py +125 -0
- mcpnuke-6.22.0/tests/test_active_prompt_injection.py +101 -0
- mcpnuke-6.22.0/tests/test_actuator_probe.py +46 -0
- mcpnuke-6.22.0/tests/test_ai_guardrail_probe.py +213 -0
- mcpnuke-6.22.0/tests/test_anon_budget_exhaust.py +224 -0
- mcpnuke-6.22.0/tests/test_anonymous_scan_detection.py +95 -0
- mcpnuke-6.22.0/tests/test_attack_chain_linkage.py +188 -0
- mcpnuke-6.22.0/tests/test_attack_chains_json.py +74 -0
- mcpnuke-6.22.0/tests/test_auth_error_redaction.py +43 -0
- mcpnuke-6.22.0/tests/test_auth_flow_support.py +102 -0
- mcpnuke-6.22.0/tests/test_by_lane_report.py +94 -0
- mcpnuke-6.22.0/tests/test_chain_judge.py +26 -0
- mcpnuke-6.22.0/tests/test_chain_propose.py +279 -0
- mcpnuke-6.22.0/tests/test_chain_replay.py +353 -0
- mcpnuke-6.22.0/tests/test_chain_replay_extended.py +230 -0
- mcpnuke-6.22.0/tests/test_chain_replay_oob.py +105 -0
- mcpnuke-6.22.0/tests/test_chain_replay_safety.py +127 -0
- mcpnuke-6.22.0/tests/test_chain_replay_transforms.py +239 -0
- mcpnuke-6.22.0/tests/test_chain_replay_wiring.py +719 -0
- mcpnuke-6.22.0/tests/test_chain_revise.py +195 -0
- mcpnuke-6.22.0/tests/test_chain_templates.py +47 -0
- mcpnuke-6.22.0/tests/test_chaining.py +114 -0
- mcpnuke-6.22.0/tests/test_chaining_severity_floor.py +81 -0
- mcpnuke-6.22.0/tests/test_check_progress.py +573 -0
- mcpnuke-6.22.0/tests/test_checks_integration.py +28 -0
- mcpnuke-6.22.0/tests/test_ci_dogfood.py +34 -0
- mcpnuke-6.22.0/tests/test_classify_probe.py +139 -0
- mcpnuke-6.22.0/tests/test_claude_args.py +111 -0
- mcpnuke-6.22.0/tests/test_claude_model_default.py +115 -0
- mcpnuke-6.22.0/tests/test_cli.py +214 -0
- mcpnuke-6.22.0/tests/test_cli_dogfood.py +104 -0
- mcpnuke-6.22.0/tests/test_cli_steps_phases.py +48 -0
- mcpnuke-6.22.0/tests/test_code_execution_precision.py +92 -0
- mcpnuke-6.22.0/tests/test_config_dump.py +225 -0
- mcpnuke-6.22.0/tests/test_config_tampering.py +59 -0
- mcpnuke-6.22.0/tests/test_coverage_flag.py +51 -0
- mcpnuke-6.22.0/tests/test_coverage_report.py +125 -0
- mcpnuke-6.22.0/tests/test_credential_in_description.py +143 -0
- mcpnuke-6.22.0/tests/test_credential_in_schema.py +75 -0
- mcpnuke-6.22.0/tests/test_credential_patterns.py +294 -0
- mcpnuke-6.22.0/tests/test_cross_server_chain.py +99 -0
- mcpnuke-6.22.0/tests/test_cross_server_replay.py +251 -0
- mcpnuke-6.22.0/tests/test_deep_rug_pull.py +145 -0
- mcpnuke-6.22.0/tests/test_delegation_chain_abuse.py +94 -0
- mcpnuke-6.22.0/tests/test_delegation_depth.py +97 -0
- mcpnuke-6.22.0/tests/test_detect_errors.py +33 -0
- mcpnuke-6.22.0/tests/test_diff.py +144 -0
- mcpnuke-6.22.0/tests/test_diff_baseline.py +95 -0
- mcpnuke-6.22.0/tests/test_docs_current.py +1116 -0
- mcpnuke-6.22.0/tests/test_dpop_enforcement.py +362 -0
- mcpnuke-6.22.0/tests/test_dvmcp.py +787 -0
- mcpnuke-6.22.0/tests/test_ecosystem_drift.py +257 -0
- mcpnuke-6.22.0/tests/test_error_leakage_json.py +179 -0
- mcpnuke-6.22.0/tests/test_error_reflection_probes.py +239 -0
- mcpnuke-6.22.0/tests/test_execution_context_forgery.py +106 -0
- mcpnuke-6.22.0/tests/test_exfil_classification.py +77 -0
- mcpnuke-6.22.0/tests/test_exfil_confirmation.py +169 -0
- mcpnuke-6.22.0/tests/test_exfil_flow.py +55 -0
- mcpnuke-6.22.0/tests/test_exfil_oob_confirmation.py +180 -0
- mcpnuke-6.22.0/tests/test_exit_codes.py +15 -0
- mcpnuke-6.22.0/tests/test_extended_args.py +154 -0
- mcpnuke-6.22.0/tests/test_false_positives.py +181 -0
- mcpnuke-6.22.0/tests/test_false_positives_stdio.py +131 -0
- mcpnuke-6.22.0/tests/test_fast_sampling.py +308 -0
- mcpnuke-6.22.0/tests/test_finding_digest_coercion.py +36 -0
- mcpnuke-6.22.0/tests/test_gitleaks_allowlist.py +32 -0
- mcpnuke-6.22.0/tests/test_identifier_tokens.py +44 -0
- mcpnuke-6.22.0/tests/test_indirect_injection_tools.py +87 -0
- mcpnuke-6.22.0/tests/test_indirect_multi_param.py +129 -0
- mcpnuke-6.22.0/tests/test_inference_backend.py +689 -0
- mcpnuke-6.22.0/tests/test_injection_patterns.py +90 -0
- mcpnuke-6.22.0/tests/test_insecure_agent_comms.py +223 -0
- mcpnuke-6.22.0/tests/test_install_script.py +181 -0
- mcpnuke-6.22.0/tests/test_inventory.py +125 -0
- mcpnuke-6.22.0/tests/test_jwt_boundary.py +231 -0
- mcpnuke-6.22.0/tests/test_jwt_validation.py +255 -0
- mcpnuke-6.22.0/tests/test_k8s.py +244 -0
- mcpnuke-6.22.0/tests/test_k8s_chain_probe.py +47 -0
- mcpnuke-6.22.0/tests/test_k8s_external.py +150 -0
- mcpnuke-6.22.0/tests/test_k8s_fingerprint.py +246 -0
- mcpnuke-6.22.0/tests/test_k8s_only_report.py +91 -0
- mcpnuke-6.22.0/tests/test_k8s_scanner.py +519 -0
- mcpnuke-6.22.0/tests/test_k8s_setup.py +52 -0
- mcpnuke-6.22.0/tests/test_k8s_tls.py +83 -0
- mcpnuke-6.22.0/tests/test_lab_baselines.py +148 -0
- mcpnuke-6.22.0/tests/test_lab_coverage.py +44 -0
- mcpnuke-6.22.0/tests/test_list_cache.py +225 -0
- mcpnuke-6.22.0/tests/test_llm_analysis_phase2.py +190 -0
- mcpnuke-6.22.0/tests/test_llm_bedrock.py +45 -0
- mcpnuke-6.22.0/tests/test_llm_chain_evidence.py +320 -0
- mcpnuke-6.22.0/tests/test_llm_ollama.py +355 -0
- mcpnuke-6.22.0/tests/test_llm_parse_findings.py +141 -0
- mcpnuke-6.22.0/tests/test_llm_phase1_grounding.py +204 -0
- mcpnuke-6.22.0/tests/test_llm_taxonomy_constraint.py +130 -0
- mcpnuke-6.22.0/tests/test_llm_text_blocks.py +147 -0
- mcpnuke-6.22.0/tests/test_llm_truncation.py +169 -0
- mcpnuke-6.22.0/tests/test_main_crash.py +19 -0
- mcpnuke-6.22.0/tests/test_mcpnuke_diff.py +122 -0
- mcpnuke-6.22.0/tests/test_model_integrity.py +404 -0
- mcpnuke-6.22.0/tests/test_model_routing.py +184 -0
- mcpnuke-6.22.0/tests/test_models.py +34 -0
- mcpnuke-6.22.0/tests/test_native_function_identity_erasure.py +99 -0
- mcpnuke-6.22.0/tests/test_oast_cli.py +56 -0
- mcpnuke-6.22.0/tests/test_oast_listener.py +194 -0
- mcpnuke-6.22.0/tests/test_oidc_resource.py +115 -0
- mcpnuke-6.22.0/tests/test_oss_normalization.py +54 -0
- mcpnuke-6.22.0/tests/test_oss_runner.py +55 -0
- mcpnuke-6.22.0/tests/test_oss_targets.py +79 -0
- mcpnuke-6.22.0/tests/test_owasp_cli.py +141 -0
- mcpnuke-6.22.0/tests/test_owasp_lab.py +92 -0
- mcpnuke-6.22.0/tests/test_packaging.py +120 -0
- mcpnuke-6.22.0/tests/test_pagination.py +197 -0
- mcpnuke-6.22.0/tests/test_pattern_anchoring.py +127 -0
- mcpnuke-6.22.0/tests/test_patterns.py +37 -0
- mcpnuke-6.22.0/tests/test_permissions_debounce.py +71 -0
- mcpnuke-6.22.0/tests/test_policy_generation.py +361 -0
- mcpnuke-6.22.0/tests/test_policy_generator.py +456 -0
- mcpnuke-6.22.0/tests/test_pre_auth_injection.py +84 -0
- mcpnuke-6.22.0/tests/test_priority_actions.py +268 -0
- mcpnuke-6.22.0/tests/test_profile.py +141 -0
- mcpnuke-6.22.0/tests/test_prompt_leakage.py +46 -0
- mcpnuke-6.22.0/tests/test_protected_resource_metadata.py +234 -0
- mcpnuke-6.22.0/tests/test_protocol.py +72 -0
- mcpnuke-6.22.0/tests/test_protocol_headers.py +71 -0
- mcpnuke-6.22.0/tests/test_protocol_negotiation.py +152 -0
- mcpnuke-6.22.0/tests/test_public_targets.py +52 -0
- mcpnuke-6.22.0/tests/test_quickstart_recipes.py +135 -0
- mcpnuke-6.22.0/tests/test_rate_limit.py +131 -0
- mcpnuke-6.22.0/tests/test_reference_target.py +174 -0
- mcpnuke-6.22.0/tests/test_reference_target_stdio.py +116 -0
- mcpnuke-6.22.0/tests/test_release_guard.py +109 -0
- mcpnuke-6.22.0/tests/test_remote_package_exec.py +262 -0
- mcpnuke-6.22.0/tests/test_report_file_mode.py +47 -0
- mcpnuke-6.22.0/tests/test_reporting_owasp.py +138 -0
- mcpnuke-6.22.0/tests/test_resolve_auth.py +39 -0
- mcpnuke-6.22.0/tests/test_response_credentials.py +68 -0
- mcpnuke-6.22.0/tests/test_response_grading.py +129 -0
- mcpnuke-6.22.0/tests/test_response_text.py +92 -0
- mcpnuke-6.22.0/tests/test_revise_chain_guard.py +24 -0
- mcpnuke-6.22.0/tests/test_risk_aware_fast.py +65 -0
- mcpnuke-6.22.0/tests/test_routing_header_binding.py +189 -0
- mcpnuke-6.22.0/tests/test_runner_entry.py +136 -0
- mcpnuke-6.22.0/tests/test_sarif.py +171 -0
- mcpnuke-6.22.0/tests/test_scan_profiles.py +37 -0
- mcpnuke-6.22.0/tests/test_scanner_ai_dispatch.py +41 -0
- mcpnuke-6.22.0/tests/test_schema_overdisclosure.py +228 -0
- mcpnuke-6.22.0/tests/test_scope_pollution.py +152 -0
- mcpnuke-6.22.0/tests/test_sdk_cache_tamper.py +427 -0
- mcpnuke-6.22.0/tests/test_secret_file.py +72 -0
- mcpnuke-6.22.0/tests/test_semantic_injection.py +65 -0
- mcpnuke-6.22.0/tests/test_server.py +456 -0
- mcpnuke-6.22.0/tests/test_server_runner.py +424 -0
- mcpnuke-6.22.0/tests/test_session_id.py +85 -0
- mcpnuke-6.22.0/tests/test_session_post_raw.py +146 -0
- mcpnuke-6.22.0/tests/test_session_protocol.py +89 -0
- mcpnuke-6.22.0/tests/test_shadow_mcp_server.py +62 -0
- mcpnuke-6.22.0/tests/test_shell_injection.py +184 -0
- mcpnuke-6.22.0/tests/test_sidecar_credential_tamper.py +96 -0
- mcpnuke-6.22.0/tests/test_ssrf_probe.py +76 -0
- mcpnuke-6.22.0/tests/test_ssti_fingerprint.py +59 -0
- mcpnuke-6.22.0/tests/test_state_mutation.py +105 -0
- mcpnuke-6.22.0/tests/test_stdio_probe_opts.py +39 -0
- mcpnuke-6.22.0/tests/test_supply_chain.py +47 -0
- mcpnuke-6.22.0/tests/test_taxonomy_coverage_claim.py +194 -0
- mcpnuke-6.22.0/tests/test_taxonomy_coverage_extended.py +354 -0
- mcpnuke-6.22.0/tests/test_taxonomy_coverage_report.py +72 -0
- mcpnuke-6.22.0/tests/test_taxonomy_loader.py +131 -0
- mcpnuke-6.22.0/tests/test_teleport_checks.py +145 -0
- mcpnuke-6.22.0/tests/test_teleport_labs.py +222 -0
- mcpnuke-6.22.0/tests/test_tls_verify_probes.py +77 -0
- mcpnuke-6.22.0/tests/test_tool_shadowing_confusable.py +142 -0
- mcpnuke-6.22.0/tests/test_transport_filter.py +44 -0
- mcpnuke-6.22.0/tests/test_trust_set.py +158 -0
- mcpnuke-6.22.0/tests/test_validate_ai_backend.py +37 -0
- mcpnuke-6.22.0/tests/test_version_consistency.py +54 -0
- mcpnuke-6.22.0/tests/test_watch.py +41 -0
- mcpnuke-6.22.0/tests/test_webhook_persistence.py +56 -0
- mcpnuke-6.22.0/uv.lock +1527 -0
- mcpnuke-6.22.0/walkthrough/README.md +429 -0
- mcpnuke-6.22.0/walkthrough/demo.sh +301 -0
- mcpnuke-6.22.0/walkthrough/demo_ai.sh +294 -0
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Conventions for mcpnuke check modules and pattern files
|
|
3
|
+
globs: mcpnuke/checks/**/*.py,mcpnuke/patterns/**/*.py
|
|
4
|
+
alwaysApply: false
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Check Module Conventions
|
|
8
|
+
|
|
9
|
+
## Static Check Template
|
|
10
|
+
|
|
11
|
+
```python
|
|
12
|
+
"""One-line description of what this check detects."""
|
|
13
|
+
|
|
14
|
+
import re
|
|
15
|
+
from mcpnuke.core.models import TargetResult
|
|
16
|
+
from mcpnuke.checks.base import time_check
|
|
17
|
+
from mcpnuke.patterns.rules import YOUR_PATTERNS
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
def check_your_check(result: TargetResult) -> None:
|
|
21
|
+
with time_check("your_check", result):
|
|
22
|
+
for tool in result.tools:
|
|
23
|
+
name: str = tool.get("name", "")
|
|
24
|
+
desc: str = tool.get("description", "")
|
|
25
|
+
combined: str = f"{name} {desc} {tool.get('inputSchema', {})}"
|
|
26
|
+
for pat in YOUR_PATTERNS:
|
|
27
|
+
if re.search(pat, combined, re.IGNORECASE):
|
|
28
|
+
result.add("your_check", "SEVERITY", f"Title '{name}'", f"Detail: {pat}", evidence=combined[:300])
|
|
29
|
+
break
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
## Behavioral Check Template
|
|
33
|
+
|
|
34
|
+
`session` is typed with `MCPSessionProtocol` from
|
|
35
|
+
`mcpnuke.core.transports.base`. Rely only on what it declares — `call`,
|
|
36
|
+
`notify`, `close`, `wait_ready`, `protocol_mode`. For anything HTTP-specific
|
|
37
|
+
(`post_raw`), gate on `hasattr(session, "post_raw")`, because stdio has no
|
|
38
|
+
header layer.
|
|
39
|
+
|
|
40
|
+
```python
|
|
41
|
+
def check_your_check(
|
|
42
|
+
session: MCPSessionProtocol,
|
|
43
|
+
result: TargetResult,
|
|
44
|
+
probe_opts: dict | None = None,
|
|
45
|
+
) -> None:
|
|
46
|
+
opts: dict = probe_opts or {}
|
|
47
|
+
_log = opts.get("_log", lambda msg: None)
|
|
48
|
+
cache: dict = opts.get("_response_cache", {})
|
|
49
|
+
with time_check("your_check", result):
|
|
50
|
+
for tool in result.tools:
|
|
51
|
+
name: str = tool.get("name", "")
|
|
52
|
+
text: str | None = cache.get(name)
|
|
53
|
+
if text is None:
|
|
54
|
+
args = _build_safe_args(tool)
|
|
55
|
+
resp = _call_tool(session, name, args)
|
|
56
|
+
text = _response_text(resp)
|
|
57
|
+
if text:
|
|
58
|
+
# Analyze response
|
|
59
|
+
pass
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
## Wiring Checklist
|
|
63
|
+
|
|
64
|
+
1. Import in `checks/__init__.py`
|
|
65
|
+
2. Call in correct phase (static / behavioral / deep probe)
|
|
66
|
+
3. Add attack chains to `core/constants.py` if applicable
|
|
67
|
+
4. Add to README scan phases table
|
|
68
|
+
5. Add to CHANGELOG
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Core mcpnuke development standards and superpowers workflow integration
|
|
3
|
+
alwaysApply: true
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# mcpnuke Development Standards
|
|
7
|
+
|
|
8
|
+
## Project Identity
|
|
9
|
+
|
|
10
|
+
mcpnuke is an MCP red teaming and security scanner. Version 6.22.0. Python 3.11+.
|
|
11
|
+
Package manager: `uv`. Test runner: `uv run pytest tests/ -v`.
|
|
12
|
+
|
|
13
|
+
## Superpowers Workflow (mandatory)
|
|
14
|
+
|
|
15
|
+
All development on mcpnuke follows the superpowers skills framework:
|
|
16
|
+
|
|
17
|
+
1. **brainstorming** before any new feature, check, or transport
|
|
18
|
+
2. **writing-plans** before multi-step implementation work
|
|
19
|
+
3. **test-driven-development** for all check modules and pattern changes — RED-GREEN-REFACTOR, no exceptions
|
|
20
|
+
4. **systematic-debugging** for any test failure or scan anomaly — form hypothesis before changing code
|
|
21
|
+
5. **verification-before-completion** before claiming anything is done — run `uv run pytest tests/ -v` and confirm output
|
|
22
|
+
6. **requesting-code-review** after completing a feature branch
|
|
23
|
+
|
|
24
|
+
## Code Conventions
|
|
25
|
+
|
|
26
|
+
- Strong typing throughout: use `dict`, `list`, `frozenset`, `int`, `str` type hints on all functions
|
|
27
|
+
- Module-level constants: `UPPER_SNAKE_CASE`, typed explicitly (e.g. `_NAME_MULTIPLIER: int = 3`)
|
|
28
|
+
- Check functions signature: `check_name(result: TargetResult)` for static, `check_name(session: MCPSessionProtocol, result: TargetResult, probe_opts: dict | None = None)` for behavioral
|
|
29
|
+
- Credential regexes belong in `patterns/credentials.py` only, in the tier that matches their false-positive risk — never in `rules.py`, `probes.py`, or a check module
|
|
30
|
+
- Every check wrapped in `with time_check("check_name", result):`
|
|
31
|
+
- Findings via `result.add(check_name, severity, title, detail, evidence=...)`
|
|
32
|
+
- Severity levels: CRITICAL, HIGH, MEDIUM, LOW
|
|
33
|
+
|
|
34
|
+
## Testing Requirements
|
|
35
|
+
|
|
36
|
+
- Every new check needs a dedicated `tests/test_<check_name>.py`
|
|
37
|
+
- Minimum 3 tests per check: positive detection, clean/negative, timing recorded
|
|
38
|
+
- Use `conftest.py` fixtures: `result_with_tools([{...}])`
|
|
39
|
+
- Full suite must pass before any commit: 0 failed. Do not cite a hardcoded pass count.
|
|
40
|
+
- Also green before committing: `ruff check .` at zero, `mypy mcpnuke/` at or below the CI ceiling. The whole package enforces `disallow_untyped_defs`
|
|
41
|
+
- DVMCP live tests gated behind `DVMCP_LIVE=1`
|
|
42
|
+
|
|
43
|
+
## Architecture Quick Reference
|
|
44
|
+
|
|
45
|
+
```
|
|
46
|
+
mcpnuke/checks/__init__.py — orchestrator, _pick_security_relevant, run_all_checks
|
|
47
|
+
mcpnuke/checks/<name>.py — individual check modules
|
|
48
|
+
mcpnuke/checks/base.py — time_check, tool_text (shared searchable surface)
|
|
49
|
+
mcpnuke/patterns/rules.py — static regex pattern sets
|
|
50
|
+
mcpnuke/patterns/probes.py — behavioral probe payloads and response analysis
|
|
51
|
+
mcpnuke/patterns/credentials.py — the only credential regexes, tiered by FP risk
|
|
52
|
+
mcpnuke/core/session.py — transport detection; re-exports the session classes
|
|
53
|
+
mcpnuke/core/transports/base.py — MCPSessionProtocol, HTTPCapableSession
|
|
54
|
+
mcpnuke/core/transports/<name>.py — sse, http, toolserver, stdio sessions
|
|
55
|
+
mcpnuke/core/protocol.py — legacy vs stateless framing (2026-07-28 spec)
|
|
56
|
+
mcpnuke/core/enumerator.py — protocol negotiation and server enumeration
|
|
57
|
+
mcpnuke/core/models.py — Finding, TargetResult dataclasses
|
|
58
|
+
mcpnuke/core/constants.py — severity weights, attack chain patterns
|
|
59
|
+
mcpnuke/scanner.py — parallel scan orchestration
|
|
60
|
+
mcpnuke/__main__.py — CLI entry point
|
|
61
|
+
mcpnuke/cli_steps.py — scan-path helpers: auth, AI backend, k8s, report
|
|
62
|
+
mcpnuke/subcommands.py — --doctor, --lab-coverage, `mcpnuke diff`; exit codes
|
|
63
|
+
```
|
|
64
|
+
|
|
65
|
+
## Invariants Guarded by Tests
|
|
66
|
+
|
|
67
|
+
These exist because each one broke once. Do not route around them:
|
|
68
|
+
|
|
69
|
+
- `tests/test_credential_patterns.py` — every consumer of the credential tiers
|
|
70
|
+
detects the same set. Add new secrets to the corpus.
|
|
71
|
+
- `tests/test_injection_patterns.py` — one shared injection marker set, no
|
|
72
|
+
private copies.
|
|
73
|
+
- `tests/test_session_protocol.py` — all four transports satisfy the Protocol,
|
|
74
|
+
and stdio never gains `post_raw`.
|
|
75
|
+
- `tests/test_check_progress.py` — the progress denominator is derived from the
|
|
76
|
+
check inventory, never hardcoded.
|
|
77
|
+
- `tests/test_docs_current.py` — README, checks, scan modes, and the roadmap
|
|
78
|
+
glance counts match the registry. Stated check counts are not handwritten.
|
|
79
|
+
|
|
80
|
+
## Project-Specific Skills
|
|
81
|
+
|
|
82
|
+
Use mcpnuke skills for domain-specific tasks:
|
|
83
|
+
- `mcpnuke-add-check` — end-to-end new security check
|
|
84
|
+
- `mcpnuke-add-patterns` — new regex detection patterns
|
|
85
|
+
- `mcpnuke-add-transport` — new transport type
|
|
86
|
+
- `mcpnuke-extend-dvmcp` — new DVMCP challenge tests
|
|
87
|
+
- `mcpnuke-run-tests` — run and interpret test suite
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Test conventions for mcpnuke — enforces TDD workflow
|
|
3
|
+
globs: tests/**/*.py
|
|
4
|
+
alwaysApply: false
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# mcpnuke Test Conventions
|
|
8
|
+
|
|
9
|
+
## TDD Workflow (superpowers: test-driven-development)
|
|
10
|
+
|
|
11
|
+
1. **RED** — Write the failing test first. Run it. Watch it fail.
|
|
12
|
+
2. **GREEN** — Write the minimal code to make it pass. Run it. Watch it pass.
|
|
13
|
+
3. **REFACTOR** — Clean up. Run tests again. Still green.
|
|
14
|
+
|
|
15
|
+
Never write implementation before the test exists.
|
|
16
|
+
|
|
17
|
+
## Test Structure
|
|
18
|
+
|
|
19
|
+
```python
|
|
20
|
+
"""Tests for <check_name>."""
|
|
21
|
+
from mcpnuke.core.models import TargetResult
|
|
22
|
+
from mcpnuke.checks.<module> import check_<name>
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
def test_<name>_positive(result_with_tools):
|
|
26
|
+
r = result_with_tools([{"name": "vuln_tool", "description": "...", "inputSchema": {}}])
|
|
27
|
+
check_<name>(r)
|
|
28
|
+
assert any(f.check == "<name>" for f in r.findings)
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
def test_<name>_clean(result_with_tools):
|
|
32
|
+
r = result_with_tools([{"name": "safe_tool", "description": "Nothing here", "inputSchema": {}}])
|
|
33
|
+
check_<name>(r)
|
|
34
|
+
assert not any(f.check == "<name>" for f in r.findings)
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
def test_<name>_timing(result_with_tools):
|
|
38
|
+
r = result_with_tools([{"name": "x", "description": "y", "inputSchema": {}}])
|
|
39
|
+
check_<name>(r)
|
|
40
|
+
assert "<name>" in r.timings
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Running Tests
|
|
44
|
+
|
|
45
|
+
```bash
|
|
46
|
+
uv run pytest tests/ -v # Full suite
|
|
47
|
+
uv run pytest tests/test_foo.py -v # Single file
|
|
48
|
+
uv run pytest tests/ -v -x # Stop on first failure
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
## Verification (superpowers: verification-before-completion)
|
|
52
|
+
|
|
53
|
+
Before claiming work is done, run and confirm:
|
|
54
|
+
- `uv run pytest tests/ -v` — 0 failed. Do not cite a hardcoded pass count.
|
|
55
|
+
- `uv run ruff check .` — zero findings, and `uv run mypy mcpnuke/` at or below
|
|
56
|
+
the ceiling in `.github/workflows/tests.yml`
|
|
57
|
+
- No import errors or deprecation warnings
|
|
58
|
+
- New tests cover positive, negative, and timing
|
|
@@ -0,0 +1,179 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: mcpnuke-add-check
|
|
3
|
+
description: >-
|
|
4
|
+
Create a new mcpnuke security check module end-to-end: pattern file,
|
|
5
|
+
check function, wire into run_all_checks, add tests, update changelog.
|
|
6
|
+
Use when adding a new security check to mcpnuke.
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# Add a New mcpnuke Check
|
|
10
|
+
|
|
11
|
+
## Gather Info
|
|
12
|
+
|
|
13
|
+
1. **Check name** — snake_case (e.g. `jwt_audience`, `ssrf_probe`)
|
|
14
|
+
2. **Check type** — static (metadata only) or behavioral (calls tools)
|
|
15
|
+
3. **What it detects** — one sentence
|
|
16
|
+
4. **Severity** — CRITICAL / HIGH / MEDIUM / LOW
|
|
17
|
+
5. **Taxonomy ID** — MCP-T## from the playbook (if applicable)
|
|
18
|
+
|
|
19
|
+
## File Locations
|
|
20
|
+
|
|
21
|
+
```
|
|
22
|
+
mcpnuke/
|
|
23
|
+
├── patterns/rules.py # Static regex patterns
|
|
24
|
+
├── patterns/probes.py # Behavioral probe payloads
|
|
25
|
+
├── checks/
|
|
26
|
+
│ ├── __init__.py # run_all_checks() — wire new check here
|
|
27
|
+
│ ├── your_check.py # New check module
|
|
28
|
+
│ └── base.py # time_check helper
|
|
29
|
+
├── core/constants.py # ATTACK_CHAIN_PATTERNS — add chains here
|
|
30
|
+
tests/
|
|
31
|
+
├── test_your_check.py # Unit tests
|
|
32
|
+
├── test_dvmcp.py # DVMCP integration tests
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
## Step-by-Step
|
|
36
|
+
|
|
37
|
+
### 1. Add patterns (if static check)
|
|
38
|
+
|
|
39
|
+
Edit `mcpnuke/patterns/rules.py`:
|
|
40
|
+
|
|
41
|
+
```python
|
|
42
|
+
YOUR_CHECK_PATTERNS = [
|
|
43
|
+
r"pattern_one",
|
|
44
|
+
r"pattern_two",
|
|
45
|
+
]
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
### 2. Create the check module
|
|
49
|
+
|
|
50
|
+
Create `mcpnuke/checks/your_check.py`:
|
|
51
|
+
|
|
52
|
+
```python
|
|
53
|
+
"""Description of what this check detects."""
|
|
54
|
+
|
|
55
|
+
import re
|
|
56
|
+
|
|
57
|
+
from mcpnuke.core.models import TargetResult
|
|
58
|
+
from mcpnuke.checks.base import time_check
|
|
59
|
+
from mcpnuke.patterns.rules import YOUR_CHECK_PATTERNS
|
|
60
|
+
|
|
61
|
+
|
|
62
|
+
def check_your_check(result: TargetResult):
|
|
63
|
+
with time_check("your_check", result):
|
|
64
|
+
for tool in result.tools:
|
|
65
|
+
name = tool.get("name", "")
|
|
66
|
+
combined = (
|
|
67
|
+
name + " "
|
|
68
|
+
+ tool.get("description", "")
|
|
69
|
+
+ " " + str(tool.get("inputSchema", {}))
|
|
70
|
+
)
|
|
71
|
+
for pat in YOUR_CHECK_PATTERNS:
|
|
72
|
+
if re.search(pat, combined, re.IGNORECASE):
|
|
73
|
+
result.add(
|
|
74
|
+
"your_check",
|
|
75
|
+
"SEVERITY",
|
|
76
|
+
f"Finding title for tool '{name}'",
|
|
77
|
+
f"Detail: {pat}",
|
|
78
|
+
evidence=combined[:300],
|
|
79
|
+
)
|
|
80
|
+
break
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
For **behavioral checks**, accept `session` and `probe_opts`:
|
|
84
|
+
|
|
85
|
+
```python
|
|
86
|
+
def check_your_check(session, result: TargetResult, probe_opts: dict | None = None):
|
|
87
|
+
opts = probe_opts or {}
|
|
88
|
+
with time_check("your_check", result):
|
|
89
|
+
# Call tools, analyze responses
|
|
90
|
+
pass
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
### 3. Wire into run_all_checks
|
|
94
|
+
|
|
95
|
+
Edit `mcpnuke/checks/__init__.py`:
|
|
96
|
+
|
|
97
|
+
1. Add import at top:
|
|
98
|
+
```python
|
|
99
|
+
from mcpnuke.checks.your_check import check_your_check
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
2. Add call in appropriate phase:
|
|
103
|
+
- **Static checks** section (always run)
|
|
104
|
+
- **Behavioral checks** section (gated on `not no_invoke`)
|
|
105
|
+
- **Deep probes** section (gated on `not no_invoke`, accept `probe_opts`)
|
|
106
|
+
|
|
107
|
+
### 4. Add attack chain patterns (if applicable)
|
|
108
|
+
|
|
109
|
+
Edit `mcpnuke/core/constants.py`, add to `ATTACK_CHAIN_PATTERNS`:
|
|
110
|
+
|
|
111
|
+
```python
|
|
112
|
+
("your_check", "code_execution"),
|
|
113
|
+
("input_sanitization", "your_check"),
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
### 5. Write tests
|
|
117
|
+
|
|
118
|
+
Create `tests/test_your_check.py`:
|
|
119
|
+
|
|
120
|
+
```python
|
|
121
|
+
"""Tests for your_check."""
|
|
122
|
+
|
|
123
|
+
import pytest
|
|
124
|
+
from mcpnuke.core.models import TargetResult
|
|
125
|
+
from mcpnuke.checks.your_check import check_your_check
|
|
126
|
+
|
|
127
|
+
|
|
128
|
+
def test_your_check_positive(result_with_tools):
|
|
129
|
+
r = result_with_tools([{
|
|
130
|
+
"name": "vuln_tool",
|
|
131
|
+
"description": "Description that matches pattern",
|
|
132
|
+
"inputSchema": {},
|
|
133
|
+
}])
|
|
134
|
+
check_your_check(r)
|
|
135
|
+
assert any(f.check == "your_check" for f in r.findings)
|
|
136
|
+
|
|
137
|
+
|
|
138
|
+
def test_your_check_clean(result_with_tools):
|
|
139
|
+
r = result_with_tools([{
|
|
140
|
+
"name": "safe_tool",
|
|
141
|
+
"description": "Nothing suspicious here",
|
|
142
|
+
"inputSchema": {},
|
|
143
|
+
}])
|
|
144
|
+
check_your_check(r)
|
|
145
|
+
assert not any(f.check == "your_check" for f in r.findings)
|
|
146
|
+
|
|
147
|
+
|
|
148
|
+
def test_your_check_timing(result_with_tools):
|
|
149
|
+
r = result_with_tools([{"name": "x", "description": "y", "inputSchema": {}}])
|
|
150
|
+
check_your_check(r)
|
|
151
|
+
assert "your_check" in r.timings
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
### 6. Run tests
|
|
155
|
+
|
|
156
|
+
```bash
|
|
157
|
+
uv run pytest tests/test_your_check.py tests/test_checks_integration.py -v
|
|
158
|
+
```
|
|
159
|
+
|
|
160
|
+
### 7. Update CHANGELOG.md
|
|
161
|
+
|
|
162
|
+
Add under `[Unreleased]` → `### Added`.
|
|
163
|
+
|
|
164
|
+
## Workflow Integration
|
|
165
|
+
|
|
166
|
+
This skill works with superpowers:
|
|
167
|
+
- **test-driven-development** — write tests (step 5) BEFORE the check module (step 2). RED first.
|
|
168
|
+
- **verification-before-completion** — run full suite before claiming done.
|
|
169
|
+
- **systematic-debugging** — if tests fail, form hypothesis before changing code.
|
|
170
|
+
|
|
171
|
+
## Checklist
|
|
172
|
+
|
|
173
|
+
- [ ] Patterns added to `rules.py` or `probes.py`
|
|
174
|
+
- [ ] Tests written FIRST and failing (TDD RED phase)
|
|
175
|
+
- [ ] Check module created in `checks/` (TDD GREEN phase)
|
|
176
|
+
- [ ] Imported and called in `checks/__init__.py`
|
|
177
|
+
- [ ] Attack chains added to `constants.py` (if applicable)
|
|
178
|
+
- [ ] Full test suite passing: `uv run pytest tests/ -v`
|
|
179
|
+
- [ ] CHANGELOG updated
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: mcpnuke-add-patterns
|
|
3
|
+
description: >-
|
|
4
|
+
Add new regex detection patterns to mcpnuke's pattern libraries with
|
|
5
|
+
test coverage. Use when adding new patterns to rules.py or probes.py,
|
|
6
|
+
or when extending detection for a vulnerability class.
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# Add mcpnuke Patterns
|
|
10
|
+
|
|
11
|
+
## Pattern Files
|
|
12
|
+
|
|
13
|
+
| File | Purpose | Used By |
|
|
14
|
+
|------|---------|---------|
|
|
15
|
+
| `mcpnuke/patterns/rules.py` | Static regex for metadata analysis | Static checks (injection, permissions, theft, etc.) |
|
|
16
|
+
| `mcpnuke/patterns/probes.py` | Probe payloads and response analysis | Behavioral checks (tool_probes, resource_poisoning) |
|
|
17
|
+
|
|
18
|
+
## Adding Static Patterns
|
|
19
|
+
|
|
20
|
+
### 1. Define the pattern list in `rules.py`
|
|
21
|
+
|
|
22
|
+
```python
|
|
23
|
+
YOUR_PATTERNS = [
|
|
24
|
+
r"pattern_one",
|
|
25
|
+
r"pattern_two",
|
|
26
|
+
]
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
Pattern guidelines:
|
|
30
|
+
- Use raw strings (`r"..."`)
|
|
31
|
+
- Case-insensitive matching is done by the caller (`re.IGNORECASE`)
|
|
32
|
+
- Use `\s+` for whitespace, `\b` for word boundaries
|
|
33
|
+
- Use `.{0,30}` for bounded wildcards (not `.*`)
|
|
34
|
+
- Test each pattern against both positive and negative examples
|
|
35
|
+
|
|
36
|
+
### 2. Add tests in `tests/test_patterns.py`
|
|
37
|
+
|
|
38
|
+
```python
|
|
39
|
+
def test_your_patterns_match():
|
|
40
|
+
text = "String that should match"
|
|
41
|
+
matches = [p for p in YOUR_PATTERNS if re.search(p, text, re.IGNORECASE)]
|
|
42
|
+
assert len(matches) >= 1
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
def test_your_patterns_no_false_positive():
|
|
46
|
+
text = "Normal safe string"
|
|
47
|
+
matches = [p for p in YOUR_PATTERNS if re.search(p, text, re.IGNORECASE)]
|
|
48
|
+
assert len(matches) == 0
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
### 3. Run tests (TDD: write tests FIRST, then patterns)
|
|
52
|
+
|
|
53
|
+
Follow superpowers test-driven-development: write the test assertions before
|
|
54
|
+
adding patterns to `rules.py`. Watch them fail (RED), then add patterns (GREEN).
|
|
55
|
+
|
|
56
|
+
```bash
|
|
57
|
+
uv run pytest tests/test_patterns.py -v
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
## Adding Probe Payloads
|
|
61
|
+
|
|
62
|
+
### In `probes.py`
|
|
63
|
+
|
|
64
|
+
Injection probes (sent to tools):
|
|
65
|
+
```python
|
|
66
|
+
YOUR_PROBES = [
|
|
67
|
+
f"payload_with_{CANARY}",
|
|
68
|
+
"payload_two",
|
|
69
|
+
]
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
Response analysis patterns (checked in tool output):
|
|
73
|
+
```python
|
|
74
|
+
YOUR_RESPONSE_PATTERNS = [
|
|
75
|
+
r"pattern_to_find_in_responses",
|
|
76
|
+
]
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
Rules:
|
|
80
|
+
- Probes should be **safe** — they test for vuln without causing damage
|
|
81
|
+
- Use the `CANARY` string (`MCP_PROBE_8f4c2a`) to detect reflection
|
|
82
|
+
- Response patterns use the same regex conventions as `rules.py`
|
|
83
|
+
|
|
84
|
+
## Existing Pattern Sets (reference)
|
|
85
|
+
|
|
86
|
+
| Name | Count | Purpose |
|
|
87
|
+
|------|-------|---------|
|
|
88
|
+
| `INJECTION_PATTERNS` | 19 | Prompt injection in metadata |
|
|
89
|
+
| `POISON_PATTERNS` | 11 | Hidden instructions, exfil hints |
|
|
90
|
+
| `DANGEROUS_TOOL_PATTERNS` | 8 categories | Dangerous capabilities |
|
|
91
|
+
| `TOKEN_THEFT_PATTERNS` | 10 | Credential exfiltration |
|
|
92
|
+
| `CODE_EXEC_PATTERNS` | 9 | Code execution indicators |
|
|
93
|
+
| `RATE_LIMIT_PATTERNS` | 5 | Missing rate limiting |
|
|
94
|
+
| `PROMPT_LEAKAGE_PATTERNS` | 8 | Prompt exposure |
|
|
95
|
+
| `SUPPLY_CHAIN_PATTERNS` | 9 | Dynamic package install |
|
|
96
|
+
| `RAC_PATTERNS` | 6 categories | Remote access |
|
|
97
|
+
| `RESPONSE_INJECTION_PATTERNS` | 11 | Injection in tool responses |
|
|
98
|
+
| `ERROR_LEAKAGE_PATTERNS` | 9 | Info disclosure in errors |
|
|
99
|
+
| `CREDENTIAL_CONTENT_PATTERNS` | 11 | Actual secrets in content |
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: mcpnuke-add-transport
|
|
3
|
+
description: >-
|
|
4
|
+
Add a new transport type to mcpnuke alongside SSE, HTTP, and ToolServer.
|
|
5
|
+
Use when adding support for a new MCP transport protocol like DPoP, mTLS,
|
|
6
|
+
or a custom gateway.
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# Add a New mcpnuke Transport
|
|
10
|
+
|
|
11
|
+
## Current Transport Architecture
|
|
12
|
+
|
|
13
|
+
```
|
|
14
|
+
detect_transport(url)
|
|
15
|
+
├── SSE probe → MCPSession
|
|
16
|
+
├── HTTP POST probe → HTTPSession
|
|
17
|
+
├── SSE+POST combos → MCPSession
|
|
18
|
+
└── ToolServer probe → ToolServerSession
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
All session types implement the same interface:
|
|
22
|
+
- `wait_ready(timeout) → bool`
|
|
23
|
+
- `call(method, params, timeout, retries) → dict | None`
|
|
24
|
+
- `notify(method, params)`
|
|
25
|
+
- `close()`
|
|
26
|
+
- Properties: `base`, `sse_url`, `post_url`
|
|
27
|
+
|
|
28
|
+
## Steps to Add a Transport
|
|
29
|
+
|
|
30
|
+
### 1. Create the session class
|
|
31
|
+
|
|
32
|
+
In a new module `mcpnuke/core/transports/<name>.py`, add the class, and
|
|
33
|
+
re-export it from `mcpnuke/core/session.py`:
|
|
34
|
+
|
|
35
|
+
```python
|
|
36
|
+
class YourSession:
|
|
37
|
+
def __init__(self, base, post_url, timeout=25.0, **kwargs):
|
|
38
|
+
self.base = base
|
|
39
|
+
self.sse_url = ""
|
|
40
|
+
self.post_url = post_url
|
|
41
|
+
self.timeout = timeout
|
|
42
|
+
# Your transport-specific setup
|
|
43
|
+
|
|
44
|
+
def wait_ready(self, timeout=10.0) -> bool:
|
|
45
|
+
return True
|
|
46
|
+
|
|
47
|
+
def call(self, method, params=None, timeout=None, retries=2) -> dict | None:
|
|
48
|
+
# Translate MCP JSON-RPC calls to your transport
|
|
49
|
+
pass
|
|
50
|
+
|
|
51
|
+
def notify(self, method, params=None):
|
|
52
|
+
pass
|
|
53
|
+
|
|
54
|
+
def close(self):
|
|
55
|
+
pass
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
### 2. Add detection logic
|
|
59
|
+
|
|
60
|
+
Create a detector function:
|
|
61
|
+
|
|
62
|
+
```python
|
|
63
|
+
def _detect_your_transport(base, hint, timeout, auth_token, **kwargs):
|
|
64
|
+
# Probe for your transport
|
|
65
|
+
# Return YourSession if detected, None otherwise
|
|
66
|
+
pass
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
### 3. Wire into detect_transport
|
|
70
|
+
|
|
71
|
+
Add your detector as a fallback in `detect_transport()`, after existing transports:
|
|
72
|
+
|
|
73
|
+
```python
|
|
74
|
+
# After ToolServer detection
|
|
75
|
+
your_session = _detect_your_transport(base, hint, ...)
|
|
76
|
+
if your_session:
|
|
77
|
+
return your_session
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
### 4. Add CLI flags (if needed)
|
|
81
|
+
|
|
82
|
+
In `mcpnuke/cli.py`, add arguments:
|
|
83
|
+
|
|
84
|
+
```python
|
|
85
|
+
p.add_argument("--your-flag", help="...")
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
Thread through `__main__.py` → `scanner.py` → `detect_transport()`.
|
|
89
|
+
|
|
90
|
+
### 5. Add verbose logging
|
|
91
|
+
|
|
92
|
+
Use the `log` callable in `detect_transport`:
|
|
93
|
+
|
|
94
|
+
```python
|
|
95
|
+
if verbose:
|
|
96
|
+
_log(f" [dim]Trying YourTransport detection...[/dim]")
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
### 6. Update scanner labels
|
|
100
|
+
|
|
101
|
+
In `mcpnuke/scanner.py` `scan_target()`, add label detection:
|
|
102
|
+
|
|
103
|
+
```python
|
|
104
|
+
if isinstance(session, YourSession):
|
|
105
|
+
transport_label = "YourTransport"
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
### 7. Test
|
|
109
|
+
|
|
110
|
+
Add transport detection tests to `tests/test_cli.py` or a new test file.
|
|
111
|
+
|
|
112
|
+
## Reference: Existing Transports
|
|
113
|
+
|
|
114
|
+
| Transport | Class | Detection Method |
|
|
115
|
+
|-----------|-------|-----------------|
|
|
116
|
+
| SSE | `MCPSession` | GET returns `text/event-stream` |
|
|
117
|
+
| HTTP | `HTTPSession` | POST initialize returns JSON-RPC |
|
|
118
|
+
| ToolServer | `ToolServerSession` | POST `/execute` returns tool response |
|