Skip to content

领域驱动设计(Domain-Driven Design)

概述

领域驱动设计(Domain-Driven Design,简称DDD)是由Eric Evans在2003年提出的一种软件设计方法论。DDD强调将复杂的业务领域作为软件设计的核心,通过深入理解业务领域,建立准确的领域模型,并将这个模型作为软件设计和实现的基础。

DDD不仅仅是一种技术方法,更是一种思维方式和协作模式。它强调领域专家与开发团队的紧密合作,通过统一的语言(Ubiquitous Language)来确保业务需求与技术实现的一致性。

架构图

DDD整体架构

┌─────────────────────────────────────────────────────────────────────────────┐
│                           领域驱动设计架构                                   │
└─────────────────────────────────────────────────────────────────────────────┘

┌─────────────────────────────────────────────────────────────────────────────┐
│                            用户界面层                                       │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐           │
│ │   Web UI    │ │  Mobile UI  │ │    API      │ │   Console   │           │
│ └─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘           │
└─────────────────────────────────────────────────────────────────────────────┘


┌─────────────────────────────────────────────────────────────────────────────┐
│                            应用服务层                                       │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐           │
│ │ 应用服务    │ │ 命令处理器  │ │ 查询处理器  │ │ 工作流协调  │           │
│ └─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘           │
└─────────────────────────────────────────────────────────────────────────────┘


┌─────────────────────────────────────────────────────────────────────────────┐
│                            领域层                                           │
│ ┌─────────────────────────────────────────────────────────────────────────┐ │
│ │                        限界上下文                                       │ │
│ │ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐       │ │
│ │ │   聚合根    │ │    实体     │ │   值对象    │ │  领域服务   │       │ │
│ │ └─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘       │ │
│ │ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐       │ │
│ │ │  领域事件   │ │   工厂      │ │   规约      │ │   策略      │       │ │
│ │ └─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘       │ │
│ └─────────────────────────────────────────────────────────────────────────┘ │
└─────────────────────────────────────────────────────────────────────────────┘


┌─────────────────────────────────────────────────────────────────────────────┐
│                            基础设施层                                       │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐           │
│ │   仓储实现  │ │  消息队列   │ │   外部API   │ │   文件系统  │           │
│ └─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘           │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐           │
│ │   数据库    │ │   缓存      │ │   日志      │ │   配置      │           │
│ └─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘           │
└─────────────────────────────────────────────────────────────────────────────┘

限界上下文映射

┌─────────────────────────────────────────────────────────────────────────────┐
│                           限界上下文映射                                     │
└─────────────────────────────────────────────────────────────────────────────┘

┌─────────────────┐    共享内核    ┌─────────────────┐
│   订单上下文    │◄──────────────▶│   支付上下文    │
│                │                │                │
│ ┌─────────────┐ │                │ ┌─────────────┐ │
│ │   订单      │ │                │ │   支付      │ │
│ │   订单项    │ │                │ │   账单      │ │
│ │   客户      │ │                │ │   交易      │ │
│ └─────────────┘ │                │ └─────────────┘ │
└─────────────────┘                └─────────────────┘
        │                                    │
        │ 客户-供应商                         │ 防腐层
        ▼                                    ▼
┌─────────────────┐                ┌─────────────────┐
│   库存上下文    │                │   用户上下文    │
│                │                │                │
│ ┌─────────────┐ │                │ ┌─────────────┐ │
│ │   产品      │ │                │ │   用户      │ │
│ │   库存      │ │                │ │   角色      │ │
│ │   仓库      │ │                │ │   权限      │ │
│ └─────────────┘ │                │ └─────────────┘ │
└─────────────────┘                └─────────────────┘
        │                                    │
        │ 开放主机服务                        │ 遵循者
        ▼                                    ▼
┌─────────────────┐    发布语言    ┌─────────────────┐
│   物流上下文    │◄──────────────▶│   报表上下文    │
│                │                │                │
│ ┌─────────────┐ │                │ ┌─────────────┐ │
│ │   运输      │ │                │ │   报表      │ │
│ │   配送      │ │                │ │   统计      │ │
│ │   跟踪      │ │                │ │   分析      │ │
│ └─────────────┘ │                │ └─────────────┘ │
└─────────────────┘                └─────────────────┘

聚合设计模式

