AgentCore MCP Reverse Connector
README.md
# AgentCore MCP Reverse Connector on Amazon EKS
This project deploys a minimal MCP-compatible Python tool server on Amazon EKS. The pod opens an outbound secure WebSocket connection to `AGENTCORE_GATEWAY_ENDPOINT` and authenticates with `AGENTCORE_AUTH_TOKEN`.
The connector implements the MCP JSON-RPC methods required for tool discovery and invocation:
- `initialize`
- `tools/list`
- `tools/call`
- `ping`
It exposes two tools:
- `get_system_info`
- `echo_data`
## Architecture Note
Amazon Bedrock AgentCore Gateway documentation describes Gateway as an MCP endpoint for agents and as a service that can invoke configured targets such as Lambda, OpenAPI, Smithy, and remote MCP server endpoints. A reverse dial-out WebSocket connector requires your AgentCore Gateway endpoint, relay, or fronting service to support a persistent outbound WebSocket contract.
This implementation assumes that contract exists and that the gateway sends MCP JSON-RPC request messages over the WebSocket. If your Gateway is configured for a standard MCP server target instead, expose this server through a normal MCP HTTP/SSE endpoint or put it behind an internal/external load balancer and register that endpoint with AgentCore.
## Project Tree
```text
agentcore-mcp-eks/
├── .dockerignore
├── .gitignore
├── Dockerfile
├── Makefile
├── README.md
├── k8s/
│ ├── base/
│ │ ├── configmap.yaml
│ │ ├── deployment.yaml
│ │ ├── hpa.yaml
│ │ ├── kustomization.yaml
│ │ ├── namespace.yaml
│ │ ├── networkpolicy.yaml
│ │ ├── pdb.yaml
│ │ ├── service.yaml
│ │ └── serviceaccount.yaml
│ └── examples/
│ └── secret.example.yaml
├── requirements.txt
└── src/
├── pyproject.toml
└── agentcore_mcp_server/
├── __init__.py
├── __main__.py
├── config.py
├── connector.py
├── health.py
├── protocol.py
└── tools.py
```
## Prerequisites
- An existing Amazon EKS cluster with worker nodes that can egress to the AgentCore Gateway endpoint over TCP 443.
- `aws` CLI configured for the target AWS account.
- `kubectl` configured for the EKS cluster.
- Docker or another OCI-compatible image builder.
- Terraform or your preferred IaC workflow if you still need to create EKS.
- A container registry, for example Amazon ECR or GitHub Container Registry.
- Kubernetes Metrics Server if you want the HPA to scale on CPU metrics.
- Known values for:
- `AGENTCORE_GATEWAY_ENDPOINT`
- `AGENTCORE_AUTH_TOKEN`
## Build and Publish
Set your image name:
```bash
cd agentcore-mcp-eks
export IMAGE="123456789012.dkr.ecr.us-east-1.amazonaws.com/agentcore-mcp-server"
export TAG="0.1.0"
```
Build and push:
```bash
docker build -t "${IMAGE}:${TAG}" .
docker push "${IMAGE}:${TAG}"
```
Update the Deployment image in `k8s/base/deployment.yaml` or use Kustomize:
```bash
kubectl kustomize k8s/base
```
## Configure Kubernetes
Create the namespace first so the Secret can be created safely:
```bash
kubectl apply -f k8s/base/namespace.yaml
```
Create the auth token secret without storing a real token in Git:
```bash
kubectl -n mcp-system create secret generic agentcore-mcp-secret \
--from-literal=AGENTCORE_AUTH_TOKEN='replace-with-real-token'
```
Set the gateway endpoint by editing `k8s/base/configmap.yaml`:
```yaml
data:
AGENTCORE_GATEWAY_ENDPOINT: "wss://gateway.example.com/mcp/reverse"
MCP_SERVER_NAME: "eks-agentcore-mcp"
```
If you want to use the example Secret manifest instead, copy `k8s/examples/secret.example.yaml`, replace the placeholder, and apply it from a secure private location.
## Deploy
Apply the manifests:
```bash
kubectl apply -k k8s/base
```
Check rollout:
```bash
kubectl -n mcp-system rollout status deployment/agentcore-mcp-server
kubectl -n mcp-system get pods -l app.kubernetes.io/name=agentcore-mcp-server
```
Tail logs:
```bash
kubectl -n mcp-system logs deployment/agentcore-mcp-server -f
```
## Operational Checks
Port-forward the internal service for health checks:
```bash
kubectl -n mcp-system port-forward svc/agentcore-mcp-server 8080:8080
curl -fsS http://127.0.0.1:8080/healthz
curl -fsS http://127.0.0.1:8080/readyz
```
Expected behavior:
- `/healthz` returns `200` when the process is running.
- `/readyz` returns `200` only after the WebSocket connection to the gateway is established.
## Troubleshooting Gateway Connectivity
Check pod environment wiring without printing the token:
```bash
kubectl -n mcp-system describe pod -l app.kubernetes.io/name=agentcore-mcp-server
```
Look for connector log messages:
```bash
kubectl -n mcp-system logs deployment/agentcore-mcp-server --tail=200
```
Common issues:
- `AGENTCORE_GATEWAY_ENDPOINT is required`: the ConfigMap is missing or the key is misspelled.
- `AGENTCORE_AUTH_TOKEN is required`: the Secret is missing or the key is misspelled.
- Repeated connect failures: verify the endpoint starts with `wss://`, DNS resolves from inside the cluster, and node security groups/NACLs permit egress to TCP 443.
- Authentication failures: rotate the Secret and restart the Deployment with `kubectl -n mcp-system rollout restart deployment/agentcore-mcp-server`.
- Readiness never becomes healthy: confirm the gateway supports the reverse WebSocket connector contract and accepts MCP JSON-RPC messages over the socket.
- NetworkPolicy blocks traffic: start by applying the Deployment without `networkpolicy.yaml`, confirm connectivity, then reapply and tighten egress for your CNI.
Run an in-cluster DNS/connectivity test:
```bash
kubectl -n mcp-system run netcheck --rm -it --restart=Never \
--image=curlimages/curl:8.10.1 -- sh
```
Then inside the shell:
```sh
nslookup gateway.example.com
curl -vk https://gateway.example.com/
```
## Security Notes
- Do not commit real tokens. Use Kubernetes Secrets, External Secrets Operator, AWS Secrets Manager, or Sealed Secrets.
- The container runs as a non-root user with a read-only root filesystem and dropped Linux capabilities.
- The default Service is `ClusterIP`; there is no public inbound endpoint because the server dials out.
- The example NetworkPolicy allows DNS and outbound HTTPS. For strict FQDN egress controls, use a CNI that supports FQDN policies such as Cilium or Calico Enterprise and restrict access to the exact AgentCore Gateway hostname.
- Tool input schemas are fully inlined and do not use JSON Schema `$ref` or `$defs`.
## References
- [Amazon Bedrock AgentCore Gateway overview](https://docs.aws.amazon.com/bedrock-agentcore/latest/devguide/gateway.html)
- [AgentCore Gateway MCP usage](https://docs.aws.amazon.com/bedrock-agentcore/latest/devguide/gateway-using.html)
- [AgentCore Gateway MCP server targets](https://docs.aws.amazon.com/bedrock-agentcore/latest/devguide/gateway-target-MCPservers.html)
- [MCP Python SDK package](https://pypi.org/project/mcp/)
This server cannot be deployed
Maintenance
ActivityInactive
ResponsivenessNo issues