• Threat Intelligence
  • AI Infrastructure Security
  • Honeypot Research

Automated Exploitation Campaigns Targeting OpenClaw Gateway Infrastructure

Our honeypot captured a sophisticated, multi-phase attack campaign targeting exposed OpenClaw Gateways. This report details the attack methodology, exploited vulnerabilities, and actionable defenses.

Automated Exploitation Campaigns Targeting OpenClaw Gateway Infrastructure

Executive Summary

AttributeDetail
First Observed2026-02-01 19:08:53 UTC
Attack OriginPortugal (185.180.141.19)
Attack Toolgitmc-org-mcp-scanner, raw JSON-RPC commands
Primary TargetOpenClaw Gateway WebSocket API (port 18789)

Bottom Line: Automated exploitation campaigns are actively targeting OpenClaw Gateway deployments. Attackers demonstrate accurate protocol knowledge, exploit authentication bypass vulnerabilities, and follow a systematic three-phase playbook to extract credentials and conversation history. Unpatched instances are at immediate risk.


1. Attack Overview

1.1 Background

OpenClaw is an AI agent gateway platform that exposes a WebSocket API on port 18789. Until recent patches, this API:

  • Defaulted to no authentication when unconfigured
  • Trusted all reverse-proxied connections as localhost
  • Exposed sensitive configuration and chat history to authenticated clients

We deployed a Beelzebub honeypot mimicking an OpenClaw Gateway to observe attacker behavior. The first probes arrived within 45 minutes.

1.1.1 Beelzebub Configuration

We deployed a Beelzebub honeypot configured to mimic OpenClaw Gateway responses across all standard endpoints.

Emulated Endpoints:

