Deploy a Hybrid reShapr Proxy
Use this procedure to run a reShapr proxy close to MCP clients or backend APIs while its configuration remains managed by an existing control plane.
The proxy initiates the control-plane connection and registers a logical Gateway. MCP requests and backend API calls use the routes you configure; they are not relayed through the control plane as part of proxy synchronization.
Prerequisites​
You need:
- a reShapr
1.0.0control plane reachable from the proxy over gRPC; - the reShapr
1.0.0CLI, authenticated withreshapr login; - Docker or Podman on the proxy host;
curlandjqfor verification;- a Service and Configuration Plan for a non-destructive backend operation;
- local access to port
7777for this verification, or a separately configured TLS proxy for remote MCP clients.
The examples use Docker. Set CONTAINER_ENGINE=podman to use the same commands with Podman.
export CONTAINER_ENGINE=docker
export RESHAPR_IMAGE=registry.reshapr.io/reshapr/reshapr-proxy:1.0.0
1. Select a Gateway Group​
List the Gateway Groups available to your organization:
reshapr gateway-group list
Record the ID and labels of an existing group, or create a dedicated group:
reshapr gateway-group create "Hybrid production" \
--labels '{"environment":"production","location":"customer-network"}'
The command returns a generated ID. Store that value for later commands:
export GATEWAY_GROUP_ID='<gateway-group-id>'
The labels advertised for the proxy's Gateway in step 3 must match this group's labels. The CLI accepts a JSON object, while RESHAPR_GATEWAY_LABELS uses semicolon-separated key=value pairs. Labels select configuration; they do not establish network or security boundaries.
2. Create a dedicated Gateway token​
Create an API token with the shortest validity that fits your operating procedure:
reshapr api-token create hybrid-gateway-01 --validity-days 30
The CLI displays the token once. Store it in your secret manager. To avoid placing it in shell history for this session, read it into an environment variable:
read -r -s -p 'Gateway API token: ' RESHAPR_CTRL_TOKEN
export RESHAPR_CTRL_TOKEN
printf '\n'
Use a dedicated token per operational boundary so that it can be rotated or revoked without affecting unrelated proxy deployments.
3. Start the proxy​
Set the control-plane address. This procedure advertises localhost:7777 and verifies the MCP endpoint from the proxy host over HTTP. Do not include a URL scheme in either hostname value.
export RESHAPR_CTRL_HOST='<control-plane-host>'
export RESHAPR_CTRL_PORT='443'
export RESHAPR_GATEWAY_FQDNS='localhost:7777'
The following command expects TLS on the control-plane connection. For a trusted development network that deliberately uses plaintext gRPC, set RESHAPR_CTRL_TLS_PLAINTEXT=true and use its plaintext port instead.
${CONTAINER_ENGINE} run --detach \
--name reshapr-hybrid-gateway \
--restart unless-stopped \
--publish 7777:7777 \
--env RESHAPR_CTRL_HOST="${RESHAPR_CTRL_HOST}" \
--env RESHAPR_CTRL_PORT="${RESHAPR_CTRL_PORT}" \
--env RESHAPR_CTRL_TLS_PLAINTEXT=false \
--env RESHAPR_CTRL_TOKEN="${RESHAPR_CTRL_TOKEN}" \
--env RESHAPR_GATEWAY_ID=hybrid-gateway-01 \
--env RESHAPR_GATEWAY_FQDNS="${RESHAPR_GATEWAY_FQDNS}" \
--env 'RESHAPR_GATEWAY_LABELS=environment=production;location=customer-network' \
"${RESHAPR_IMAGE}"
Use a unique RESHAPR_GATEWAY_ID for each running proxy. This value identifies the logical Gateway registered by that proxy. If the host cannot reach the control plane, check DNS, egress firewall rules, the configured port, and the TLS mode before changing the registration settings.
4. Check readiness​
Query the proxy locally:
curl --fail --silent http://localhost:7777/q/health/ready | jq '.status'
The expected status is "UP". If readiness fails, inspect the startup and registration messages:
${CONTAINER_ENGINE} logs --tail 100 reshapr-hybrid-gateway
Readiness confirms that the proxy completed its initial connection and Gateway registration. It does not confirm that a particular Exposition targets this Gateway.
5. Target the Gateway Group​
Create an Exposition from an existing Configuration Plan and target the group selected in step 1:
export CONFIGURATION_PLAN_ID='<configuration-plan-id>'
reshapr expo create \
--configuration "${CONFIGURATION_PLAN_ID}" \
--gateway-group "${GATEWAY_GROUP_ID}" \
--name hybrid-endpoint
The structured creation response contains endpoint details but not the Exposition ID. Resolve the unique ID by the name just created:
export EXPOSITION_ID="$(
reshapr expo list --all --output json \
| jq -er '.[] | select(.name == "hybrid-endpoint") | .id'
)"
Confirm that the Exposition is active and that ENDPOINTS contains the hostname advertised by the proxy's registered Gateway:
reshapr expo list
reshapr expo get "${EXPOSITION_ID}"
If the Exposition remains inactive, compare the proxy's RESHAPR_GATEWAY_LABELS with the labels shown by reshapr gateway-group list, then inspect the proxy logs.
6. Verify the MCP endpoint​
Build the MCP URL from the Exposition ID. With the direct local configuration in this guide, it uses HTTP:
export MCP_URL="http://localhost:7777/mcp/${EXPOSITION_ID}"
Discover the stateless MCP server:
curl --silent --show-error \
--header 'Content-Type: application/json' \
--header 'Accept: application/json, text/event-stream' \
--header 'MCP-Protocol-Version: 2026-07-28' \
--header 'Mcp-Method: server/discover' \
--data '{"jsonrpc":"2.0","id":1,"method":"server/discover","params":{"_meta":{"io.modelcontextprotocol/protocolVersion":"2026-07-28","io.modelcontextprotocol/clientInfo":{"name":"reshapr-docs","version":"1.0.0"},"io.modelcontextprotocol/clientCapabilities":{}}}}' \
"${MCP_URL}" | jq '.result | {supportedVersions, capabilities}'
The response must include 2026-07-28 in supportedVersions. List the exposed Tools:
curl --silent --show-error \
--header 'Content-Type: application/json' \
--header 'Accept: application/json, text/event-stream' \
--header 'MCP-Protocol-Version: 2026-07-28' \
--header 'Mcp-Method: tools/list' \
--data '{"jsonrpc":"2.0","id":2,"method":"tools/list","params":{"_meta":{"io.modelcontextprotocol/protocolVersion":"2026-07-28","io.modelcontextprotocol/clientInfo":{"name":"reshapr-docs","version":"1.0.0"},"io.modelcontextprotocol/clientCapabilities":{}}}}' \
"${MCP_URL}" | jq '.result.tools[] | {name, description}'
Choose a read-only Tool whose backend effect you understand, then call it with valid arguments:
export TOOL_NAME='<read-only-tool-name>'
export TOOL_ARGUMENTS='{}'
jq -n \
--arg name "${TOOL_NAME}" \
--argjson arguments "${TOOL_ARGUMENTS}" \
'{jsonrpc:"2.0",id:3,method:"tools/call",params:{name:$name,arguments:$arguments,_meta:{"io.modelcontextprotocol/protocolVersion":"2026-07-28","io.modelcontextprotocol/clientInfo":{name:"reshapr-docs",version:"1.0.0"},"io.modelcontextprotocol/clientCapabilities":{}}}}' | \
curl --silent --show-error \
--header 'Content-Type: application/json' \
--header 'Accept: application/json, text/event-stream' \
--header 'MCP-Protocol-Version: 2026-07-28' \
--header 'Mcp-Method: tools/call' \
--header "Mcp-Name: ${TOOL_NAME}" \
--data @- \
"${MCP_URL}" | jq '.result'
A successful, expected backend response verifies the client-to-proxy and proxy-to-backend paths. It does not prove that other Tools or network routes are correctly configured.
Roll back​
Delete the Exposition created by this procedure before removing its dedicated Gateway Group:
reshapr expo delete "${EXPOSITION_ID}"
${CONTAINER_ENGINE} rm --force reshapr-hybrid-gateway
List API tokens, then delete the dedicated token by its generated ID:
reshapr api-token list
reshapr api-token delete '<api-token-id>' --force
If you created the Gateway Group only for this procedure and no other Exposition uses it, remove it:
reshapr gateway-group delete "${GATEWAY_GROUP_ID}"
Deleting the token prevents later registration with that credential. A proxy that is already running can retain its last synchronized configuration during a control-plane connectivity loss, so stop the container as well when access must end immediately.
Result​
You now have a reShapr 1.0.0 proxy running in another trust domain, registered as a logical Gateway with a dedicated credential, selected through Gateway Group labels, and verified through its MCP endpoint.
Limits​
- The topology does not by itself prove data residency or compliance. Validate DNS, routing, proxies, identity providers, observability exporters, and backend dependencies.
- Proxy-to-control-plane TLS depends on
RESHAPR_CTRL_TLS_PLAINTEXT=falseand a correctly configured control-plane TLS endpoint. MCP client ingress and backend TLS are separate boundaries. - Remote MCP clients need a TLS ingress, load balancer, or reverse proxy. Configure it first, then advertise its host and optional port through
RESHAPR_GATEWAY_FQDNSinstead oflocalhost:7777. - Live configuration propagation is not a zero-downtime upgrade or rollback guarantee.
- A production deployment also needs durable secret injection, ingress TLS, resource limits, health supervision, logging, and an image update policy.
Next step​
Read Deployment Models and Trust Boundaries for the complete traffic map and Control Plane to Proxy Synchronization for registration and recovery behavior.
For production Kubernetes controls, continue with Deploy reShapr on Kubernetes for Production.