┌─────────────────────────────────────────────────────────────────────────────┐
│                           订单聚合                                          │
└─────────────────────────────────────────────────────────────────────────────┘

                    ┌─────────────────┐
                    │   订单聚合根    │ ◄─── 聚合根
                    │                │
                    │ - 订单ID        │
                    │ - 客户ID        │
                    │ - 订单状态      │
                    │ - 创建时间      │
                    │ - 总金额        │
                    │                │
                    │ + 添加订单项    │
                    │ + 移除订单项    │
                    │ + 确认订单      │
                    │ + 取消订单      │
                    └─────┬───────────┘
                          │ 包含

                    ┌─────────────────┐
                    │    订单项       │ ◄─── 实体
                    │                │
                    │ - 订单项ID      │
                    │ - 产品ID        │
                    │ - 产品名称      │
                    │ - 数量          │
                    │ - 单价          │
                    │ - 小计          │
                    │                │
                    │ + 更新数量      │
                    │ + 计算小计      │
                    └─────┬───────────┘
                          │ 包含

                    ┌─────────────────┐
                    │    金额         │ ◄─── 值对象
                    │                │
                    │ - 数值          │
                    │ - 货币          │
                    │                │
                    │ + 加法          │
                    │ + 减法          │
                    │ + 比较          │
                    └─────────────────┘

聚合边界规则:
1. 聚合根是唯一的入口点
2. 外部只能通过聚合根访问聚合内部
3. 聚合内部保证一致性
4. 聚合之间通过ID引用

核心概念

1. 统一语言(Ubiquitous Language)

定义: 统一语言是领域专家和开发团队共同使用的语言,它准确地反映了业务领域的概念和规则。

特征:

  • 共同理解:所有团队成员使用相同的术语
  • 业务导向:术语来源于业务领域而非技术实现
  • 持续演进:随着对领域理解的深入而不断完善
  • 无歧义性:每个术语都有明确的含义

实践方法:

术语词汇表

┌─────────────────────────────────────────────────────────────┐
│                    电商领域术语词汇表                        │
├─────────────────────────────────────────────────────────────┤
│ 术语        │ 定义                                         │
├─────────────────────────────────────────────────────────────┤
│ 订单        │ 客户购买商品的正式请求                        │
│ 购物车      │ 客户临时存放待购买商品的容器                  │
│ 库存        │ 可供销售的商品数量                           │
│ 支付        │ 客户为订单付款的过程                         │
│ 发货        │ 将订单商品从仓库发送给客户的过程              │
│ 退款        │ 将已支付金额返还给客户的过程                  │
└─────────────────────────────────────────────────────────────┘

领域模型对话

业务专家: "当客户下单时,我们需要检查库存是否充足"
开发人员: "你是说当Order被创建时,需要验证Inventory的可用数量?"
业务专家: "是的,如果库存不足,订单应该被拒绝"
开发人员: "明白,我们在Order.create()方法中添加库存检查逻辑"

2. 限界上下文(Bounded Context)

定义: 限界上下文是一个明确的边界,在这个边界内,特定的领域模型是有效和一致的。

特征:

  • 明确边界:清晰定义上下文的范围
  • 模型一致性:上下文内模型保持一致
  • 语言统一:上下文内使用统一语言
  • 自治性:上下文可以独立演进

识别方法:

业务能力分析

电商系统限界上下文识别:

┌─────────────────┐  ┌─────────────────┐  ┌─────────────────┐
│   订单管理      │  │   库存管理      │  │   支付处理      │
│                │  │                │  │                │
│ - 订单创建      │  │ - 库存查询      │  │ - 支付处理      │
│ - 订单修改      │  │ - 库存预留      │  │ - 退款处理      │
│ - 订单取消      │  │ - 库存扣减      │  │ - 账单生成      │
│ - 订单查询      │  │ - 补货管理      │  │ - 对账管理      │
└─────────────────┘  └─────────────────┘  └─────────────────┘

┌─────────────────┐  ┌─────────────────┐  ┌─────────────────┐
│   用户管理      │  │   商品管理      │  │   物流管理      │
│                │  │                │  │                │
│ - 用户注册      │  │ - 商品录入      │  │ - 配送安排      │
│ - 用户认证      │  │ - 商品分类      │  │ - 物流跟踪      │
│ - 权限管理      │  │ - 价格管理      │  │ - 签收确认      │
│ - 个人信息      │  │ - 促销活动      │  │ - 异常处理      │
└─────────────────┘  └─────────────────┘  └─────────────────┘

数据一致性需求

强一致性需求 (同一上下文):
- 订单与订单项
- 用户与用户权限
- 商品与商品库存

最终一致性需求 (跨上下文):
- 订单与库存
- 订单与支付
- 支付与物流

3. 聚合(Aggregate)

定义: 聚合是一组相关对象的集合,作为数据修改的单元,由聚合根统一管理。

