Sign inGet started
Skills / Software-development

Domain-Driven Design (DDD)

The heart of software is its ability to solve domain-related problems for its users. All other features, vital though they may be, support this basic purpose.

Domain-Driven Design is Eric Evans's foundational methodology for tackling software complexity by making the business domain the primary driver of architecture and code. It provides two interlocking layers: Strategic Design, which establishes Bounded Contexts, Ubiquitous Language, and context integration patterns; and Tactical Design, which uses named building blocks — Entities, Value Objects, Aggregates, Domain Services, and Domain Events — to implement the model in code. DDD is the reference framework for architects, engineering leads, and teams navigating complex domains, microservices decomposition, or legacy modernization.

By Eric Evans · Free
Specimen 01 · Live diagnosisDomain-Driven Design (DDD)
Input

“We're building a logistics platform — shippers post freight orders, carriers bid on them, and we handle the matching, tracking, and invoicing. It's…”

Diagnosis
Let's build your domain model using DDD's Strategic Design first — Bounded Contexts and subdomain classification before we touch Aggregates or Entities.
Full transcript ↓
Calibrated referenceagent-skills.ai
The gap

Stop modeling your database. Start modeling the domain that actually matters.

DDD is organized into Strategic Design and Tactical Design layers, applied in strict sequence. Strategic Design starts with Knowledge Crunching — iterative collaboration with domain experts — to identify subdomains, classify them as Core (your competitive differentiator), Supporting (necessary but not differentiating), or Generic (commodity, buy or reuse), and define Bounded Contexts: explicit boundaries within which a single internally consistent model applies. Context relationships are documented in a Context Map using named integration patterns: Shared Kernel, Customer-Supplier, Conformist, Anti-Corruption Layer, Open Host Service, and Published Language — each with specific implications for team coupling and model translation. Only after strategic clarity does Tactical Design refine each context's internal model using Evans's building blocks: Entities (identity-tracked, mutable), Value Objects (equality-by-value, immutable), Aggregates (consistency boundaries controlled by a root Entity), Domain Services (stateless operations), Domain Events (immutable records of meaningful domain occurrences), Repositories (persistence abstractions), and Factories (complex construction logic). DDD is explicitly iterative — a Breakthrough in domain understanding often requires refactoring both the model and the Ubiquitous Language that names it. Evans explicitly warns against the Anemic Domain Model antipattern, where objects become data holders and all logic migrates into services.

The problem

Software systems become unmaintainable when the code model diverges from business reality — developers model database tables instead of domain concepts, teams use different words for the same thing, and service boundaries are drawn along technical seams rather than domain boundaries. The result is the 'model-implementation gap': a system that's expensive to change, fragile at integration points, and increasingly opaque to the stakeholders who depend on it. DDD addresses this directly with a prescriptive system for finding where models belong, what they should contain, and how they should communicate.

The solution

Walk away with explicit Bounded Context boundaries your teams can own, a Ubiquitous Language glossary that eliminates vocabulary drift between developers and domain experts, and Aggregate designs that enforce business invariants rather than leaving consistency to luck.

You bring
  • A description of your business domain, product, or system — even rough requirements or a user story map
  • Your current or planned technical architecture, service list, or data model
  • Information about team structure, organizational boundaries, and inter-team dependencies
  • Specific pain points: service boundary confusion, vocabulary misalignment, a legacy monolith to decompose, or a new complex domain to model from scratch
You get
  • A Context Map identifying bounded contexts, their integration pattern relationships, and ownership boundaries — ready to drive microservice or team topology decisions
  • A Ubiquitous Language Glossary with per-context term definitions, disambiguation notes, and guidance on where each term applies and where it doesn't
  • Aggregate Boundary Specifications naming each root entity, the objects in its consistency cluster, and the invariants it must enforce
  • A Subdomain Classification Matrix labeling each subdomain as Core, Supporting, or Generic with build-vs-buy-vs-partner recommendations
In action

Watch the methodology work.

Three specimens from a single real session: the same situation, before and after, the full transcript, and the skill answering live in the channel where the work happens.

Fig.01The same situation, two ways
Specimens A · B
Specimen ABefore
Without the skill

