DefectDojo MCP Server
The official open-source Model Context Protocol server for DefectDojo.
It lets Claude, Cursor, VS Code and other MCP clients work with your DefectDojo instance through the DefectDojo REST API v2. Ask an assistant to find the open critical findings in a product, explain a finding, compare two imports, or (when you turn writes on) import a scan and update finding status.
- Works with open-source DefectDojo 2.x and 3.x, and with DefectDojo Pro.
- Read-only by default. Write tools only exist when you enable them.
- Text from DefectDojo is marked as untrusted, because scanner output can carry prompt injection.
- Runs locally over stdio, or as a streamable HTTP server with authentication.
- No telemetry of any kind.
Quick start
You need:
- uv, which provides the
uvxcommand. - The URL of your DefectDojo instance.
- A DefectDojo API v2 key. In DefectDojo, open the user menu and choose API v2 Key. Use a dedicated account with only the permissions the assistant needs (see Security).
Check that it starts:
DEFECTDOJO_URL=https://defectdojo.example.com DEFECTDOJO_API_KEY=your-key uvx defectdojo-mcp-server --help
The package on PyPI is defectdojo-mcp-server. A package named defectdojo-mcp also exists on PyPI, but it is an unrelated project, not this server.
Claude Desktop
Open Settings > Developer > Edit Config and add the server to claude_desktop_config.json:
{
"mcpServers": {
"defectdojo": {
"command": "uvx",
"args": ["defectdojo-mcp-server"],
"env": {
"DEFECTDOJO_URL": "https://defectdojo.example.com",
"DEFECTDOJO_API_KEY": "your-api-key"
}
}
}
}
Restart Claude Desktop after saving.
Claude Code
claude mcp add defectdojo \
--env DEFECTDOJO_URL=https://defectdojo.example.com \
--env DEFECTDOJO_API_KEY=your-api-key \
-- uvx defectdojo-mcp-server
Cursor
Add this to ~/.cursor/mcp.json (all projects) or .cursor/mcp.json (one project):
{
"mcpServers": {
"defectdojo": {
"command": "uvx",
"args": ["defectdojo-mcp-server"],
"env": {
"DEFECTDOJO_URL": "https://defectdojo.example.com",
"DEFECTDOJO_API_KEY": "your-api-key"
}
}
}
}
VS Code
Add this to .vscode/mcp.json. VS Code asks for the API key once and stores it securely, so the key stays out of the file:
{
"inputs": [
{
"type": "promptString",
"id": "defectdojo-api-key",
"description": "DefectDojo API v2 key",
"password": true
}
],
"servers": {
"defectdojo": {
"type": "stdio",
"command": "uvx",
"args": ["defectdojo-mcp-server"],
"env": {
"DEFECTDOJO_URL": "https://defectdojo.example.com",
"DEFECTDOJO_API_KEY": "${input:defectdojo-api-key}"
}
}
}
}
Docker
docker run -i --rm \
-e DEFECTDOJO_URL=https://defectdojo.example.com \
-e DEFECTDOJO_API_KEY=your-api-key \
ghcr.io/defectdojo/defectdojo-mcp
To build the image yourself instead, run docker build -t defectdojo-mcp . in a clone and use defectdojo-mcp as the image name.
Use "command": "docker" with these arguments in any client config above to run it in a container. For HTTP mode inside a container, bind all interfaces in the container (--host 0.0.0.0), publish the port to loopback only (-p 127.0.0.1:8000:8000), and set DEFECTDOJO_MCP_ALLOWED_HOSTS.
Configuration
All settings come from environment variables.
| Variable | Default | Description |
|---|---|---|
DEFECTDOJO_URL |
required | Base URL of the instance, for example https://defectdojo.example.com. A trailing /api/v2 is accepted and removed. |
DEFECTDOJO_API_KEY |
required | API v2 key. Not needed in HTTP pass-through mode. Never logged. |
DEFECTDOJO_VERIFY_SSL |
true |
true, false, or the path to a CA bundle for private certificate authorities. |
DEFECTDOJO_TIMEOUT |
30 |
Request timeout in seconds. |
DEFECTDOJO_ALLOW_WRITES |
false |
Set to true to register the write tools. |
DEFECTDOJO_IMPORT_DIRS |
none | Folders that import_scan and reimport_scan may read report files from. Separate several with : (; on Windows). While unset, imports by file path are refused and only base64 uploads work. The home folder itself and the filesystem root are never accepted. |
DEFECTDOJO_MAX_UPLOAD_MB |
25 |
Largest scan report the server will upload. |
DEFECTDOJO_MCP_AUTH_TOKEN |
none | Bearer token that HTTP clients must send in token mode. |
DEFECTDOJO_MCP_ALLOWED_HOSTS |
none | Comma-separated host names accepted in the Host header when serving HTTP on a non-loopback address. |
Tools
Every tool returns JSON. List tools are paged with limit and offset, and each page reports count and next_offset.
Read tools (always available)
| Tool | What it does |
|---|---|
get_instance_info |
Instance URL, DefectDojo version, edition (open source or Pro, best effort), current user, and whether writes are on. |
list_findings |
Search findings by product, engagement, test, product type, severity, active, verified, duplicate, false positive, risk accepted, mitigated, out of scope, CVE or other vulnerability id, CWE, title text, component, file path, tags and dates. Sortable. |
get_finding |
One finding with full text fields, vulnerability ids, CWE, file path, component, notes, affected endpoints or locations, and its test, engagement and product. |
get_finding_stats |
Exact counts by severity and by status for a product, engagement, test, product type or the whole instance. |
list_finding_notes |
Notes on a finding. |
list_products, get_product |
Products. Newer releases call them assets. |
list_product_types |
Product types. Newer releases call them organizations. |
list_engagements, get_engagement |
Engagements. |
list_tests, get_test |
Tests, meaning individual scan imports or manual tests. |
list_scan_types |
Scan types the instance can import, for use as scan_type. |
list_test_imports |
Import and reimport history for a test, with the findings each run created, closed, reactivated or left untouched. |
get_current_user |
The user the API key belongs to. |
list_locations |
Hosts, URLs and other locations. Uses the locations API on newer releases and the endpoints API on older ones. |
Write tools (only with DEFECTDOJO_ALLOW_WRITES=true)
| Tool | What it does |
|---|---|
import_scan |
Upload a scan report as a new test. Target an engagement id, or name a product and engagement and let DefectDojo create them with auto_create_context. Supports close_old_findings, minimum_severity, tags, scan date, version and CI metadata. |
reimport_scan |
Upload a newer report into an existing test so DefectDojo closes fixed findings and adds new ones. |
add_finding_note |
Add a note to a finding. |
update_finding_status |
Set active, verified, false positive, out of scope, or mitigated (with an optional date and note). |
risk_accept_findings |
Risk accept, or revoke acceptance for, up to 50 findings with DefectDojo's simple risk acceptance. |
create_product |
Create a product in a product type. |
create_engagement |
Create an engagement in a product. |
Scan reports reach the server in one of two ways. Over stdio, pass file_path pointing at a file inside one of the DEFECTDOJO_IMPORT_DIRS folders. Over stdio or HTTP, pass the report as file_content_base64 with a file_name.
File path imports fail closed. With no DEFECTDOJO_IMPORT_DIRS set, the server refuses them instead of falling back to its working directory. It also refuses the home folder and the filesystem root as import folders, resolves symlinks before checking that a file is inside an allowed folder, rejects hidden files and anything inside a hidden folder (any path part that starts with a dot, before or after following symlinks), enforces the size limit, and never includes file contents in error messages. Point DEFECTDOJO_IMPORT_DIRS at a dedicated reports folder, not at a home folder or a whole repository.
Prompts
| Prompt | What it does |
|---|---|
triage_critical_findings |
Walks through the open critical and high findings of a product and suggests a verdict for each. |
summarize_import_changes |
Summarizes what the latest import of a test created, closed and reactivated. |
Read-only by default
Without DEFECTDOJO_ALLOW_WRITES=true the write tools are not registered at all, so an assistant cannot call them even by mistake. The prompts and server instructions also tell the assistant whether changes are possible.
To enable writes, add "DEFECTDOJO_ALLOW_WRITES": "true" to the env block of your client config. Most clients still ask you to approve each tool call, and the write tools carry MCP annotations that mark them as state-changing.
Security
Prompt injection
Finding titles, descriptions, notes, file paths, component names and similar fields usually come straight from scanner output. Anyone who controls something that gets scanned can put text there, including instructions aimed at an AI assistant.
This server wraps every free-text value from DefectDojo in a pair of tags with a random 16-character hex suffix chosen for that value, for example <untrusted-data-3f9c0a7b1e2d4c58>...</untrusted-data-3f9c0a7b1e2d4c58>. A client or model recognizes the data by the matching suffix on the opening and closing tag. Text inside cannot close the wrapper early because it cannot guess the suffix. As a second layer, look-alike tags inside the text are escaped, bidirectional control characters are shown as code points such as [U+202E], and long fields are truncated. Tool descriptions and the server instructions tell the model to treat tagged text as data only. This lowers the risk but cannot remove it, so keep a person in the loop for write actions and review what the assistant proposes.
Local files
A prompt-injected assistant could try to upload local files, such as keys or dotfiles, to DefectDojo through import_scan. That is why file path imports are off until you name the folders in DEFECTDOJO_IMPORT_DIRS, and why hidden files are always refused. Keep scan reports in their own folder.
API key scope
The server can do anything the API key's user can do. Create a dedicated DefectDojo user for the assistant, give it access only to the products it needs, and keep writes off unless you need them. The key is sent only to DEFECTDOJO_URL, redirects are never followed, and the key is redacted from logs and error messages.
HTTP mode
Over stdio the server is only reachable by the client that started it. HTTP mode is for shared or remote setups:
export DEFECTDOJO_URL=https://defectdojo.example.com
export DEFECTDOJO_API_KEY=your-api-key
export DEFECTDOJO_MCP_AUTH_TOKEN=$(python -c "import secrets; print(secrets.token_urlsafe(32))")
defectdojo-mcp --transport http --host 127.0.0.1 --port 8000
The endpoint is http://127.0.0.1:8000/mcp, and /healthz answers without authentication for health checks. The server refuses to start in HTTP mode without one of these authentication modes:
- Token mode (
--http-auth token, the default). Every request must sendAuthorization: Bearer <DEFECTDOJO_MCP_AUTH_TOKEN>. All callers share the server's DefectDojo key, so give that key the narrowest permissions that work for everyone. - Pass-through mode (
--http-auth passthrough). Every request carries the caller's own DefectDojo key inX-DefectDojo-Api-KeyorAuthorization: Token <key>. The server holds no key of its own and DefectDojo enforces each caller's permissions.
The server binds to 127.0.0.1 by default and checks the Host and Origin headers to block DNS rebinding. To serve other machines, bind a non-loopback address, set DEFECTDOJO_MCP_ALLOWED_HOSTS to the public host name, and put a TLS-terminating reverse proxy in front. Keys and tokens travel in headers, so plain HTTP across a network exposes them.
Report security problems as described in SECURITY.md.
Compatibility
- Open-source DefectDojo 2.x and 3.x. The server uses long-standing API v2 endpoints and skips fields a version does not return. On older releases, filters that the instance does not know are ignored by DefectDojo, so the date filters on
list_findingsneed a release from late 2024 or newer.list_locationsuses the locations API in 3.x and falls back to endpoints on older releases. - DefectDojo Pro. Everything here works against Pro through the same API. Pro also includes its own built-in MCP server at
https://<your-instance>/mcpwith more capabilities, andget_instance_infomentions it when it detects Pro. - MCP. Built on the official MCP Python SDK 2.x and protocol version 2026-07-28, with fallback to earlier protocol versions for older clients.
- Python 3.11 or newer.
Development
git clone https://github.com/DefectDojo/defectdojo-mcp
cd defectdojo-mcp
uv sync
uv run pytest # unit tests with mocked HTTP
uv run ruff check .
uv run ruff format --check .
uv run mypy
The live test suite runs every tool against a real DefectDojo instance over stdio. Point it at a disposable instance, since it creates products, engagements and findings:
DEFECTDOJO_LIVE_URL=http://127.0.0.1:8080 DEFECTDOJO_LIVE_API_KEY=your-key uv run pytest -m live
See CONTRIBUTING.md for more.
License
BSD 3-Clause. See LICENSE.
Metadata
Release files for defectdojo-mcp-server 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| defectdojo_mcp_server-0.1.0.tar.gz | 66.4 kB | With provenance | Details for defectdojo_mcp_server-0.1.0.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| defectdojo_mcp_server-0.1.0-py3-none-any.whl | Python 3 | none | any | Details for defectdojo_mcp_server-0.1.0-py3-none-any.whl |
Total release size: 113.3 kB
Release files / defectdojo_mcp_server-0.1.0.tar.gz
| Download URL | defectdojo_mcp_server-0.1.0.tar.gz |
|---|---|
| Size | 66.4 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
e3ee79f722f63e6057c116414d43fa9d7c8b34ba9f1a90c40ddfd4407019db56
|
|
BLAKE2b-256 checksum How to use checksums |
b88dd211ab76aa68b5119dbaf05056e5275365d9693964c2f92f0a82c1fb6d1c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.16
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Nov 11, 2026.
Transparency logRelease files / defectdojo_mcp_server-0.1.0-py3-none-any.whl
| Download URL | defectdojo_mcp_server-0.1.0-py3-none-any.whl |
|---|---|
| Size | 46.9 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
1e0dc841bd4bb4a220c1d7aca7b8365532e7dc2c5482cecf109346139ddd080d
|
|
BLAKE2b-256 checksum How to use checksums |
9b29a29b6dff3ca141b2704ccb829f569c8d1842dad20d7c39ace8ef0c456de5
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.16
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Nov 11, 2026.
Transparency logSecurity for defectdojo-mcp-server 0.1.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
Full provenance
Both files in this release have been uploaded with provenance metadata.
Attestation for defectdojo_mcp_server-0.1.0.tar.gz
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Nov 11, 2026.
Transparency logA note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.