设计原则:

  • 一致性边界:聚合内保证强一致性
  • 事务边界:一个事务只能修改一个聚合
  • 引用规则:聚合间通过ID引用,不直接引用对象
  • 大小适中:聚合不宜过大,影响性能

聚合根职责:

┌─────────────────────────────────────────┐
│              聚合根职责                  │
├─────────────────────────────────────────┤
│ 1. 控制访问入口                         │
│    - 外部只能通过聚合根访问聚合内部      │
│    - 封装聚合内部的复杂性               │
│                                        │
│ 2. 维护业务不变性                       │
│    - 确保聚合内部状态的一致性           │
│    - 执行业务规则和约束                 │
│                                        │
│ 3. 发布领域事件                         │
│    - 在状态变化时发布相关事件           │
│    - 通知其他聚合或上下文               │
│                                        │
│ 4. 管理生命周期                         │
│    - 控制聚合的创建和销毁               │
│    - 管理聚合内实体的生命周期           │
└─────────────────────────────────────────┘

4. 实体(Entity)

定义: 实体是具有唯一标识的对象,其标识在整个生命周期中保持不变。

特征:

  • 唯一标识:具有全局唯一的标识符
  • 可变性:属性可以改变,但标识不变
  • 生命周期:有明确的创建、修改、销毁过程
  • 业务意义:标识具有业务含义

实体设计:

┌─────────────────────────────────────────┐
│               用户实体                   │
├─────────────────────────────────────────┤
│ 标识:                                   │
│ - userId: UserId (值对象)               │
│                                        │
│ 属性:                                   │
│ - email: Email (值对象)                 │
│ - name: PersonName (值对象)             │
│ - registrationDate: Date                │
│ - lastLoginTime: DateTime               │
│ - status: UserStatus (枚举)             │
│                                        │
│ 行为:                                   │
│ + changeEmail(newEmail: Email)          │
│ + updateProfile(name: PersonName)       │
│ + activate()                           │
│ + deactivate()                         │
│ + recordLogin()                        │
└─────────────────────────────────────────┘

5. 值对象(Value Object)

定义: 值对象是没有标识的对象,通过其属性值来区分,具有不可变性。

特征:

  • 无标识:没有唯一标识符
  • 不可变:创建后不能修改
  • 值相等:通过值比较相等性
  • 可替换:可以用相同值的对象替换

值对象设计:

┌─────────────────────────────────────────┐
│               金额值对象                 │
├─────────────────────────────────────────┤
│ 属性:                                   │
│ - amount: BigDecimal                    │
│ - currency: Currency                    │
│                                        │
│ 约束:                                   │
│ - amount >= 0                          │
│ - currency 不能为空                     │
│                                        │
│ 行为:                                   │
│ + add(other: Money): Money              │
│ + subtract(other: Money): Money         │
│ + multiply(factor: BigDecimal): Money   │
│ + equals(other: Money): boolean         │
│ + compareTo(other: Money): int          │
│                                        │
│ 不变性:                                 │
│ - 所有操作返回新的Money对象             │
│ - 不提供修改内部状态的方法              │
└─────────────────────────────────────────┘

6. 领域服务(Domain Service)

定义: 领域服务封装了不自然属于实体或值对象的业务逻辑。

使用场景:

  • 跨聚合操作:需要协调多个聚合的业务逻辑
  • 复杂计算:复杂的业务计算逻辑
  • 外部依赖:需要访问外部系统的业务逻辑
  • 策略模式:可变的业务规则

服务设计:

┌─────────────────────────────────────────┐
│            价格计算服务                  │
├─────────────────────────────────────────┤
│ 职责:                                   │
│ - 计算订单总价                          │
│ - 应用折扣规则                          │
│ - 计算税费                              │
│ - 处理促销活动                          │
│                                        │
│ 方法:                                   │
│ + calculateOrderTotal(                  │
│     order: Order,                       │
│     customer: Customer,                 │
│     promotions: List<Promotion>         │
│   ): Money                              │
│                                        │
│ + applyDiscount(                        │
│     amount: Money,                      │
│     discount: Discount                  │
│   ): Money                              │
│                                        │
│ + calculateTax(                         │
│     amount: Money,                      │
│     taxRate: TaxRate                    │
│   ): Money                              │
└─────────────────────────────────────────┘

7. 领域事件(Domain Event)

定义: 领域事件表示领域中发生的重要业务事件,用于解耦聚合间的依赖。

特征:

  • 业务意义:表示重要的业务事件
  • 不可变:事件一旦发生不能修改
  • 时序性:有明确的发生时间
  • 异步处理:通常异步处理

