Why DDD? Solving the Black‑Box Problem in Software Development
This article explains why Domain‑Driven Design is needed, critiques traditional development workflows that produce opaque code, and presents various modeling and aggregation strategies—including code examples—to involve non‑developers and bridge the gap between business experts and developers.
Why Use DDD?
Domain‑Driven Design (DDD) consists of strategic and tactical parts, with the core being strategic: business modeling, domain partitioning, and a unified language that serve business modeling.
Problems with Traditional Development Process
Traditional workflows often result in a black‑box program that only developers understand. The typical steps are:
Business side describes abstract requirements.
Product translates requirements into a concrete PRD.
Developers implement based on the PRD.
Testers test based on the PRD.
Product acceptance.
Business acceptance.
Developers take the longest time, while testers, product managers, and business stakeholders are blocked, and program quality relies on testing.
Example Project: Approval System
The PRD defined a three‑layer model: process instance, process node, and approval task. The implementation created approval tasks directly from the process instance, treating process nodes as virtual concepts without explicit representation, leading to confusion when new requirements added a comment feature for nodes.
How Business Modeling Solves the Black‑Box Issue
DDD introduces a business expert role (typically the business side or product). The steps are:
Establish a clear context and unified language so both experts and developers share understanding.
Perform business modeling using techniques such as use‑case analysis, event storming, or four‑color modeling to identify domains and aggregates.
Developers follow the established business model when writing code, making the implementation visible to business experts.
This creates a communication bridge similar to an adapter, allowing experts to evaluate new requirements realistically.
Involving Non‑Developers in Development
Unified language, business modeling, and rich domain models (OOP) enable non‑developers to participate. Think of the code as building material, the business model as a blueprint, and developers as construction workers following the design.
Implementing the Business Model in Code
Aggregates are expressed through OOP concepts such as aggregate roots, entities, and value objects. Below is a Java example of an order aggregate.
public class OrderItemEntity {
private Long id;
private Product product; // value object
private Count count; // value object
private ItemAmount itemAmt; // value object
public void modifyCount(Count count) {
this.count = count;
this.itemAmt = new ItemAmount(this.product.getPrice() * count.get());
}
}
public class OrderAggregate {
private Long id;
private OrderNo orderNo; // value object
private Amount amt; // value object
private List<OrderItemEntity> items;
public void modifyItemCount(Product product, Count count) {
OrderItemEntity item = this.items.stream()
.filter(product::equals)
.findAny()
.get();
item.modifyCount(count);
ItemAmount itemAmt = item.getItemAmt();
this.amt = new Amount(this.amt.get() + itemAmt.get());
}
}
// Usage example
Product product = new Product("Computer");
Count count = new Count(100);
Amount amt = orderAggregate.modifyItemCount(product, count);The code loads the entire aggregate into memory, which is unrealistic for large data sets (e.g., hundreds of thousands of items).
Theory vs. Reality
Loading a 1:n relationship entirely in memory assumes unlimited memory, which contradicts real‑world constraints.
Various Approaches to Aggregate Implementation
Model Lifting (Infinite Nesting)
Split large aggregates: promote OrderItem to Order, then Order to BatchOrder, and so on, creating nested aggregates until memory usage is acceptable.
Repository‑Holding Method
Keep a reference to a repository inside the aggregate root and load related data on demand, optionally adding an interface layer to isolate persistence.
public class OrderAggregate {
private Long id;
private OrderNo orderNo;
private Amount amt;
private OrderItemRel orderItemRel; // interface to repository
public Amount modifyItemCount(Product product, Count count) {
List<OrderItemEntity> items = orderItemRel.find(product);
OrderItemEntity item = items.stream()
.filter(product::equals)
.findAny()
.get();
item.modifyCount(count);
ItemAmount itemAmt = item.getItemAmt();
this.amt = new Amount(this.amt.get() + itemAmt.get());
return this.amt;
}
}Id‑Association Method
Instead of loading full aggregates, associate entities by IDs and perform operations within a single function with transaction control.
Aggregate Splitting
Create separate OrderAggregate and OrderItemAggregate, using domain events to maintain eventual consistency.
Flexible Scenario Method (Aggregate Splitting Plus)
Identify the primary subject of a use case (e.g., OrderItem) and model it as its own aggregate, keeping the Order lightweight for scenarios like payment where items are not needed.
public class OrderItemAggregate {
private Long id;
private Product product;
private Count count;
private ItemAmount itemAmt;
private OrderEntity orderEntity;
public void modifyCount(Count count) {
this.count = count;
ItemAmount newAmt = new ItemAmount(this.product.getPrice() * count.get());
Amount orderAmt = this.orderEntity.getAmt();
this.orderEntity.modifyAmt(new Amount(orderAmt.get() - this.itemAmt.get() + newAmt.get()));
this.itemAmt = newAmt;
}
}
public class OrderEntity {
private Long id;
private OrderNo orderNo;
private Amount amt;
public void modifyAmt(Amount amt) { this.amt = amt; }
}
// Usage
orderItemAggregate.modifyCount(new Count(100));Conclusion
The flexible scenario approach, which adapts aggregates to real‑world constraints without tying them to infrastructure services, best preserves domain consistency, aligns with DDD principles, and incurs low implementation cost, though convincing stakeholders of its validity can be challenging.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Alibaba Cloud Developer
Alibaba's official tech channel, featuring all of its technology innovations.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
