— May 15, 2026 · 13 min read
The EDI integration patterns that truly stood the test of time
Hohpe and Woolf published Enterprise Integration Patterns in 2003 — a catalogue of 65 recipes that has irrigated every B2B middleware since. In 2026, eight of these patterns have become the implicit backbone of any serious EDI integration. A walkthrough of what works, why, and how it is instrumented.
The catalogue as a shared language
Enterprise Integration Patterns (EIP) lists 65 integration patterns organised in six families: channels, message construction, routing, transformation, endpoints, and observation. Twenty years on, the book is still quoted almost weekly in internal RFCs across major integration platforms (MuleSoft, Apache Camel, Boomi). Its strength is less invention than naming. Putting a name on a behaviour lets distant teams understand each other in five words: "this route is a content-based router", "this flow needs a claim check" — and everyone knows what to code.
All eight patterns selected here trace back to 2003 or earlier (the circuit breaker was codified by Nygard in 2007 and Fowler in 2014). All are proven on real-world EDIFACT, X12, UBL or JSON-on-webhook flows. None claims to be new: they are stabilised tools, and that is precisely why they have endured.
1. Idempotency on the control key
The idempotency
pattern guarantees that receiving a message twice (replay, duplicate, AS2
retransmission) does not produce two business effects. In EDI, the idempotency key
is almost always already present on the message: in EDIFACT it is the tuple
UNB+UNOC:3+SENDER+RECEIVER+20260515:1023+REF12345, where REF12345 is
the interchange control reference (data element 0020 of the UNB segment). In X12
it is segment ISA-13 (Interchange Control Number).
The practical implementation reduces to a SQL table with the key as the unique
column and a status (received, processed, rejected). When a message arrives, the
consumer issues an INSERT … ON CONFLICT DO NOTHING; if the insert is
rejected, the message is a duplicate and the consumer returns the same
acknowledgment as the first time — not a fresh ACK that would panic the sender.
Real case: in 2024 at a Belgian wholesaler, a PEPPOL access point replayed an INVOIC 47 times due to a misconfigured retry. Without idempotency on the ERP side it would have meant 47 duplicate payments. With idempotency, it was 47 times the same MDN returned, with zero business work.
2. Dead Letter Channel for repeated rejections
The Dead Letter Channel pattern (DLC) — EIP 119 — answers a simple question: what to do with a message that fails processing multiple times? In EDI, this most commonly appears as a recurring negative CONTRL. A partner sends an ORDERS every hour; for reason X (missing mandatory field, line without GTIN) it fails. Without a DLC, the integration engine blocks, alerts, and the whole integration line freezes.
With a DLC, the message moves to a dedicated channel (typically a separate queue
or a /edi/dlc/ folder) after a fixed number of attempts (say 3). The
operator can inspect, fix, and replay the message manually — without blocking the
pipeline for the other partners. The DLC's role is therefore to isolate poison
without swallowing the chain.
3. Circuit Breaker for partner outages
The Circuit
Breaker — popularised by Michael Nygard in Release It! in 2007 and
codified by Martin Fowler in 2014 — handles an adjacent case: what to do when the
remote partner falls over? If a partner's PEPPOL access point has been returning
503 Service Unavailable for two hours, retrying each message
immediately is counter-productive.
The circuit breaker opens the circuit after a failure threshold (say 5 consecutive failures), queues new messages, and only allows sends again after a timeout (typically 5 minutes) or a success in "half-open" mode. That protects the pipeline from error cascades and gives the partner time to recover.
4. The PO ↔ ASN ↔ INVOIC saga
The saga — pattern described in the 1987 SAGAS paper by Garcia-Molina and Salem, then revived by Garcia-Molina himself and the microservice architects from 2015 — models a long-running non-atomic transaction. In EDI, it is exactly the three-way match: a purchase order (ORDERS or X12 850), a despatch advice (DESADV or X12 856), an invoice (INVOIC or X12 810). The three messages must be coherent — quantities, prices, references — but may arrive at very different times (PO in January, ASN in March, invoice in April).
Implementing this saga amounts to keeping a state machine per PO number:
created → shipped → invoiced → paid, with compensations on failure
(cancel PO, return ASN, credit note). Modern ERPs (SAP S/4 Order Fulfillment,
Oracle Fusion) embed this machine natively; on end-to-end integrations, it is
typically the integration engine (Mirth, Boomi, Stedi) that carries it.
5. Claim Check for attachments
The Claim Check pattern — EIP 358 — solves a practical problem: how to transport a large piece of data attached to a message without weighing down the queue? The data is stored on a separate endpoint (S3, blob storage) and only an identifier ("cloak- room ticket") travels with the message. The consumer fetches the data on arrival.
In EDIFACT, claim check is natively implemented by the FII
segment in some messages, but the most common modern use case is different: an
INVOIC needing to reference an attachment (PDF, photo, contract). Rather than
embedding the PDF in base64 inside the XML — which Factur-X does but at
significant cost on volumes — the PDF is deposited on S3 and only the signed URL
ships inside cac:AdditionalDocumentReference.
6. Content-Based Router at the boundary
The Content- Based Router — EIP 230 — inspects message content to decide destination. In EDI, this is the typical case of a single ingress endpoint receiving all of a partner's flows: ORDERS, ORDRSP, INVOIC, DESADV all arrive on the same AS2 endpoint, and the engine checks the message's UNH-1 header to route: ORDERS→procurement ERP, ORDRSP→procurement ERP, INVOIC→accounting, DESADV→logistics.
This pattern, mundane in API middlewares, remains central in EDI architectures because external partners only configure one AS2 endpoint per relationship. The content-based router is therefore the first filter on the inbound side. Its typical implementation is an XPath or XSLT match on the first few segments.
7. Message Translator (the mapping)
The Message Translator — EIP 85 — is the backbone of the entire EDI chain. Converting an EDIFACT D.96A ORDERS into the internal ERP's JSON is a bilateral mapping, usually written in XSLT, in code (Java/Python/Go), or with a graphical mapper (Boomi, Talend, Mirth Connect). What sets a good mapping apart from a bad one: handling cardinalities, code lists (qualifiers), and defaults when the sender omits an optional field.
The 2026 reflex is to frame these mappings with contract tests: a fixture set (example ORDERS) paired with its expected transformation (expected JSON), versioned in the repo. Any mapping change is measured against those fixtures — rare discipline ten years ago, banal today. The topic is covered in more detail on the Testing EDI pipelines page.
8. Canonical Data Model for hub-and-spoke
The Canonical Data Model — EIP — answers the combinatorial problem of N-to-N integrations. With 5 internal ERPs and 200 external partners, without a CDM one could write up to 1000 mappings (5 × 200). With an intermediate CDM, one writes 205 mappings (5 internal to CDM + 200 external to CDM).
The CDM is typically defined in JSON Schema or XML Schema, proprietary to the company. It represents a "canonical" PO with every business property, independent from any external standard. Inbound mappings translate ORDERS D.96A, ORDERS D.01B, X12 850, cXML OrderRequest, or UBL Order into this CDM; outbound mappings from the CDM to internal ERPs no longer depend on the source format.
The practical effect: adding a 201st partner only costs one mapping (to the CDM), not five. That scaling effect is what distinguishes mature integration platforms from old-school point-to-point setups.
What did not hold up
Symmetrically, it is instructive to call out three patterns that had their moment and are less central today than 2003 would have predicted:
- The centralised Message Broker as embodied by heavy ESBs (IBM Integration Bus, Oracle Service Bus). The pattern itself still holds, but the centralised implementation has been eroded by microservices and decentralised buses (Kafka, RabbitMQ, NATS). The broker did not disappear: it atomised.
- The Process Manager (EIP 312) as a central BPEL engine. The pattern remains valid, but BPEL as a language has been replaced by simpler orchestrators (Temporal, AWS Step Functions, lightweight Camunda BPMN). The concept survives, the historical tech is gone.
- The universal Message Bus as imagined by Hohpe — a single channel on which every service publishes and subscribes. Practice has shown that a single shared bus creates strong cross-team coupling; modern architectures prefer a federation of specialised queues (by domain, by throughput constraint).
The catalogue as positive debt
The peculiar merit of the eight patterns above is that they have stayed smaller than the technologies that carry them. Idempotency, claim check, circuit breaker, content-based router: each fits on a page and is re-implementable in 100 lines. They survive migrations because they describe an intent, not a tech. That is precisely why they have become the shared language of EDI and API integrators in 2026, interchangeably.
For anyone preparing a new integration in 2026, the healthy reflex is less about chasing the latest platform and more about explicitly qualifying which patterns are active on each edge of the graph. A edge × pattern matrix in the architecture doc usefully replaces 30 pages of prose. The full catalogue — 65 patterns — lives on ediverse on the Patterns page, organised by family.