事件设计:

┌─────────────────────────────────────────┐
│            订单已创建事件                │
├─────────────────────────────────────────┤
│ 事件信息:                               │
│ - eventId: EventId                      │
│ - occurredOn: DateTime                  │
│ - version: int                          │
│                                        │
│ 业务数据:                               │
│ - orderId: OrderId                      │
│ - customerId: CustomerId                │
│ - orderItems: List<OrderItem>           │
│ - totalAmount: Money                    │
│ - orderDate: DateTime                   │
│                                        │
│ 元数据:                                 │
│ - correlationId: String                 │
│ - causationId: String                   │
│ - userId: UserId                        │
└─────────────────────────────────────────┘

事件处理流程:
订单创建 ──▶ 发布事件 ──▶ 库存预留 ──▶ 发送确认邮件
    │           │           │           │
    ▼           ▼           ▼           ▼
  聚合根      事件总线    库存服务    通知服务

战略设计

1. 上下文映射(Context Mapping)

映射关系类型:

共享内核(Shared Kernel)

特点:
- 两个上下文共享部分模型
- 需要密切协调变更
- 适用于紧密相关的团队

示例:
订单上下文 ←→ 支付上下文
共享: 客户信息、金额类型

客户-供应商(Customer-Supplier)

特点:
- 上游团队为下游团队提供服务
- 下游团队依赖上游团队
- 需要协商接口变更

示例:
库存上下文 (供应商) ──▶ 订单上下文 (客户)
接口: 库存查询、库存预留

遵循者(Conformist)

特点:
- 下游完全遵循上游模型
- 无法影响上游设计
- 适用于外部系统集成

示例:
报表上下文 ──▶ 第三方分析系统
遵循: 第三方系统的数据格式

防腐层(Anti-Corruption Layer)

特点:
- 保护本地模型不受外部影响
- 转换外部模型到本地模型
- 适用于遗留系统集成

示例:
新订单系统 ←─ 防腐层 ←─ 遗留ERP系统
转换: ERP数据格式 → 领域模型

开放主机服务(Open Host Service)

特点:
- 提供标准化的服务接口
- 多个客户端可以使用
- 定义发布语言

示例:
用户服务 ──▶ 标准用户API
客户端: 订单服务、支付服务、物流服务

发布语言(Published Language)

特点:
- 定义标准的交换格式
- 文档化的接口规范
- 版本化管理

示例:
XML Schema、JSON Schema、Protocol Buffers

2. 上下文集成模式

数据库集成

┌─────────────┐    ┌─────────────┐
│  上下文A    │    │  上下文B    │
└─────┬───────┘    └─────┬───────┘
      │                  │
      ▼                  ▼
┌─────────────────────────────┐
│        共享数据库           │
└─────────────────────────────┘

优点: 实现简单、数据一致性
缺点: 紧耦合、难以独立演进

文件传输集成

┌─────────────┐  文件  ┌─────────────┐
│  上下文A    │ ────▶ │  上下文B    │
│            │       │            │
│ 生成文件    │       │ 处理文件    │
└─────────────┘       └─────────────┘

优点: 松耦合、批量处理
缺点: 延迟高、错误处理复杂

远程过程调用

┌─────────────┐   RPC   ┌─────────────┐
│  上下文A    │ ──────▶ │  上下文B    │
│            │ ◄────── │            │
│ 调用服务    │  响应   │ 提供服务    │
└─────────────┘         └─────────────┘

优点: 实时交互、类型安全
缺点: 紧耦合、可用性依赖

消息传递

┌─────────────┐  消息  ┌─────────────┐  消息  ┌─────────────┐
│  上下文A    │ ────▶ │  消息中间件 │ ────▶ │  上下文B    │
│            │       │            │       │            │
│ 发布消息    │       │ 路由转发    │       │ 订阅消息    │
└─────────────┘       └─────────────┘       └─────────────┘

优点: 松耦合、异步处理、可扩展
缺点: 复杂性增加、最终一致性

战术设计

1. 聚合设计模式

聚合大小原则

小聚合原则:
✓ 一个聚合根 + 少量实体/值对象
✓ 单一事务边界
✓ 高内聚、低耦合
✓ 性能考虑

大聚合问题:
✗ 并发冲突增加
✗ 内存占用过大
✗ 加载性能下降
✗ 事务复杂度增加

聚合引用规则

内部引用:
聚合根 ──▶ 实体 (直接引用)
实体 ──▶ 值对象 (直接引用)

外部引用:
聚合A ──▶ 聚合B (通过ID引用)

