envoy-mcp-openapi-processor

mcp
Security Audit
Warn
Health Warn
  • License — License: MIT
  • Description — Repository has a description
  • Active repo — Last push 0 days ago
  • Low visibility — Only 7 GitHub stars
Code Pass
  • Code scan — Scanned 8 files during light audit, no dangerous patterns found
Permissions Pass
  • Permissions — No dangerous permissions requested

No AI report is available for this listing yet.

SUMMARY

An Envoy external processor that transforms Model Context Protocol (MCP) requests into upstream HTTP API calls based on OpenAPI specifications.

README.md

envoy-mcp-openapi-processor

An Envoy external processor
that transforms Model Context Protocol (MCP) requests into upstream HTTP API calls
based on OpenAPI specifications.

The external processor server communicates only with Envoy over gRPC via a Unix domain socket. Envoy owns all
downstream client and upstream service connections, while the processor inspects and can mutate request and response
data relayed by Envoy.

Installation

go get github.com/ing-bank/envoy-mcp-openapi-processor

Quick Start

See examples/mcp-server for a complete working example including Envoy proxy configured to use the
envoy-mcp-openapi-processor server.

OpenTelemetry

To enable export of logs and traces to an OpenTelemetry collector, use one of the options below. If neither is used, the server runs with a no-op tracer provider and a no-op logger.

Option 1: Use provided initialization functions

package main

import (
	"context"

	mcp_proc "github.com/ing-bank/envoy-mcp-openapi-processor"
)

func main() {
	telemetryConfig := mcp_proc.TelemetryConfig{
		OtelEndpoint:   "otel-collector:4317",
		ServiceName:    "mcp-sidecar",
		ServiceVersion: "1.0.0",
	}
	ctx := context.Background()
	err := mcp_proc.InitLogger(telemetryConfig)
	// ...
	tracerShutdown, err := mcp_proc.InitTracer(ctx, telemetryConfig)
	// ...
	var cfg mcp_proc.Config
	// ...
	mcp_proc.RunServer(ctx, &cfg)
}

Option 2: Bring your own provider

Set the global tracer provider by calling otel.SetTracerProvider(myTracerProvider) and the global zap logger by calling zap.ReplaceGlobals(myLogger) before starting the server.

Development

Tests

To run all tests, execute the following command:

make test

To check the test coverage, execute the following command:

make coverage-check

E2E tests

To run the end-to-end suite (spins up Envoy, the processor, and a mock upstream via Docker Compose, then exercises MCP <=> REST translation), execute the following command:

make e2e

Requires Docker. On failure, container logs are captured in e2e/last-run.log.

Fuzz tests

Run server handler fuzz tests one at a time:

make fuzz-request
make fuzz-response

Each command runs until stopped with Ctrl+C and reports any issues found.

DNS Rebinding Protection

The processor validates the Host/:authority and Origin headers of every
request. By default only loopback hostnames are accepted: localhost, 127.0.0.1 and
::1 (any port); anything else is refused with HTTP 403. This protects unauthenticated
localhost deployments against DNS rebinding attacks where a malicious website's DNS resolves
to 127.0.0.1 so the victim's browser sends same-origin requests to the local server.

A missing Host header is rejected (fail closed). A missing Origin header
is accepted (non-browser clients do not send one), but a present Origin
must be a URL whose hostname is allowed.

Deployments serving other domains configure them via Config.AllowedHosts:

cfg := &mcp_proc.Config{
    // ...
    AllowedHosts: []string{"mcp.example.com"},
}

Matching is case-insensitive and ignores ports. A non-empty list replaces
the localhost default — include "localhost" explicitly if it should remain
allowed.

Each entry is one of:

  • "*" — match any host. This disables DNS rebinding protection, so use it only
    on trusted networks.
  • "*.example.com" — match any subdomain at any depth (foo.example.com,
    a.b.example.com) but not the apex example.com.
  • "mcp.example.com" — exact match.

Security Checklist

Before deploying to production, we advise to verify if the following controls are in place

Container Security

  • Container runs as non-root user
  • Read-only root filesystem where possible
  • No privileged mode
  • Resource limits (CPU, memory) configured
  • seccomp profile applied
  • AppArmor/SELinux enabled
  • Container image scanned for CVEs
  • Image signed and verified

Envoy Configuration

  • TLS configured for downstream connections
  • TLS configured for upstream connections
  • Buffer limits set (≤32KB for edge deployments)
  • Connection limits configured
  • Stream limits configured (≤100 concurrent for HTTP/2)
  • Timeouts configured (connection, stream, request)
  • Overload manager enabled
  • Admin endpoint restricted to localhost
  • use_remote_address: true for edge deployments
  • Path normalization enabled
  • headers_with_underscores_action: REJECT_REQUEST

Reviews (0)

No results found