Your codebase has a single `Order` model with 47 columns, referenced by your shipper portal, carrier mobile app, ops dashboard, and finance exports — each team added their own fields. 'Carrier' means three different things in three different services. Your microservices migration plan lists 12 proposed services that all share the same `orders` database table. A change to add a pricing field broke the carrier app. New developers spend their first month asking 'what does this field actually mean and who owns it?'

×The situation as it arrives — before the methodology is applied.
Specimen BAfter
With Domain-Driven Design (DDD)

Your system has four named Bounded Contexts — Freight Posting, Carrier Matching, Transportation Execution, Financial Settlement — each with its own Ubiquitous Language and explicit integration boundaries. 'Load', 'Bid', 'Shipment', and 'Invoice' are precise terms that mean one thing per context. A `LoadAwarded` domain event cleanly hands off from Carrier Matching to Transportation Execution with no shared database. Finance integrates a billing platform behind an Anti-Corruption Layer. Your best engineers focus on the Carrier Matching model because the Subdomain Classification told them that's where the competitive advantage lives.

The same situation once the methodology holds.
Fig.02A real session, unedited
In-app · assistant
Domain-Driven Design (DDD)Claude
Domain-Driven Design (DDD)
Let's build your domain model using DDD's Strategic Design first — Bounded Contexts and subdomain classification before we touch Aggregates or Entities. Tell me about the system you're working on: what does the business do, and where does the unique competitive value live? What does your organization do that a commodity SaaS platform couldn't replace?
We're building a logistics platform — shippers post freight orders, carriers bid on them, and we handle the matching, tracking, and invoicing. It's one Rails monolith right now and everything is a mess. The word 'Order' means five different things depending on who you ask.
That 'Order means five things' symptom is the clearest possible signal of Bounded Context bleed — multiple domain models sharing a term they've outgrown. Before we fix anything in code, let's surface those contexts.
From what you've described, I can see distinct domain activities: shippers creating load requirements (freight procurement), carriers evaluating and bidding (carrier matching), the negotiation process (pricing), movement and status tracking (transportation execution), and settlement (financial). Each of these likely has a different definition of 'Order' — and that's not a bug, it's a feature, as long as we make the boundaries explicit.
Let me ask: when a carrier says 'Order,' what do they actually mean? And when your finance team says 'Order,' what do they mean?
Carriers call it a 'Load' — they care about pickup and delivery locations, weight, and equipment type. Finance calls it a 'Shipment' and cares about the invoice amount, payment terms, and whether it settled. 'Order' is basically a developer invention that got overloaded.
Exactly — you just did your first Knowledge Crunching pass. 'Load' and 'Shipment' are the Ubiquitous Language terms for two different Bounded Contexts. Using the generic developer term 'Order' across your monolith is what's causing the confusion — it's not a naming problem, it's a missing boundary problem.
Here are the Bounded Contexts emerging from your description:
1.
Freight Posting — shippers describe what needs to move; core concept is a `Load` (origin, destination, commodity, equipment type)2. Carrier Matching — carriers evaluate `Loads`; core concept is a `Bid` and the matching logic3. Transportation Execution — an accepted load becomes a `Shipment` in motion; core concept is tracking events4. Financial Settlement — completed shipments become `Invoices`; core concept is amounts, payment terms, settlement status
Now the critical Strategic Design question: which of these is your Core Domain? Where does the competitive differentiator live?
The matching and pricing — that's our secret sauce. We do dynamic pricing based on real-time market conditions. Everything else is basically table stakes.
Then your Subdomain Classification looks like this:
| Subdomain | Classification | Recommendation ||---|---|---|| Carrier Matching + Dynamic Pricing | Core | Best engineers, deepest DDD modeling, own entirely || Transportation Execution (tracking) | Supporting | Build lean — necessary but not differentiating || Freight Posting (shipper UX) | Supporting | Build lean — table-stakes acquisition funnel || Financial Settlement | Generic | Buy — Stripe, Tipalti, or similar billing platform |
This classification directly shapes where DDD investment pays off. The Carrier Matching and Pricing context deserves a rich domain model, a precisely defined Ubiquitous Language agreed with your pricing experts, and Domain Events for every significant pricing decision. The settlement context should integrate a billing platform behind an Anti-Corruption Layer rather than building custom invoicing logic — an ACL translates between your `Shipment` model and whatever the billing system calls a 'billable event,' so neither side has to conform to the other's language.
Ready to draft the Context Map showing how these bounded contexts integrate, or would you like to drill into the Aggregate design for Carrier Matching first?
Let's do the Context Map. I'm especially unsure about the relationship between Carrier Matching and Transportation Execution — they share a lot of concepts.
Shared concepts across contexts are exactly where you need to be careful. 'Route' in your matching engine means a graph traversal with cost functions and carrier capacity constraints. 'Route' in Transportation Execution means a sequence of observed waypoints with timestamps. Forcing one model to serve both is what creates the bloated `Order` problem you already have.
For Carrier Matching → Transportation Execution, I'd recommend a Published Language pattern via Domain Events: Carrier Matching publishes `LoadAwarded` events (with Route ID, assigned carrier, initial ETA) that Transportation Execution consumes. Execution translates that event into its own `Shipment` aggregate using its own language — no shared tables, no shared classes, no direct database joins across the boundary.
Full Context Map:
```[Carrier Matching] --Published Language (Domain Events)--> [Transportation Execution][Freight Posting] --Customer-Supplier--> [Carrier Matching] [Transportation Execution] --Open Host Service (REST/events)--> [external tracking apps][Financial Settlement ACL] --Anti-Corruption Layer--> [external billing platform][Identity Context] --Conformist--> [external auth provider]```
The `LoadAwarded` event is your clean handoff boundary. Carrier Matching's internal model — your most complex, highest-value domain logic — stays fully encapsulated. Want me to now build out the Ubiquitous Language glossary for the Carrier Matching context and identify its Aggregates?
Reply to Domain-Driven Design (DDD)
What the skill is doing
01Bounded Context Discovery
02Ubiquitous Language Workshop
03Context Map Generation
Fig.03The same skill, in the channel you already use
WhatsApp · live
9:41
DDDomain-Driven Design (DDD)typing…
Messages are end-to-end encrypted. No one outside of this chat can read them.
Today
We're building a logistics platform — shippers post freight orders, carriers bid on them, and we handle the matching, tracking, and invoicing. It's on…9:14✓✓
Let's build your domain model using DDD's Strategic Design first — Bounded Contexts and subdomain classification before we touch A…9:14
Tell me about the system you're working on: what does the business do, and where does the unique competitive value live?9:15
What does your organization do that a commodity SaaS platform couldn't replace?9:15
Message