示例:
class Order {
    private OrderId id;                    // 自身ID
    private CustomerId customerId;         // 外部聚合ID引用
    private List<OrderItem> items;         // 内部实体直接引用
    private ShippingAddress address;       // 值对象直接引用
}

聚合一致性保证

强一致性 (聚合内):
- 同一事务内修改
- 立即验证业务规则
- 原子性操作

最终一致性 (聚合间):
- 通过领域事件
- 异步处理
- 补偿机制

示例:
// 聚合内强一致性
order.addItem(productId, quantity);  // 立即验证库存
order.calculateTotal();              // 立即计算总价

// 聚合间最终一致性
orderCreated.publish();              // 发布事件
// 异步处理: 库存扣减、发送邮件等

2. 仓储模式(Repository Pattern)

定义: 仓储提供了一个类似集合的接口来访问聚合,封装了数据访问的复杂性。

设计原则:

┌─────────────────────────────────────────┐
│              仓储设计原则                │
├─────────────────────────────────────────┤
│ 1. 每个聚合根一个仓储                   │
│    - OrderRepository for Order          │
│    - CustomerRepository for Customer    │
│                                        │
│ 2. 仓储接口在领域层定义                 │
│    - 避免基础设施依赖                   │
│    - 支持测试和模拟                     │
│                                        │
│ 3. 仓储实现在基础设施层                 │
│    - 具体的数据访问技术                 │
│    - ORM映射和查询实现                  │
│                                        │
│ 4. 提供集合式接口                       │
│    - add(), remove(), findById()       │
│    - 隐藏查询复杂性                     │
└─────────────────────────────────────────┘

仓储接口设计:

┌─────────────────────────────────────────┐
│            订单仓储接口                  │
├─────────────────────────────────────────┤
│ interface OrderRepository {             │
│                                        │
│   // 基本操作                          │
│   void add(Order order);               │
│   void remove(Order order);            │
│   Order findById(OrderId id);          │
│                                        │
│   // 业务查询                          │
│   List<Order> findByCustomerId(        │
│     CustomerId customerId);            │
│   List<Order> findByStatus(            │
│     OrderStatus status);               │
│   List<Order> findByDateRange(         │
│     Date from, Date to);               │
│                                        │
│   // 规约模式                          │
│   List<Order> findBySpecification(     │
│     Specification<Order> spec);        │
│ }                                      │
└─────────────────────────────────────────┘

3. 工厂模式(Factory Pattern)

使用场景:

  • 复杂的对象创建逻辑
  • 需要验证创建参数
  • 多种创建方式
  • 封装创建细节

工厂设计:

┌─────────────────────────────────────────┐
│              订单工厂                    │
├─────────────────────────────────────────┤
│ class OrderFactory {                    │
│                                        │
│   public Order createOrder(            │
│     CustomerId customerId,             │
│     List<OrderItemData> items,         │
│     ShippingAddress address            │
│   ) {                                  │
│     // 验证参数                        │
│     validateCustomer(customerId);      │
│     validateItems(items);              │
│     validateAddress(address);          │
│                                        │
│     // 创建订单                        │
│     OrderId orderId = generateId();    │
│     Order order = new Order(           │
│       orderId, customerId, address);   │
│                                        │
│     // 添加订单项                      │
│     for (OrderItemData item : items) { │
│       order.addItem(                   │
│         item.productId,                │
│         item.quantity,                 │
│         item.price);                   │
│     }                                  │
│                                        │
│     return order;                      │
│   }                                    │
│ }                                      │
└─────────────────────────────────────────┘

4. 规约模式(Specification Pattern)

定义: 规约模式将业务规则封装为可组合的对象,支持复杂的查询和验证逻辑。

规约设计:

┌─────────────────────────────────────────┐
│              规约接口                    │
├─────────────────────────────────────────┤
│ interface Specification<T> {            │
│   boolean isSatisfiedBy(T candidate);   │
│                                        │
│   Specification<T> and(                │
│     Specification<T> other);           │
│   Specification<T> or(                 │
│     Specification<T> other);           │
│   Specification<T> not();              │
│ }                                      │
└─────────────────────────────────────────┘

┌─────────────────────────────────────────┐
│            具体规约实现                  │
├─────────────────────────────────────────┤
│ class HighValueOrderSpec                │
│   implements Specification<Order> {     │
│                                        │
│   private Money threshold;             │
│                                        │
│   public boolean isSatisfiedBy(        │
│     Order order) {                     │
│     return order.getTotal()            │
│       .isGreaterThan(threshold);       │
│   }                                    │
│ }                                      │
│                                        │
│ class RecentOrderSpec                  │
│   implements Specification<Order> {     │
│                                        │
│   private int days;                    │
│                                        │
│   public boolean isSatisfiedBy(        │
│     Order order) {                     │
│     return order.getOrderDate()        │
│       .isAfter(                        │
│         LocalDate.now().minusDays(days)│
│       );                               │
│   }                                    │
│ }                                      │
└─────────────────────────────────────────┘

