SB SIEM MCP: Wazuh AI Agent
The problem
SIEM APIs assume a human clicking through dashboards, one query and one panel at a time. An LLM agent does not work like that. It wants to pull an alert, check the agent's health, cross-reference a MITRE technique and look at vulnerability posture in the same breath. There was no clean way to give it that without also giving it unrestricted access to a high-privilege system.
What it does
sb-siem-mcp is a local process your AI client spawns as a child, the same way it would spawn a language server or a linter. No Docker required, no containers, no agents to install. It points at the Wazuh you already have and exposes 28 typed tools over the Model Context Protocol.
It talks to both the Wazuh REST API on port 55000 for management operations and the Wazuh Indexer on port 9200 for alerts and vulnerabilities. That split matters: in Wazuh 4.x and 5.x, alerts and vulnerability data are indexer-only and simply are not available through the REST API. The IndexerClient handles the distinction transparently so the agent never has to care.
The nine domains are alerts and triage, threat hunting, compliance, agents and groups, CDB threat-intel lists, manager and cluster operations, security analysis, and incident response.
The design question
The interesting problem was never "how do I connect an LLM to Wazuh." It was "how do I connect an LLM to Wazuh without regretting it."
MCP helps because it gives the agent a typed, discoverable contract instead of a free-text prompt that generates raw API calls. You define exactly what the agent can do, and more importantly what it cannot. That distinction is the entire project.
On top of the contract there are six layers of defence: input validation with shell-metacharacter blocking and strict regex for agent IDs, IPs, CVEs and MITRE technique IDs; token-bucket rate limiting at 30 calls per 60 seconds for reads and 5 per 120 seconds for destructive operations; output sanitisation that redacts AWS keys, JWTs, SSH keys and passwords before anything reaches the model; append-only JSONL audit logging; a two-step confirmation gate with an expiring token on every destructive tool; and RBAC across four hierarchical roles.
Why the confirmation gate exists
Two of the 28 tools can change the world: run_active_response can trigger a firewall drop or a host-deny across your fleet, and agent_command executes on a remote endpoint. Both require confirm=True plus a one-time expiring token, and both write to the audit log before they act.
The failure mode this prevents is specific and realistic. A model that has misread the context should not be able to silently blackhole a production IP range. Making the destructive path require a second, deliberate round trip means a confused agent stalls instead of escalating.
Operating it
Seven Prometheus metrics are exposed on :9090: tool call counts by name and status, per-tool latency histograms, rate-limit rejections, API connectivity, audit entries, in-flight calls, and errors by type. If an agent starts hammering a tool or a Wazuh node goes dark, it shows up on a dashboard rather than in a support ticket.
The full tool surface is documented as an OpenAPI 3.0 spec with a Swagger UI at :8000/docs, generated from the same definitions the MCP server registers. CI runs a test matrix, and Dependabot, pip-audit and CodeQL run on every push plus a weekly schedule.
Scope and limits
Every project page on this site carries this section. If a tool is not ready for something, the honest place to say so is next to the claim, not three pages into a README.
- Independent third-party project, not affiliated with or endorsed by Wazuh Inc.
- The MCP HTTP endpoint has no built-in client authentication. Bind it to localhost, or put it behind a reverse proxy with auth.
- Targets Wazuh 4.x. Wazuh 5.x replaces the Indexer with a new storage back-end and will require changes.
- The docker-compose stack is a demo convenience. It disables several security features for local testing and should not be used in production as shipped.
Building something in this territory, or hiring for it?