The same skill, where the work happens.

No new app to learn. The methodology runs over the WhatsApp Business API, so the answer lands as a reply in the thread you’re already in — same rigour, zero context-switch.

Reads the situation, names the pattern, returns one concrete next move.
Delivered in seconds, inside a conversation that already exists.
Specimen · WhatsApp Business API · live
Capabilities

What it does, specifically.

Each capability is a distinct move drawn straight from the source methodology — not a generic assistant guessing.

CapabilityC-01

Bounded Context Discovery

Guides you through identifying the natural seams in your domain where a single consistent model breaks down — the points where 'Customer' in billing means something fundamentally different from 'Customer' in fulfillment. Each Bounded Context gets an explicit name, scope, and owner, preventing the terminological bleed that causes integration bugs and misaligned teams.

Based on Evans's core Strategic Design principle that a model should have explicitly bounded applicability — a Bounded Context delimits the scope within which a domain model is defined and applicable, freeing teams to optimize their model independently within that boundary.
CapabilityC-02

Ubiquitous Language Workshop

Produces a per-context domain glossary by surfacing the terms domain experts use, reconciling them with developer vocabulary, and codifying the agreed language. The resulting glossary is not just documentation — it becomes the naming standard for classes, methods, events, and APIs within each bounded context.

Grounded in Evans's Knowledge Crunching process, where developers and domain experts iteratively refine a shared model expressed in language that permeates both conversations and code, eliminating the costly translation layer between business intent and implementation.
CapabilityC-03

Context Map Generation

Documents the relationships between bounded contexts using Evans's named integration patterns — Shared Kernel, Customer-Supplier, Conformist, Anti-Corruption Layer, Open Host Service, and Published Language. Each pattern carries specific implications for team autonomy, coupling tolerance, and who bears translation responsibility.