使用示例:
Specification<Order> highValueRecent = 
  new HighValueOrderSpec(Money.of(1000))
    .and(new RecentOrderSpec(30));

List<Order> orders = orderRepository
  .findBySpecification(highValueRecent);

分层架构

1. 用户界面层(User Interface Layer)

职责:

  • 处理用户交互
  • 展示数据
  • 输入验证
  • 会话管理

组件:

┌─────────────────────────────────────────┐
│            用户界面层组件                │
├─────────────────────────────────────────┤
│ Controllers/Handlers:                   │
│ - 处理HTTP请求                          │
│ - 参数验证和转换                        │
│ - 调用应用服务                          │
│ - 返回响应                              │
│                                        │
│ View Models/DTOs:                      │
│ - 数据传输对象                          │
│ - 视图模型                              │
│ - 序列化/反序列化                       │
│                                        │
│ Validators:                            │
│ - 输入验证                              │
│ - 格式检查                              │
│ - 安全验证                              │
└─────────────────────────────────────────┘

2. 应用服务层(Application Service Layer)

职责:

  • 协调领域对象
  • 事务管理
  • 安全检查
  • 工作流控制

应用服务设计:

┌─────────────────────────────────────────┐
│            订单应用服务                  │
├─────────────────────────────────────────┤
│ @Service                               │
│ class OrderApplicationService {         │
│                                        │
│   @Transactional                       │
│   public OrderId createOrder(          │
│     CreateOrderCommand command) {      │
│                                        │
│     // 1. 验证权限                     │
│     securityService.checkPermission(   │
│       command.getUserId(),             │
│       "CREATE_ORDER");                 │
│                                        │
│     // 2. 获取领域对象                 │
│     Customer customer = customerRepo   │
│       .findById(command.getCustomerId())│
│     Product product = productRepo      │
│       .findById(command.getProductId())│
│                                        │
│     // 3. 执行领域逻辑                 │
│     Order order = orderFactory         │
│       .createOrder(customer, product,  │
│         command.getQuantity());        │
│                                        │
│     // 4. 持久化                      │
│     orderRepository.add(order);        │
│                                        │
│     // 5. 发布事件                     │
│     eventPublisher.publish(            │
│       new OrderCreatedEvent(order));   │
│                                        │
│     return order.getId();              │
│   }                                    │
│ }                                      │
└─────────────────────────────────────────┘

3. 领域层(Domain Layer)

职责:

  • 业务逻辑实现
  • 业务规则验证
  • 领域模型定义
  • 领域事件发布

层次结构:

领域层
├── 聚合
│   ├── 聚合根
│   ├── 实体
│   └── 值对象
├── 领域服务
├── 领域事件
├── 仓储接口
├── 工厂
└── 规约

4. 基础设施层(Infrastructure Layer)

职责:

  • 数据持久化
  • 外部系统集成
  • 技术服务提供
  • 横切关注点

组件:

┌─────────────────────────────────────────┐
│            基础设施层组件                │
├─────────────────────────────────────────┤
│ 持久化:                                │
│ - 仓储实现                              │
│ - ORM映射                              │
│ - 数据库访问                            │
│                                        │
│ 消息:                                  │
│ - 事件发布器                            │
│ - 消息队列                              │
│ - 事件处理器                            │
│                                        │
│ 外部集成:                              │
│ - 外部API客户端                         │
│ - 适配器                                │
│ - 防腐层                                │
│                                        │
│ 技术服务:                              │
│ - 日志                                  │
│ - 缓存                                  │
│ - 配置                                  │
│ - 安全                                  │
└─────────────────────────────────────────┘

实施策略

1. 团队组织

康威定律应用

"设计系统的组织,其产生的设计等同于组织之间的沟通结构"

组织结构 ──▶ 系统架构

示例:
┌─────────────┐    ┌─────────────┐
│  订单团队   │    │  订单上下文 │
│            │───▶│            │
│ - 产品经理  │    │ - 订单聚合  │
│ - 开发人员  │    │ - 订单服务  │
│ - 测试人员  │    │ - 订单API   │
└─────────────┘    └─────────────┘