EndpointPurpose
/, /wsWebSocket handshake (101 upgrade)
/mcpMCP JSON-RPC endpoint
/sseServer-Sent Events transport
/uiControl UI interface
/tools/invokeTool invocation (returns 401)
/v1/chat/completionsOpenAI-compatible API
/v1/responsesOpenResponses API
/hooks/*Webhook triggers
/health, /status, /metricsService fingerprinting

Configuration

apiVersion: "v1"
protocol: "http"
address: ":18789"
description: "OpenClaw Gateway decoy"
commands:
  # --------------------------
  # WebSocket handshake decoy
  # --------------------------
  # Note: Sec-WebSocket-Accept here is static (not computed from Sec-WebSocket-Key).
  # This is enough to trick many scanners; strict WS clients may reject it.
  - regex: "^/$"
    headers:
      - "Server: openclaw-gateway"
      - "Connection: Upgrade"
      - "Upgrade: websocket"
      - "Sec-WebSocket-Version: 13"
      - "Sec-WebSocket-Accept: s3pPLMBiTxaQ9kYGzzhZRbK+xOo=" # dummy
      - "Cache-Control: no-store"
    statusCode: 101
    handler: ""

  - regex: "^/ws$"
    headers:
      - "Server: openclaw-gateway"
      - "Connection: Upgrade"
      - "Upgrade: websocket"
      - "Sec-WebSocket-Version: 13"
      - "Sec-WebSocket-Accept: s3pPLMBiTxaQ9kYGzzhZRbK+xOo=" # dummy
      - "Cache-Control: no-store"
    statusCode: 101
    handler: ""

  # --------------------------
  # Control UI (HTTP fallback)
  # --------------------------
  - regex: "^/ui/?$"
    headers:
      - "Content-Type: text/html; charset=utf-8"
      - "Server: openclaw-gateway"
      - "Cache-Control: no-store"
    statusCode: 200
    handler: |
      <!doctype html>
      <html>
      <head><meta charset="utf-8"><title>OpenClaw Gateway</title></head>
      <body>
        <h1>OpenClaw Gateway</h1>
        <p>Control UI is enabled.</p>
        <ul>
          <li><code>/tools/invoke</code></li>
          <li><code>/v1/chat/completions</code></li>
          <li><code>/v1/responses</code></li>
          <li><code>/hooks/*</code></li>
          <li><code>WS:</code> <code>/</code> or <code>/ws</code></li>
        </ul>
      </body>
      </html>

  # --------------------------
  # Basic probes
  # --------------------------
  - regex: "^/(health|status|metrics)$"
    headers:
      - "Content-Type: application/json"
      - "Server: openclaw-gateway"
      - "Cache-Control: no-store"
    statusCode: 200
    handler: |
      {"ok":true,"service":"openclaw-gateway","version":"0.0.0","note":"decoy"}

  # --------------------------
  # Tools Invoke (POST /tools/invoke)
  # Always enabled in real OpenClaw, but gated by auth/policy
  # --------------------------
  - regex: "^/tools/invoke$"
    headers:
      - "Content-Type: application/json"
      - "Server: openclaw-gateway"
      - 'WWW-Authenticate: Bearer realm="openclaw"'
      - "Cache-Control: no-store"
    statusCode: 401
    handler: |
      {"error":{"message":"Unauthorized","type":"auth_error","code":"invalid_api_key"}}

  # --------------------------
  # OpenAI-compatible (POST /v1/chat/completions) – often disabled by default
  # --------------------------
  - regex: "^/v1/chat/completions$"
    headers:
      - "Content-Type: application/json"
      - "Server: openclaw-gateway"
      - "Cache-Control: no-store"
    statusCode: 404
    handler: |
      {"error":{"message":"Not Found (endpoint disabled)","type":"not_found","code":"endpoint_disabled"}}

  # --------------------------
  # OpenResponses-compatible (POST /v1/responses) – often disabled by default
  # --------------------------
  - regex: "^/v1/responses$"
    headers:
      - "Content-Type: application/json"
      - "Server: openclaw-gateway"
      - "Cache-Control: no-store"
    statusCode: 404
    handler: |
      {"error":{"message":"Not Found (endpoint disabled)","type":"not_found","code":"endpoint_disabled"}}

  # --------------------------
  # Hooks (/hooks/wake, /hooks/agent, /hooks/<name>)
  # --------------------------
  - regex: "^/hooks/(wake|agent)$"
    headers:
      - "Content-Type: application/json"
      - "Server: openclaw-gateway"
      - 'WWW-Authenticate: Bearer realm="openclaw-hooks"'
      - "Cache-Control: no-store"
    statusCode: 401
    handler: |
      {"error":{"message":"Unauthorized hook","type":"auth_error","code":"invalid_hook_token"}}

  - regex: "^/hooks/[^/]+$"
    headers:
      - "Content-Type: application/json"
      - "Server: openclaw-gateway"
      - 'WWW-Authenticate: Bearer realm="openclaw-hooks"'
      - "Cache-Control: no-store"
    statusCode: 401
    handler: |
      {"error":{"message":"Unauthorized hook mapping","type":"auth_error","code":"invalid_hook_token"}}

  # --------------------------
  # Canvas hint (redirect to canvas host)
  # --------------------------
  - regex: "^/__openclaw__/canvas/?$"
    headers:
      - "Location: http://127.0.0.1:18793/__openclaw__/canvas/"
      - "Server: openclaw-gateway"
      - "Cache-Control: no-store"
    statusCode: 301
    handler: ""

  # --------------------------
  # Catch-all with LLM
  # --------------------------
  - regex: "^.*$"
    plugin: "LLMHoneypot"

For complete configuration, see Beelzebub API documentation.

1.2 Attacker Objectives

A successful compromise yields:

AssetImpact
API KeysAnthropic, OpenAI credentials for LLM abuse
Gateway CredentialsFull administrative access
Channel TokensTelegram, Discord, Slack bot takeover
Conversation HistoryComplete user-AI interaction logs
Node Infrastructure MapLateral movement in multi-node deployments

1.3 Key Findings

  1. Direct Protocol Attacks: Sending raw JSON-RPC commands for shell execution
  2. Protocol Downgrade Exploitation: Probes force minProtocol: 1 to target authentication weaknesses in pre-January 2026 releases
  3. Accurate Protocol Knowledge: 100% of probed methods map to real OpenClaw handlers—this is not guesswork
  4. Systematic Enumeration: A three-phase playbook (reconnaissance → enumeration → exploitation) extracts maximum value
  5. Client Impersonation: Attackers spoof legitimate client identifiers (openclaw-control-ui, moltbot-control-ui)

2. Vulnerability Analysis

2.1 Authentication Bypass (Patched January 2026)

Root Cause: Authentication defaulted to none when no token or password was configured.

// VULNERABLE CODE
const mode: ResolvedGatewayAuth["mode"] =
  authConfig.mode ?? (password ? "password" : token ? "token" : "none");

// PATCHED CODE
const mode: ResolvedGatewayAuth["mode"] =
  authConfig.mode ?? (password ? "password" : "token");

Impact: Full unauthenticated access to all gateway functions.

2.2 Reverse Proxy Trust Bypass (Patched January 2026)

Root Cause: Gateways behind nginx/Caddy/Traefik treated all proxied connections as trusted localhost.

// VULNERABLE CODE
const isLocalClient = isLocalGatewayAddress(clientIp);
// Problem: clientIp was the proxy's address (127.0.0.1), not the real client

// PATCHED CODE
const hasProxyHeaders = Boolean(forwardedFor || realIp);
const remoteIsTrustedProxy = isTrustedProxyAddress(remoteAddr, trustedProxies);
const hasUntrustedProxyHeaders = hasProxyHeaders && !remoteIsTrustedProxy;
const isLocalClient =
  !hasUntrustedProxyHeaders && isLocalGatewayAddress(clientIp);

Impact: Any external connection routed through an unconfigured reverse proxy bypasses authentication.

3. Attack Methodology

3.1 Three-Phase Attack Playbook

PhaseMethodsObjective
1. Reconnaissancehealth, system-presence, ping, versionConfirm target, fingerprint version
2. Enumerationagents.list, sessions.list, models.list, node.list, device.pair.listInventory assets, assess value
3. Exploitationconfig.get, chat.history, tool (exec)Extract credentials, read data, execute commands

3.2 Attack Techniques

Direct Command Execution

Raw JSON-RPC for shell access:

{"id": 1, "method": "tool", "params": {"args": {"command": "whoami"}, "name": "exec"}, "jsonrpc": "2.0"}
{"id": 4, "method": "tool", "params": {"args": {"command": "cat ~/.openclaw/agents/*/sessions/*.jsonl"}, "name": "exec"}, "jsonrpc": "2.0"}

Protocol Downgrade

Forcing older protocol versions to exploit patched vulnerabilities:

{
  "id": 1,
  "type": "req",
  "method": "connect",
  "params": {
    "client": {
      "id": "cli-client",
      "mode": "interactive",
      "version": "1.0.0",
      "platform": "linux"
    },
    "maxProtocol": 1,
    "minProtocol": 1
  }
}

Client Impersonation

Spoofing legitimate control UI clients to blend with normal traffic:

{
  "params": {
    "role": "operator",
    "client": {
      "id": "openclaw-control-ui",
      "mode": "webchat",
      "version": "dev"
    },
    "scopes": ["operator.admin", "operator.approvals", "operator.pairing"]
  }
}

3.3 Probed Methods vs. Real Handlers

Every probed method has a corresponding handler in OpenClaw source:

Probed MethodHandler LocationExposure Risk
node.listsrc/gateway/server-methods/nodes.ts:223Infrastructure mapping
chat.historysrc/gateway/server-methods/chat.ts:184Full conversation exfiltration
device.pair.listsrc/gateway/server-methods/devices.ts:33Device enumeration
channels.statussrc/gateway/server-methods/channels.ts:70Channel credential exposure
config.schemasrc/gateway/server-methods/config.ts:101Configuration structure
config.getsrc/gateway/server-methods/config.ts:*API keys, tokens (plaintext)

4. Technical Evidence

4.1 Attack Timeline

All times UTC on February 1, 2026.

TimePhaseActivity
19:08:53ReconInitial WebSocket probe (GET /)
19:08:54ReconMCP initialization via gitmc-org-mcp-scanner
19:08:54ReconSSE endpoint probe (/sse)
19:08:56ExploitDirect command execution attempts (whoami, file reads)
19:08:57ExploitProtocol downgrade attempt (minProtocol: 1)
19:08:58ExploitClient impersonation (moltbot-control-ui)
19:08:59EnumSystematic method enumeration (9-request sequence)
19:09:00ReconGeneric API discovery (ping, echo, version, etc.)
19:09:01ExploitAlternative frame type probing
19:09:02ExploitMalformed JSON/parser fuzzing

Total attack duration: ~9 seconds for complete reconnaissance-to-exploitation cycle.

4.2 Scanner Identification

{
  "clientInfo": {
    "name": "gitmc-org-mcp-scanner",
    "version": "1.0.0"
  },
  "protocolVersion": "2025-06-18",
  "capabilities": {
    "sampling": {},
    "elicitation": {},
    "roots": { "listChanged": true }
  }
}

4.3 Full Enumeration Sequence

Captured from a single WebSocket session:

{"id": "req-1", "type": "req", "method": "connect", "params": {...}}
{"id": "req-2", "type": "req", "method": "health", "params": {}}
{"id": "req-3", "type": "req", "method": "system-presence", "params": {}}
{"id": "req-4", "type": "req", "method": "agents.list", "params": {}}
{"id": "req-5", "type": "req", "method": "sessions.list", "params": {}}
{"id": "req-6", "type": "req", "method": "config.get", "params": {}}
{"id": "req-7", "type": "req", "method": "models.list", "params": {}}
{"id": "req-8", "type": "req", "method": "skills.status", "params": {}}
{"id": "req-9", "type": "req", "method": "cron.list", "params": {}}

4.4 Version Targeting Evidence

Probe CharacteristicTarget Version
minProtocol: 1, maxProtocol: 1Pre-January 2026 (no device identity)
minProtocol: 3, maxProtocol: 3Current releases
role: "operator" without device blockOlder releases
role: "user" with webchat modeTesting privilege bypass

5. Indicators of Compromise

5.1 Network IOCs

IP Addresses:
  - 185.180.141.19 # Portugal, Lisbon metropolitan area

User-Agent Patterns:
  - python-httpx/*
  - Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/66.0.3359.117 Safari/537.36

Ports:
  - 18789/tcp (OpenClaw Gateway default)

5.2 Request Signatures

# MCP Scanner Initialization
- method: POST
  path: /mcp
  body_contains: '"method":"initialize"'
  body_contains: 'mcp-scanner'

# Direct Command Execution
- method: POST
  body_contains: '"method":"tool"'
  body_contains: '"name":"exec"'

# Protocol Downgrade
- body_contains: '"minProtocol": 1'
- body_contains: '"maxProtocol": 1'

# Client Impersonation
- body_contains: '"id":"moltbot-control-ui"'
- body_contains: '"id":"openclaw-control-ui"'

# Credential Extraction
- body_contains: '"method":"config.get"'
- body_contains: '"method":"chat.history"'

# Infrastructure Enumeration
- body_contains: '"method":"node.list"'
- body_contains: '"method":"agents.list"'
- body_contains: '"method":"sessions.list"'

6. Detection & Hunting

6.1 Sigma Detection Rule

title: OpenClaw Gateway Exploitation Attempt
id: b2c3d4e5-f6a7-8901-bcde-f23456789012
status: experimental
description: Detects MCP protocol scanning and exploitation attempts targeting OpenClaw AI agent infrastructure
author: Beelzebub Security Lab
date: 2026/02/01
references:
  - https://github.com/mariocandela/beelzebub
  - https://openclaw.ai/
logsource:
  category: webserver
  product: any

detection:
  # Phase 1: Scanner Initialization
  scanner_init:
    cs-method: POST
    cs-uri-stem|contains: "/mcp"
    request_body|contains|all:
      - '"method":"initialize"'
      - "mcp-scanner"

  # Phase 2: Direct Exploitation
  tool_execution:
    request_body|contains|all:
      - '"method":"tool"'
      - '"name":"exec"'

  credential_extraction:
    request_body|contains:
      - '"method":"config.get"'

  protocol_downgrade:
    request_body|contains|all:
      - '"minProtocol"'
      - ": 1"

  # Phase 3: Enumeration
  infrastructure_enum:
    request_body|contains:
      - '"method":"node.list"'
      - '"method":"agents.list"'
      - '"method":"sessions.list"'
      - '"method":"chat.history"'

  # Client Impersonation
  client_spoof:
    request_body|contains:
      - "moltbot-control-ui"
      - "openclaw-control-ui"

  condition: scanner_init or tool_execution or credential_extraction or protocol_downgrade or infrastructure_enum or client_spoof

falsepositives:
  - Legitimate MCP client initialization from known internal IPs
  - Authorized security testing

level: high

tags:
  - attack.reconnaissance
  - attack.t1595
  - attack.t1046
  - attack.credential_access
  - attack.t1552

6.2 Hunting Queries

Splunk:

index=webserver sourcetype=access_combined
| search (uri_path="/mcp" OR uri_path="/ws" OR uri_path="/sse")
| where match(request_body, "(?i)(config\.get|chat\.history|node\.list|method.*tool.*exec)")
| stats count by src_ip, uri_path, request_body
| where count > 3

Elastic/KQL:

http.request.body.content: (*"method":"config.get"* OR *"method":"chat.history"* OR *"method":"node.list"* OR *"name":"exec"*)
AND url.path: ("/mcp" OR "/ws" OR "/sse")

7. Remediation Guidance

PriorityActionCommand/Config
P0Update OpenClawVersions before January 26, 2026 are vulnerable
P0Verify authenticationopenclaw config get gateway.auth
P0Block exposed portsFirewall port 18789 from public access

7.1 Network Architecture

DO NOT expose the OpenClaw gateway directly to the internet.

Recommended access patterns:

  • Local development: Bind to localhost only
  • Remote access: Tailscale Serve or VPN with IP allowlisting
  • Production: Private network with authenticated API gateway

7.2 Credential Rotation

If you suspect compromise, rotate immediately:

  1. Anthropic API keys
  2. OpenAI API keys
  3. Gateway authentication tokens
  4. Channel tokens (Telegram, Discord, Slack)
  5. Any credentials stored in OpenClaw config

7.3 Monitoring Implementation

Deploy detection rules from Section 6 and monitor for:

  • POST requests to /mcp, /ws, /sse
  • JSON-RPC tool method with exec name
  • config.get and chat.history requests
  • Protocol downgrade attempts (minProtocol: 1)
  • Spoofed client identifiers

8. Framework Mapping

Observed BehaviorMITRE ATT&CKMITRE ATLASOWASP API 2023OWASP Agentic 2026
Protocol enumerationT1595 Active ScanningAML.T0006 Active ScanningAPI9 Improper Inventory
Service fingerprintingT1046 Network Service Discovery
AI endpoint probingT1595 Active ScanningAML.T0040 AI Model Inference API
Tool invocation/RCEAML.T0053 AI Agent Tool InvocationASI02 Tool Misuse
System discoveryT1082 System Info DiscoveryAML.T0050 Command Interpreter
Config discoveryAML.T0084 Discover AI Agent Config
Credential theftAML.T0083 Creds from AI Agent ConfigAPI5 Broken Function AuthASI03 Privilege Abuse
Client impersonationT1078 Valid AccountsAML.T0074 MasqueradingAPI2 Broken AuthenticationASI03 Privilege Abuse
Parser fuzzingAPI8 Security Misconfiguration

The Beelzebub team is dedicated to making the internet a better and safer place ❤️

Try Our Managed Platform

Security deception runtime framework with zero false positives
Continuous validation via automated AI Red Teaming
Real-time malware analysis via our CTI Hub
Instant threat containment driven by the AI SOC