The EDI 214 is the message that tells a shipper where a load is. Formally it is the X12 Transportation Carrier Shipment Status Message, and every explanation of it online is written for North America, which is a problem if your lanes run Rotterdam to Milan. European road freight uses a different message for the same job, and increasingly uses neither, because the same facts now arrive over a road freight visibility API instead.
This is the status message on all three channels: what the 214 carries, what EDIFACT does in its place in Europe, and what the equivalent looks like as an event.
What the 214 actually contains
A 214 is a report, not an instruction. It belongs to a family: the 204 tenders the load, the 990 accepts or declines it, the 214 reports what happened to it and the 210 invoices for it. Sending a 214 for a load that was never tendered is a common and confusing error in a new connection.
The payload is smaller than the surrounding documentation suggests. Three things matter:
- The reference that identifies the shipment, carried in the B10 segment. If the carrier’s reference and yours differ and no cross-reference exists, nothing else in the message can be used.
- The status itself, carried in AT7: a status code, an optional reason code, and a date and time.
- Where it happened, carried in the location segments, usually as city, state or province and country rather than coordinates.
Everything else is optional and most implementations ignore it.
The status codes that carry the traffic
The X12 code list runs to dozens of values. In practice about a dozen carry almost all real traffic on a truckload or groupage lane:
- X3 arrived at pickup location
- CP completed loading at pickup location
- AM loaded on truck
- AF carrier departed pickup location with shipment
- X6 en route to delivery location
- X2 estimated date and time of arrival at consignee
- AG estimated delivery
- X1 arrived at delivery location
- D1 completed unloading at delivery location
- CD carrier departed delivery location
- AH attempted delivery
- SD shipment delayed
- CA shipment cancelled
A delay or exception code is only useful with its reason code alongside it. An SD on its own says the load is late, which the receiver already knows. SD with a reason distinguishing a border queue from a breakdown from a consignee who closed early is the difference between a status feed and a working exception process.
What Europe uses instead
X12 is a North American standard. European road freight runs on EDIFACT, and the status message is IFTSTA, the International Multimodal Status Report. It sits alongside IFTMIN for the transport instruction and IFTMAN for the arrival notice, the same family logic as the X12 set.
Structurally IFTSTA does the same three jobs: a reference that identifies the consignment, a status carried in the STS segment using UN/EDIFACT code lists for the status and its reason, a location in LOC and the timing in DTM. UN/CEFACT Recommendation 24 exists precisely to harmonise trade and transport status codes across these implementations.
The catch is that the code semantics are agreed per implementation guideline rather than universally. Two carriers can both send you a conformant IFTSTA and mean materially different things by the same status, particularly around what counts as arrival: at the gate, at the dock, or at the moment the driver reports it. This is why an EDI mapping is bespoke work per partner even when both sides are standards-compliant, and why connecting the fortieth carrier costs as much as the fourth.
The same events over an API
A visibility API expresses the same milestones as events rather than as a file. The set is deliberately small, because a small set of events that every carrier can produce beats a rich set that only three of them support: assigned, en route to pickup, arrived at pickup, loaded, departed, en route to delivery, arrived at delivery, unloaded, proof of delivery captured, exception raised.
Three differences change how the data behaves, and none of them is the format.
The event arrives when it happens. A 214 or an IFTSTA travels in a file on a transmission window. The event exists in your system at the end of that window, not at the moment the truck crossed the gate. Where the difference between a record and live information matters, it is the difference set out in the guide to track and trace in European trucking.
The timestamp can be machine-generated. A geofence crossing produces an arrival time nobody typed. A status message keyed by a driver or a planner produces an arrival time somebody typed, often at the end of the shift, and if that party would pay the detention it is not evidence.
Position is continuous rather than punctuated. A status message tells you the truck reached a milestone. A position feed tells you where it is between milestones, which is what makes a predicted arrival possible at all, as set out in the piece on how machine learning reaches high ETA accuracy.
Mapping between the three without losing meaning
Any shipper running mixed channels ends up maintaining a translation table. Four rules keep it honest.
- Normalise to your own event names, not to the incoming code. Decide internally what “arrived at delivery” means, in one sentence, and map X1, the corresponding IFTSTA status and the API event onto it. Storing raw codes and interpreting them at read time guarantees two teams interpret them differently.
- Record the source and the generation method with every event. Channel, and whether the timestamp came from a geofence, a driver app or a keyed entry. Every dwell, detention and on-time figure depends on that distinction, and it cannot be reconstructed later.
- Treat every event as replayable. EDI files are resent and webhooks are retried. Without an idempotency key built from the shipment reference, the status and the event time, a resend creates a second arrival and the dwell calculation silently doubles.
- Expect messages out of order. A departure can arrive before the arrival it follows. Order by event time rather than receipt time, and reject any state transition that is impossible rather than storing it.
The proof of delivery is the one milestone worth treating separately, because it carries a document and often a signature rather than just a timestamp, and the handling is covered in the guide to ePOD and driver apps.
None of this makes the 214 obsolete. If a North American partner sends one and it works, it works. What it is not is the European default, and building a status architecture around X12 semantics because the documentation was easiest to find is a mistake that surfaces two carriers later. Decide what your milestones mean first, then accept them from whichever channel each carrier can sustain, and keep the question of who operates the flows separate, as set out in the comparison of 3PL and 4PL models.