┌─────────────┐    ┌─────────────┐
│  支付团队   │    │  支付上下文 │
│            │───▶│            │
│ - 产品经理  │    │ - 支付聚合  │
│ - 开发人员  │    │ - 支付服务  │
│ - 测试人员  │    │ - 支付API   │
└─────────────┘    └─────────────┘

团队自治原则

每个团队负责一个或多个限界上下文:
- 独立的开发周期
- 独立的技术选型
- 独立的部署流程
- 独立的数据存储

团队间协作:
- 明确的接口契约
- 定期的集成测试
- 统一的监控标准
- 共享的基础设施

2. 实施步骤

第一阶段:领域建模

1. 事件风暴 (Event Storming)
   - 识别领域事件
   - 发现聚合边界
   - 确定限界上下文

2. 统一语言建立
   - 术语词汇表
   - 概念模型图
   - 业务流程图

3. 上下文映射
   - 识别上下文关系
   - 定义集成策略
   - 设计防腐层

第二阶段:架构设计

1. 分层架构设计
   - 定义层次职责
   - 设计依赖关系
   - 确定技术选型

2. 聚合设计
   - 识别聚合根
   - 定义聚合边界
   - 设计聚合关系

3. 服务设计
   - 应用服务设计
   - 领域服务设计
   - 基础设施服务设计

第三阶段:实现开发

1. 核心领域实现
   - 聚合实现
   - 领域服务实现
   - 仓储接口定义

2. 应用层实现
   - 应用服务实现
   - 命令处理器实现
   - 查询处理器实现

3. 基础设施实现
   - 仓储实现
   - 事件发布器实现
   - 外部集成实现

第四阶段:集成测试

1. 单元测试
   - 聚合测试
   - 领域服务测试
   - 应用服务测试

2. 集成测试
   - 上下文内集成
   - 跨上下文集成
   - 端到端测试

3. 性能测试
   - 负载测试
   - 压力测试
   - 容量规划

3. 迁移策略

绞杀者模式(Strangler Pattern)

遗留系统迁移:

阶段1: 新功能用DDD实现
┌─────────────┐    ┌─────────────┐
│  遗留系统   │    │  新DDD系统  │
│            │    │            │
│ 现有功能    │    │ 新功能      │
└─────────────┘    └─────────────┘

阶段2: 逐步迁移现有功能
┌─────────────┐    ┌─────────────┐
│  遗留系统   │    │  新DDD系统  │
│            │    │            │
│ 部分功能    │    │ 大部分功能  │
└─────────────┘    └─────────────┘

阶段3: 完全替换
                   ┌─────────────┐
                   │  新DDD系统  │
                   │            │
                   │ 全部功能    │
                   └─────────────┘

分支抽象(Branch by Abstraction)

代码级别的渐进迁移:

1. 创建抽象层
   interface OrderService {
     Order createOrder(...);
   }

2. 实现新旧两套逻辑
   class LegacyOrderService implements OrderService
   class DddOrderService implements OrderService

3. 通过配置切换
   @ConditionalOnProperty("order.service.type")
   OrderService orderService;

4. 逐步切换到新实现
   order.service.type=ddd

5. 移除旧实现
   删除LegacyOrderService

优势与挑战

优势

1. 业务对齐

统一语言:
- 减少沟通误解
- 提高需求理解准确性
- 加速开发进度
- 降低维护成本

领域模型:
- 准确反映业务逻辑
- 易于业务人员理解
- 支持业务变化
- 提高代码可读性

2. 代码质量

高内聚低耦合:
- 清晰的职责分离
- 减少代码依赖
- 提高代码复用性
- 易于单元测试

业务逻辑集中:
- 避免贫血模型
- 业务规则集中管理
- 减少重复代码
- 提高一致性

3. 可维护性

模块化设计:
- 独立的上下文
- 清晰的边界
- 局部化变更影响
- 支持并行开发

演进友好:
- 支持渐进式重构
- 新功能易于添加
- 遗留系统易于替换
- 技术栈易于升级

挑战

1. 学习成本

概念复杂:
- 大量新概念和模式
- 需要深入理解业务
- 设计技能要求高
- 团队培训成本

实践经验:
- 缺乏最佳实践
- 容易过度设计
- 边界划分困难
- 性能优化复杂

2. 实施复杂性

初期投入:
- 建模时间长
- 开发周期延长
- 架构设计复杂
- 基础设施要求高

团队协作:
- 需要领域专家参与
- 跨团队协调复杂
- 统一语言建立困难
- 上下文集成挑战

3. 性能考虑

对象创建开销:
- 大量小对象
- 内存占用增加
- GC压力增大
- 序列化成本

