Ambassador
The sidecar taking over outbound hardening — mTLS, retries, circuit
breaker, observability — so the application only talks to localhost.
Problem
An ERP service must send INVOIC to 50 heterogeneous partners: AS2 at Walmart, AS4 at Stellantis, SFTP at Carrefour, HTTPS at Amazon Vendor. Each has its retry scheme, client certificate, endpoint, timeout policy. If the application code embeds all of that, it becomes a configuration hub. Any cert rotation triggers an application redeploy.
Forces
- Outbound protocols vary. AS2, AS4, SFTP, HTTPS, JMS — one per major partner, plus versions.
- Reliability patterns vary too. Retry, backoff, circuit breaker: configured per partner per SLA.
- Application code must stay simple. The business is not "send in mutual TLS 1.3 to walmart.com", it is "emit an INVOIC".
- The application language may lack libraries. Python does not have the best AS2 client; a Java sidecar provides it.
Solution
Deploy alongside the application container an ambassador container
(typically Envoy or a custom proxy). The business code calls http://localhost:9090/partner/walmart in plain HTTP.
The ambassador handles: dynamic DNS resolution, mTLS termination,
certificate rotation, partner-specific retries, circuit breaker,
OpenTelemetry export, latency measurement. The contract between app
and ambassador is stable (localhost + path); the external
configuration evolves without touching the code.
┌──────────────────────────────────────────────────────────┐
│ Pod │
│ ┌───────────────┐ localhost:9090 ┌─────────────────┐ │
│ │ App │ ─────────────────▶ │ Ambassador │ │
│ │ (plain HTTP) │ │ Envoy sidecar │ │
│ └───────────────┘ │ retries, mTLS, │ │
│ │ circuit breaker │ │
│ └────────┬────────┘ │
└────────────────────────────────────────────────│─────────┘
│ mTLS
▼
edi.partners (Walmart, Stellantis)
EDI implementation
Concrete case: in a Kubernetes EDI hub, deploy as a sidecar an
open-source AS2 connector (Mendelson AS2, OpenAS2, minimal Sterling
B2Bi). The Python application service POSTs JSON to localhost:8080/send/walmart; the ambassador converts
to AS2, S/MIME-signs, encrypts, sends over TLS 1.3, retrieves the
signed MDN, validates the signature, and republishes the event on
Kafka. Partner certificate rotation: kubectl rollout
restart of the sidecar, not the service. Cloud variant: AWS
App Mesh, Consul Connect, Linkerd — the ambassador is generated
automatically.
Anti-patterns
- Transparent ambassador on the code side. If the app must still know partner names and quirks, the abstraction brings nothing. The ambassador must hide complexity, not relocate it.
- Business logic in the ambassador. Putting EDIFACT→JSON mapping in the ambassador turns it into a Message Translator — another pattern, to keep separate.
- No circuit breaker. Without breaker, the ambassador retries forever against a downed partner and blocks the app via timeouts.
Related patterns
- Sidecar — parent pattern; the ambassador is an outbound-specialised sidecar.
- Smart Proxy — the Hohpe variant, more ESB-oriented.
- Circuit Breaker — always embedded in a production ambassador.
- Service Mesh — the ambassador generalised via mesh.
Sources
- Burns B., Oppenheimer D. — Design Patterns for Container-based Distributed Systems, HotCloud 2016. Academic source of the sidecar / ambassador / adapter trio. usenix.org — HotCloud 2016
- Microsoft Architecture Center — Ambassador pattern. learn.microsoft.com — Ambassador
- Indu R. — Cloud Native Patterns, Manning 2019. Chap. "Sidecar / Ambassador / Adapter". manning.com — Cloud Native Patterns
- Envoy — Outbound proxy mode. The reference implementation of an ambassador in production. envoyproxy.io — Architecture overview