Jul 2026 • 7 min read
When the canonical model becomes the interface
Why a technically correct interchange model can become the wrong contract for a human-facing workflow.
The backend problem was real
Canonical models solve a legitimate systems problem. When several sources describe the same domain differently, a shared model gives ingestion, transformation, validation, and publication a stable language.
I saw this while working on a transport-data platform. Source datasets arrived in different shapes, while downstream consumers expected standardised output. DATEX II, a European standard for exchanging road-traffic information, was an important part of that boundary.
The architecture needed consistency. The mistake was assuming that the same model should also become the interface people edited.
The model reached the wrong layer
The first phase of the transformation workflow asked data owners to map raw data onto a canonical model through a JSON editor. A visual transformation builder was planned for a later phase, but it had not been delivered at that point.
The canonical model closely followed DATEX II. For a relatively simple variable-speed-limit dataset, the resulting configuration grew beyond 1,000 lines of JSON and contained 68 object definitions. It exposed concepts such as carriageways, lanes, OpenLR location references, and variable-message-sign structures, even where they contributed nothing to the task in front of the user.
The platform could validate and process that structure. That did not make it a reasonable editing model.
The data owner was trying to express a speed limit at a location. The interface was asking them to navigate the vocabulary and nesting of an interchange standard.
Technical correctness is not usability
Schema-driven interfaces can create a false sense of completeness. If every field can be rendered and every constraint can produce an error, the UI may look finished from the system's perspective.
The user's experience can still be poor.
In this case, validation could report a missing OpenlrFormOfWayEnum. That message was accurate in terms of the schema. It was not actionable for someone configuring a speed limit.
A useful interface needed to translate the same failure into the language of the task: a location was incomplete, a speed value was missing, or a mapping could not be published. The distinction is not cosmetic. Validation is part of the contract between the system and the person operating it.
One domain can need three contracts
The approach I would use again separates three responsibilities.
- The interchange contract describes what an external standard or consumer requires. It can be detailed, strict, and specific because interoperability is its job.
- The canonical contract describes the durable domain concepts the platform needs across sources and targets. It should be neutral enough that one output format does not define the whole system.
- The editing contract describes the task a person is performing. It can expose a focused projection of the canonical model, add defaults, and return validation messages written for that workflow.
These contracts do not always require three separately stored models. An editing contract may be a projection generated from the canonical schema. What matters is that the responsibilities remain separate and that one layer does not leak into another merely because the types already exist.
Keep standard-specific complexity at the boundary
For the transport example, the intended direction was straightforward:
Rendering diagram…
DATEX II concepts still mattered. They belonged in the target adapter, where the platform prepared output for consumers that understood the standard.
The canonical model could then focus on cross-cutting ideas such as identity, source, use case, timestamps, validity, location, and attributes. The editing contract could present only the subset needed for the current transformation and explain failures without exposing backend terminology.
This boundary also made the planned visual builder more credible. A form or drag-and-drop tool generated from a focused schema is manageable. Generating the same interface from hundreds of nested standard-specific properties only moves the JSON editor's complexity into a different set of controls.
Version the model you expect people to keep
Simplifying a canonical model does not remove evolution. It makes that evolution visible.
Configurations should identify the canonical version they target. When the model changes, the platform needs an explicit migration path rather than allowing a standards upgrade to cascade unpredictably through stored configuration.
That might mean automatic migration for compatible additions, a guided review when meaning changes, and a clear refusal when the platform cannot preserve intent. The important part is ownership: schema evolution is a platform capability, not a surprise delegated to every screen and every user.
The extra boundary has a cost
Adapters and task-shaped contracts introduce code. They need mapping tests, documentation, and ownership. A smaller canonical model can also discard useful detail if the team simplifies before understanding what must round-trip.
There are cases where exposing a standard directly is reasonable. A specialist tool used by people who already work in that standard may benefit from fidelity more than abstraction. A short-lived integration with one source and one target may not justify several contracts.
The decision should come from the users and the expected lifespan of the system, not from a rule that every backend model must be hidden.
A practical review before building the UI
When a schema is about to become an editing experience, I would ask:
- Which fields express the user's task, and which exist only for interchange?
- How many concepts must someone learn before completing the simplest valid case?
- Do validation messages describe a business correction or a schema implementation?
- Can the model support another output format without importing the first format's vocabulary?
- What happens to saved configurations when the schema changes?
- Could a future form or visual builder be generated from this contract without reproducing the same cognitive load?
Those questions are cheaper to answer before a generic schema renderer becomes the product.
What I would keep doing
I would bring frontend, backend, and data-modelling engineers into this boundary early. The UI often reveals accidental coupling because it is the first place where every structural decision has to become understandable to a person.
The model closest to the user should describe the work they are trying to do. The model closest to the system boundary should describe the standard. Treating them as the same thing may remove an adapter, but it makes every user and every future interface pay the difference.