查询复杂性:
- 跨聚合查询困难
- 需要额外的查询模型
- 数据一致性挑战
- 缓存策略复杂

最佳实践

1. 建模实践

事件风暴

参与者:
- 领域专家
- 产品经理
- 架构师
- 开发人员

步骤:
1. 识别领域事件 (橙色便签)
2. 找出命令 (蓝色便签)
3. 发现聚合 (黄色便签)
4. 识别限界上下文 (大纸张)
5. 定义上下文关系 (箭头连线)

产出:
- 事件列表
- 聚合清单
- 上下文地图
- 统一语言词汇表

领域建模

建模原则:
1. 从业务出发,不是技术
2. 关注核心领域
3. 保持模型简单
4. 持续重构完善

建模工具:
- UML类图
- 领域模型图
- 事件流图
- 上下文地图

2. 代码实践

聚合设计

设计原则:
1. 小聚合优于大聚合
2. 通过ID引用其他聚合
3. 一个事务修改一个聚合
4. 使用最终一致性

实现技巧:
- 延迟加载
- 快照优化
- 事件溯源
- CQRS分离

测试策略

测试金字塔:

单元测试 (70%):
- 聚合测试
- 值对象测试
- 领域服务测试

集成测试 (20%):
- 仓储测试
- 应用服务测试
- 事件处理测试

端到端测试 (10%):
- 用户场景测试
- 性能测试
- 安全测试

3. 架构实践

依赖管理

依赖方向:
用户界面层 ──▶ 应用服务层 ──▶ 领域层 ◄── 基础设施层

依赖倒置:
- 领域层定义接口
- 基础设施层实现接口
- 通过依赖注入连接

事件驱动

事件设计:
- 业务事件优于技术事件
- 事件不可变
- 包含足够的上下文信息
- 版本化管理

事件处理:
- 幂等性设计
- 错误重试机制
- 死信队列处理
- 监控和告警

工具和框架

1. 建模工具

txt
可视化工具:
- Miro/Mural (事件风暴)
- Lucidchart (架构图)
- txt (UML图)
- Context Mapper (上下文映射)

协作工具:
- Confluence (文档)
- Notion (知识库)
- GitHub Wiki (版本控制)
- Slack/Teams (沟通)

2. 开发框架

Java生态:
- Spring Boot (应用框架)
- Axon Framework (CQRS/ES)
- JPA/Hibernate (持久化)
- Spring Data (仓储)

.NET生态:
- ASP.NET Core (应用框架)
- MediatR (CQRS)
- Entity Framework (持久化)
- EventStore (事件存储)

Node.js生态:
- NestJS (应用框架)
- TypeORM (持久化)
- EventStore (事件存储)
- Bull (消息队列)

3. 基础设施

消息中间件:
- Apache Kafka
- RabbitMQ
- Apache Pulsar
- Redis Streams

数据存储:
- PostgreSQL (关系型)
- MongoDB (文档型)
- EventStore (事件存储)
- Redis (缓存)

监控工具:
- Prometheus (指标)
- Grafana (可视化)
- ELK Stack (日志)
- Jaeger (链路追踪)

总结

领域驱动设计是一种以业务领域为核心的软件设计方法论,它通过深入理解业务领域,建立准确的领域模型,并将这个模型作为软件设计和实现的基础。

核心价值:

  1. 业务对齐:确保软件准确反映业务需求
  2. 代码质量:提高代码的可读性和可维护性
  3. 团队协作:建立统一的沟通语言
  4. 架构清晰:明确的职责分离和边界定义

适用场景:

  1. 复杂的业务领域
  2. 长期维护的系统
  3. 大型团队协作
  4. 业务规则频繁变化

实施建议:

  1. 从小开始:选择核心子域进行试点
  2. 持续学习:团队需要不断学习和实践
  3. 业务参与:确保领域专家深度参与
  4. 渐进演进:采用渐进式的实施策略

成功关键因素:

  1. 领导支持:管理层的理解和支持
  2. 团队能力:具备DDD实践能力的团队
  3. 业务配合:业务专家的积极参与
  4. 技术基础:合适的技术栈和基础设施

DDD不仅仅是一种技术方法,更是一种思维方式。它要求我们从业务的角度思考软件设计,将复杂的业务领域转化为清晰的软件模型。虽然学习和实施DDD需要投入大量的时间和精力,但对于复杂的业务系统来说,这种投入是值得的。

通过DDD,我们可以构建出真正反映业务需求、易于维护和扩展的软件系统,为企业的数字化转型提供坚实的技术基础。