前面介绍了DDD分层架构的实体,并完成了实体层超类型的开发,同时提供了验证方面的支持.本篇将介绍另一个重要的构造块——值对象,它是聚合中的主要成分. 如果说你已经在使用DDD分层架构,但你却从来没有使用过值对象,这毫不奇怪,因为多年来养成的数据建模思维已经牢牢把你禁锢,以致于你在使用面向对象方式进行开发时,还是以数据为中心. 当我们完成了基本的需求分析以后,如果说需要进行设计,那么你能想到的就是数据库表及表关系的设计,这就是数据建模.数据建模的主要依据是数据库范式设计,根据要求严格程度的递增分为…
前面已经介绍过Entity Framework的工作单元和映射层超类型的封装,从本文开始,将逐步介绍仓储以及对查询的扩展支持. 什么是仓储 仓储表示聚合的集合. 仓储所表现出来的集合外观,仅仅是一种模拟,除了测试以外,没有理由使用内存中真正的集合来创建仓储. 不应该为所有实体建立仓储,只有聚合才拥有仓储. 仓储用来重建已持久化的聚合,而工厂用于新建聚合. 使用仓储的优点 直接使用Entity Framework的DbContext不是很好吗,为什么还要在DbContext的上方封装一层仓储呢,这…
在应用程序框架实战十四:DDD分层架构之领域实体(基础篇)一文中,我介绍了领域实体的基础,包括标识.相等性比较.输出实体状态等.本文将介绍领域实体的一个核心内容——验证,它是应用程序健壮性的基石.为了完成领域实体的验证,我们在前面已经准备好了验证公共操作类和异常公共操作类. .Net提供的DataAnnotations验证方法非常强大,Mvc会自动将DataAnnotations特性转换为客户端Js验证,从而提升了用户体验.但是客户端验证是靠不住的,因为很容易绕开界面向服务端提交数据,所以服务端…
前面已经介绍了DDD分层架构的实体和值对象,本文将介绍聚合以及与其高度相关的并发主题. 我在之前已经说过,初学者第一步需要将业务逻辑尽量放到实体或值对象中,给实体“充血”,这样可以让业务逻辑高度内聚,并为你提供业务逻辑的唯一访问点.而聚合则是第二步,它将多个相关业务概念包装到单一的概念中,从而大幅简化系统设计,由于受传统数据建模思维影响,我在聚合方面吃过大亏,花了将近一年才真正用起来,为了你少走弯路,我会把一些要点总结出来供你参考. 什么是聚合? 聚合包装一组高度相关的对象,作为一个数据修改的单…
上一篇,我介绍了自己在DDD分层架构方面的一些感想,本文开始介绍领域层的实体,代码主要参考自<领域驱动设计C#2008实现>,另外参考了网上找到的一些示例代码. 什么是实体 由标识来区分的对象称为实体. 实体的定义隐藏了几个信息: 两个实体对象,只要它们的标识属性值相等,哪怕标识属性以外的所有属性值都不相等,这两个对象也认为是同一个实体,这意味着两个对象是同一实体在其生命周期内的不同阶段. 为了能正确区分实体,标识必须唯一. 实体的标识属性值是不可变的,标识属性以外的属性值是可变的.如果标识值…
DDD分层架构之值对象(介绍篇) 前面介绍了DDD分层架构的实体,并完成了实体层超类型的开发,同时提供了验证方面的支持.本篇将介绍另一个重要的构造块——值对象,它是聚合中的主要成分. 如果说你已经在使用DDD分层架构,但你却从来没有使用过值对象,这毫不奇怪,因为多年来养成的数据建模思维已经牢牢把你禁锢,以致于你在使用面向对象方式进行开发时,还是以数据为中心. 当我们完成了基本的需求分析以后,如果说需要进行设计,那么你能想到的就是数据库表及表关系的设计,这就是数据建模.数据建模的主要依据是数据库范…
DDD分层架构之值对象(层超类型篇) 上一篇介绍了值对象的基本概念,得到了一些朋友的支持,另外也有一些朋友提出了不同意见.这其实是很自然的事情,设计本来就充满了各种可能性,没有绝对正确的做法,只有更好的实践.但是设计与实践的好与坏,对于不同的人,以及处于不同的环境都有不同的诠释,这是一个仁者见仁,智者见智的问题.DDD非常抽象,以至于它的每一个概念,对于不同的人都有不同的看法,更何况基于DDD的.Net实践,就更难分辨哪一个用法更标准.更正宗. 我对DDD的认识虽然还很肤浅,用得也很山寨,但这可…
上一篇介绍了值对象的基本概念,得到了一些朋友的支持,另外也有一些朋友提出了不同意见.这其实是很自然的事情,设计本来就充满了各种可能性,没有绝对正确的做法,只有更好的实践.但是设计与实践的好与坏,对于不同的人,以及处于不同的环境都有不同的诠释,这是一个仁者见仁,智者见智的问题.DDD非常抽象,以至于它的每一个概念,对于不同的人都有不同的看法,更何况基于DDD的.Net实践,就更难分辨哪一个用法更标准.更正宗. 我对DDD的认识虽然还很肤浅,用得也很山寨,但这可能更加适合初步接触DDD的朋友.还是那…
前一篇介绍了仓储的基本概念,并谈了我对仓储的一些认识,本文将实现仓储的基本功能. 仓储代表聚合在内存中的集合,所以仓储的接口需要模拟得像一个集合.仓储中有很多操作都是可以通用的,可以把这部分操作抽取到基类中. 在Util.Domains项目中创建一个文件夹Repositories,这个文件夹用来放仓储相关的接口.在Repositories下创建一个仓储接口IRepository. 把仓储基接口放到Util.Domains,是因为仓储接口是在领域层定义的,这与传统三层架构的数据访问层接口的位置不同…
最近的更新速度越来越慢,主要是项目上比较忙,封装EasyUi也要花很多时间.不过大家请放心,本系列不会半途夭折,并且代码干货也会持续更新.本文继续介绍表现层和Asp.net Mvc,我将在本篇讨论一些重要的设计问题和封装技巧. 是否需要将控制器分离为独立项目 经常有人问我,是否有必要将控制器从Web项目中分离出来,下面谈一下我的认识,仅供你参考,不一定正确,请根据你自己的实际情况决定. 控制器的作用是调用业务逻辑,将获得的结果传给视图显示.从根本上说,控制器只是起协调作用,它不应该自身完成复杂的…