P286 10.5.1 N层应用程序概述 图10-33 三层应用程序结构图
表示层
·用户界面
·外部接口
·会话管理
业务逻辑层
·业务过程和规则
·业务模版
数据访问层
·数据访问和存储
·数据管理
表示层:主要包含ASP.NET Web窗体、页面用户界面等元素。该层主要完成两个任务:
1.从业务逻辑层获取数据并显示给用户
2.实现与用户的交互,将有关数据回送给业务逻辑层进行处理,其中可能包括数据验证、处理用户界面事件等。
业务逻辑层:负责处理来自数据存储或者发送给数据存储的数据
数据访问层:包含数据存储和与它交互的组件与服务
从后面的三个例子理解,表示层是aspx页面上的控件和对控件的数据绑定,用于进行显示数据、录入数据用于人机交互。在回送数据时,包括数据验证
业务逻辑层是独立的两个类:业务实体类(业务规则)、业务逻辑类(业务过程)
数据访问层是直接和数据库打交道,对数据库进行增删改查四种基本操作,这一层可以使用自定义的数据访问类,也可以使用类型化DataSet
这一节一共三个例子,下面是我对这三个例子的理解
P292 10.5.6 典型应用1 绑定数据访问层
这个例子不是三层的,它没有中间的业务逻辑层,他执行的任务直接使用SQL语句在ObjectDataSource控件中定义了
P305 10.5.7 典型应用2 绑定业务逻辑层
这个例子是三层结构的,和第一个例子相比,它多了一个业务逻辑层。这一层包含两个类:P316的业务实体类Author、P318的业务逻辑类AuthorsComponent.cs
P322 10.5.8 典型应用3 绑定类型化DataSet
这个例子好简单,就是,理解好“类型化DataSet”就可以了,它是把第一个例子里数据访问层中的自定义数据访问类替换掉了,用类型化DataSet替换,这种替换是为了简化编程
三层结构,和以前一直写的东西,不同的就是多了一个业务逻辑层,从第二个例子看,业务逻辑类是调用数据访问类中的方法进行数据处理的,实际上,他除了封装业务流程外,就是把数据库中的字段名,转换成了业务实体类中定义的公共属性,通过这种转换,让程序员可以在不清楚数据库结构的情况下,也可以很方便的编程
我想,通过这种转换也可以把分工分得更细,我前一段时间经常写的一个项目,数据库不是我创建的,我只是按分配到的页面写各类查询统计,但我对数据库不熟悉,而且没有数据字典,所以每次分配任务后,我都要先花时间把涉及的数据表和字段名弄一通,到后来,分配任务给我的人连字段名和字段描述都一起给我了
如果,我们有一个业务逻辑层,可以省去这些麻烦
在数据层中,直接使用数据库的字段名,对数据库进行增删改查等等操作
在业务层中,把数据库里的字段名,转换成所有程序员都熟悉的某个对象里的公共属性,就算不熟悉也不要紧,因为在编程中对每个属性使用///加入注释
在表现层中,只是对数据控件的数据绑定,绑定时使用的是业务实体类中的公共属性,和数据库没有直接关系
以前,我也能理解到这一步,就是,每一次看到书上说的如果修改字段名,只需要修改业务层不需要修改表现层时,我就会想到,如果我增加字段或者删除字段,不是一样子要修改表现层吗?以前,每一次这样子想到,我就对这个三层结构很不喜欢,因为他多做了这么多工作,就是实现不到增加字段时不修改页面,现在我觉得我好笨蛋,三层结构不是妈妈,业务层也不是妈妈,不是想要什么功能,他都可以实现的,三层结构有他的优点,他实现了他要做到的所有事情就够了啊
如果一个GridView只显示了“新闻标题”这样子的一列,现在我要加上“点击率”一列,有谁可以做到不修改aspx页面呢?
我不是说不可以,我们可以不设置GridView的每一列,让它在绑定数据时自动生成每一列(AutoGenerateColumns=true),这样子,如果我们修改了数据层,多返回一个字段,修改了业务层,多加一个私有字段和对应的公共属性,就可以在不修改aspx页面的情况下自动多加一列“点击率”
就是,有一个要求是,我们是在中国,我们的字段描述使用的是中文,如果我们不在编程中使用中文做公共变量,数据绑定的结果就是GridView的每一列的标题都是英文
所以,我们还是必须修改表现层中的aspx页面
就是,就算是这样子,业务层还是完成了他要完成的工作,他还是用他的优点帮我们减少了好多工作
嗯,再多说一句哈,就算是妈妈也不是要什么都可以的,不信你上班时间里跟妈妈说要去玩碰碰车,看妈妈不把你批评个够,就是,妈妈不满足我上班时间玩碰碰车,不等于妈妈不是好妈妈,对不对?
一个控件、一种应用程序的架构模型就是这样子的,我们要做的是搞清楚它的优点,把它用好,用灵活,我们不可以把它不能做的强加给他,然后还要因为它不能做它做不到的东西就放弃它
记《不要把接口当妈妈,要什么都可以》:http://www.nnllok.cn/myBlog/archives/2008/4579.html
---------------------------------------------------------------------------
2009-08-20 11:35再记:
关于业务流程,有个问题我想不好,也没找到这样子的例子:
如果一个操作动到多个表,比如添加支付方式,要同时添加用户角色的比例、代理角色的比例、商户的比例,这4个添加操作,只要有一个没有成功,数据库就必须回滚,这4个添加操作是一个业务流程,那应该把“添加支付方式”写成业务逻辑类中的一个方法吗?还是应该直接在数据访问类中写一个方法直接操作这4个表呢?
我觉得应该是写在业务逻辑类中的,就是,如果要在业务逻辑类里调用数据访问类的方法完成这4个操作,数据访问类中,添加支付方式、添加用户角色的比例、添加代理角色的比例、添加商户的比例,这4个方法就必须写成可传入SqlConnection参数,或者说是SqlCommand参数,这样子才可以保证数据库的回滚操作
如果,我们还有一个单独的“添加角色比例”这样子的功能,那在数据访问类中,“添加角色比例”这个功能就必须有两个方法了,可以是重载的方法,就是,必须有两个,一个是自连接数据库添加数据,一个是传入SqlCommand添加数据
对“角色比例”这个表,是不需要独立添加的功能的,就是,这种情况很常见的,有子母表数据时,子表经常都会有和母表数据同时添加、子表数据单独添加两种页面
如果我的想法正确,那业务流程就是业务流程,是和数据访问类没有关系的,数据访问类中,只是对“每一表或每一个视图”做增、删、改、查4种基本操作,或者是对“每一个存储过程”做调用,和数据的走向没有关系
这样子就是,界面是界面、业务流程是业务流程、数据库是数据库,完全分开了
总结:
好处:
1.界面开发人员不需要了解数据库结构
2.修改界面不需要动到业务流程,修改数据库结构(修改字段名或字段大小)不需要同时修改界面文件,如果是添加、删除字段,也可以把对界面文件的修改降到最低
3.修改业务流程不需要动界面文件,业务流程集合在类中定义,如果修改业务流程,比如删除数据前先验证有没有相关记录弄到不允许删除的,如果原来只有一个相关表需要验证,现在改为两个相关表,这时候只需要修改业务逻辑类,不需要动界面文件
不好的地方:
好像很麻烦,因为多了一个业务逻辑层,这一层相当于做一个程序中可以使用的数据字典,还有就是每个页面要完成的后台功能都被写成业务逻辑类中的一个方法,业务逻辑类只是调用数据访问类中的方法,所以小项目中,会让业务逻辑类显得麻烦