Domain driven design DDD:建模具有-a

Domain driven design DDD:建模具有-a,domain-driven-design,domain-model,Domain Driven Design,Domain Model,我正试图遵循DDD,我对这个示例情况的建模有疑问: 我有一名实体员工: public class Employee{ public Int32 Id {get;set;} public String Name {get;set;} public Decimal Salary {get;set;} public List<Retirement> Retirements {get;set;} } 我的疑问是: 员工实体真的需要退休清单吗 (员工存在,但不存在

我正试图遵循DDD,我对这个示例情况的建模有疑问:

我有一名实体员工:

public class Employee{
   public Int32 Id {get;set;}
   public String Name {get;set;}
   public Decimal Salary {get;set;}
   public List<Retirement> Retirements {get;set;}
}
我的疑问是:

  • 员工实体真的需要退休清单吗
(员工存在,但不存在退休,但退休不存在,且不存在员工)

  • 如果我必须让所有今天退休的员工都退休,是不是更多 “合乎逻辑”搜索员工还是退休
  • 当我雇用一名雇员时,我不希望他退休。事实并非如此 一个共同特征。它会改变员工的行为吗

  • 首先,你的问题一点也不清楚

    我看到的第二个问题是退休班有一个结束日期?那是干什么的

    我将采用以下设计:

    class Employee{
    
       public Int32 Id {get;set;}
       public String Name {get;set;}
       public Decimal Salary {get;set;}
       public bool IsRetired {set;get;}
       public virtual Retirement Retirement{set;get;} 
    
    }
    
    今天,我将为退休员工提供如下服务:

    employees.Where(x=>x.Retirement.Beginning < Datetime.Today);
    
    class Employee{
    
       public Int32 Id {get;set;}
       public String Name {get;set;}
       public Decimal Salary {get;set;}
       public bool IsRetired {set;get;}
       public virtual IEnumerable<Retirement> Retirements{set;get;} 
    }
    
    employees.Where(x=>x.Retirement.start
    如果您有退休记录,您可以进行如下设计:

    employees.Where(x=>x.Retirement.Beginning < Datetime.Today);
    
    class Employee{
    
       public Int32 Id {get;set;}
       public String Name {get;set;}
       public Decimal Salary {get;set;}
       public bool IsRetired {set;get;}
       public virtual IEnumerable<Retirement> Retirements{set;get;} 
    }
    
    class员工{
    公共Int32 Id{get;set;}
    公共字符串名称{get;set;}
    公共十进制工资{get;set;}
    公共布尔值为{set;get;}
    公共虚拟IEnumerable失效{set;get;}
    }
    
    首先,你的问题一点也不清楚

    我看到的第二个问题是退休班有一个结束日期?那是干什么的

    我将采用以下设计:

    class Employee{
    
       public Int32 Id {get;set;}
       public String Name {get;set;}
       public Decimal Salary {get;set;}
       public bool IsRetired {set;get;}
       public virtual Retirement Retirement{set;get;} 
    
    }
    
    今天,我将为退休员工提供如下服务:

    employees.Where(x=>x.Retirement.Beginning < Datetime.Today);
    
    class Employee{
    
       public Int32 Id {get;set;}
       public String Name {get;set;}
       public Decimal Salary {get;set;}
       public bool IsRetired {set;get;}
       public virtual IEnumerable<Retirement> Retirements{set;get;} 
    }
    
    employees.Where(x=>x.Retirement.start
    如果您有退休记录,您可以进行如下设计:

    employees.Where(x=>x.Retirement.Beginning < Datetime.Today);
    
    class Employee{
    
       public Int32 Id {get;set;}
       public String Name {get;set;}
       public Decimal Salary {get;set;}
       public bool IsRetired {set;get;}
       public virtual IEnumerable<Retirement> Retirements{set;get;} 
    }
    
    class员工{
    公共Int32 Id{get;set;}
    公共字符串名称{get;set;}
    公共十进制工资{get;set;}
    公共布尔值为{set;get;}
    公共虚拟IEnumerable失效{set;get;}
    }
    
    同意@DarthVader。现在最好是这样(员工-->收集<退休>),因为没有更多已知的需求


    员工的退休记录可能是空的,这可能有点奇怪,但这会对员工的客户隐瞒细节(例如,员工何时退休,他/她是否已经退休)。

    同意@DarthVader。现在最好是这样(员工-->收集<退休>),因为没有更多已知的需求


    员工的退休信息可能是空的,这可能有点奇怪,但这会向员工的客户隐瞒细节(例如,员工何时退休,他/她是否已经退休)。

    当然,这是一个数据模型,而不是模型

    要开始DDD,你应该读几遍

    以下是您发布的代码的几个问题:

  • 实体应该由而不是Int32标识
  • 实体的标识不能更改:它可以公开只读属性,但不能公开可变属性
  • 实体应该被适当地封装:它们的状态应该只作为的结果而改变,但您是通过属性来公开它的
  • DDD中的关键概念是什么:如果
    员工
    退休人员
    属于同一个概念,您应该与领域专家一起思考
  • 如果
    员工
    和退休人员
    属于同一个有界上下文,则应通过标识符而不是直接对象引用来关联它们
  • 每个实体应仅持有严格要求的状态,以强制执行其不变量(上下文边界内相关的不变量)
  • 因此,要回答您的问题:

    • 员工实体真的需要退休清单吗
    否。如果它有像
    void Retire(DateTime from,DateTime to)
    这样的命令,它可能需要公开一组不可变的失效(例如和
    IEnumerable
    )。然而,如果这种情况下,退休将是一个价值对象,而不是一个实体;比如:

    public sealed Retirement {
       public Retirement (DateTime begining, DateTime end)
       {
           Begining = begining;
           End = end;
       }
       public DateTime Begining {get; private set;}
       public DateTime End {get; private set;}
    }
    
    • 如果我必须让所有今天退休的员工都参与进来,那么搜索“员工”还是“退休”更“合乎逻辑”
    也许,您应该只有一个员工存储库,即使是那些已经退休的员工

    通常,在OO语言中,每种类型的实体都有一个存储库是最佳选择

    • 当我雇用一名雇员时,我不希望他退休。这不是一个共同特征。它会改变员工的行为吗

    您应该使用为不变量的冲突建模。如果员工不能在雇佣当天退休,您应该抛出
    退休
    命令中记录的特定异常。

    当然,这是一个数据模型,而不是模型

    要开始DDD,你应该读几遍

    以下是您发布的代码的几个问题:

  • 实体应该由而不是Int32标识
  • 实体的标识不能更改:它可以公开只读属性,但不能公开可变属性
  • 实体应该被适当地封装:它们的状态应该只作为的结果而改变,但您是通过属性来公开它的
  • DDD中的关键概念是什么:如果
    员工
    退休人员
    属于同一个概念,您应该与领域专家一起思考
  • 如果
    员工
    和退休人员
  • 属于同一个有界上下文,则应通过标识符而不是直接对象引用来关联它们
  • 每个实体应仅持有严格要求的状态,以强制执行其不变量(上下文边界内相关的不变量)
  • 因此,要回答您的问题:

    • 员工实体真的需要退休清单吗
    否。如果它有类似于
    void Retire(D)的命令,它可能需要公开一组不可变的失效(例如和
    IEnumerable