Applies Evans's full Context Mapping pattern catalog from the Strategic Design section of the blue book, each with applicability criteria based on organizational dynamics, model compatibility, and acceptable coupling levels.
CapabilityC-04

Aggregate Boundary Design

Identifies which domain objects form consistency clusters, which object acts as the Aggregate Root (the only external entry point), and which invariants the root must enforce. Guides the critical boundary-sizing decisions that prevent both bloated aggregates that serialize into megabyte payloads and anemic aggregates that leak invariant enforcement.

Based on Evans's Aggregate pattern: a cluster of domain objects treated as a single unit for data changes, where all external access routes through the root to ensure invariants are never violated — including the rule that only aggregate roots can be referenced by other aggregates.
CapabilityC-05

Core Domain Distillation

Classifies every subdomain as Core (the competitive differentiator — build here, invest deeply), Supporting (necessary but not differentiating — build simply or outsource), or Generic (commodity functionality — buy or reuse), and recommends investment strategy accordingly. Focuses your best engineering talent on the domain work that creates competitive advantage.

Based on Evans's Distillation strategy — the Core Domain is where DDD investment pays the highest return, while Generic and Supporting subdomains should receive minimal modeling effort to free resources for what actually differentiates the business.
Tested

Graded before it shipped.

Every skill is scored against independent scenarios for methodology fidelity before it goes live — not vibes, a rubric.

What it produces
OutputD-01

Context Map Diagram

A structured map of all bounded contexts in your system, the named integration pattern governing each relationship (ACL, Customer-Supplier, Published Language, etc.), direction of dependency, and team ownership. Serves as the architectural backbone for microservice decomposition or Team Topologies decisions.

OutputD-02

Ubiquitous Language Glossary

A per-context term dictionary with precise definitions, usage rules, and disambiguation notes — especially for terms that appear in multiple contexts with different meanings (e.g., 'Customer in Billing context ≠ Recipient in Fulfillment context'). Formatted for team wikis or architectural decision records.

OutputD-03

Aggregate Boundary Specification

For each key aggregate: the root entity, the objects inside its consistency boundary, the invariants the root enforces, lifecycle transitions, and recommended Repository interface. Includes a 'why this boundary' rationale and flags for common aggregate bloat antipatterns.

OutputD-04

Subdomain Classification Matrix

A table classifying each subdomain as Core, Supporting, or Generic, with investment strategy recommendation (build carefully / build simply / buy-or-reuse), strategic value rationale, and candidate third-party solutions for Generic subdomains.

The source

Grounded in the original work.

Every answer traces back to a real source and the practitioner who wrote it — not a secondhand summary. Here is the source of record.

Source authorA-01

Eric Evans

Eric Evans is the author of 'Domain-Driven Design: Tackling Complexity in the Heart of Software' (Addison-Wesley, 2003), universally called 'the blue book' and one of the most influential software design texts of the past two decades. He is the founder of Domain Language, a consultancy specializing in DDD coaching and training for complex software organizations. Evans is a recurring keynote speaker at DDD Europe and DDD eXchange, and his pattern catalog — Bounded Contexts, Ubiquitous Language, Aggregates — has directly shaped how modern teams design microservices architectures and distributed systems.

Status · Inspired by Eric Evans’s work — not yet claimed. Are you Eric Evans?
Primary sourceS-01

Domain-Driven Design: Tackling Complexity in the Heart of Software

by Eric Evans

Author of 'the blue book' (Addison-Wesley, 2003); founder of Domain Language consultancy; keynote speaker at DDD Europe and DDD eXchange; originator of Bounded Context, Ubiquitous Language, and Aggregate patterns adopted industry-wide.

Read the original ↗
Citationdomainlanguage.com
In the build queue

Be first to run it.

Domain-Driven Design (DDD) is being built right now. Leave your email and we’ll tell you the moment it goes live.

Notify meEmail
At launchI'm designing a system (or trying to decompose a monolith) and I'm not sure where to draw the service or team boundaries. Can we start with Strategic Design — walk through the domain together so you can help me classify subdomains and draw the first version of a Context Map?