我已经生成了一些流畅的NHibernate代码。它有实体代码,如:
private ISet<CardPlace> _cardPlace;
public MagazineType()
{
_cardPlace = new HashedSet<CardPlace>();
}
public virtual ISet<CardPlace> CardPlace
{
get { return _cardPlace; }
set { _cardPlace = value; }
}
此属性的映射如:
HasMany(x => x.CardPlace)
.Access.CamelCaseField(Prefix.Underscore)
.Cascade.AllDeleteOrphan()
.Fetch.Select()
.AsSet()
.Inverse()
.LazyLoad()
.KeyColumns.Add("MAGAZINE_ID");
我不明白的是.Access.CamelCaseField(Prefix.Underscore)
行。为什么它没有直接映射到属性,而是映射到私有支持字段?这样做有什么理由吗?
答案 0 :(得分:2)
如果删除
.Access.CamelCaseField(Prefix.Underscore)
映射将是属性getter和setter。
该行指示流利的禁止使用该字段。
答案 1 :(得分:1)
这里的答案是/应该/可能是:改进领域模型设计。这里的主要帮助词是&#34;封装&#34; 。这是因为:
为什么我们要尝试创建实体模型(包含所有业务/验证规则) ...
......同时保持后门打开,即有公共制定者。
有一篇非常好的文章,真的很深入:
让我引用一下,只是摘要 (但请仔细阅读该文字)
在理论上谈论聚合根边界很有趣,但是你可能看到的许多领域模型只在名称上有边界。
如果域模型公开操作和命令只是为了通过直接转到属性设置器来绕过这些操作,那么根本就没有边界。
...
离开公共制定者的理由通常用“更容易测试”来表达。根据经验,无效的域对象更容易混淆,更难测试,原因很简单,因为您无法知道在使用应用程序时已经设置了实际上有效的上下文。
文章(read it please)中的所有论点都集中在最后一段:
我们可以避免这种混乱,并且可能会出现额外的防御性编码 删除只应通过在我们的域模型上执行的操作和命令进行更改的数据的公共setter。
再一次,这就是封装的全部内容。我们的模型只公开支持的内容,不允许不支持的内容。
注意:嗯,我确实使用公共制定者,而且我确实使用&#34;借口&#34;喜欢&#34;它更适合测试...