实战项目分析(二)

(接上文

 

4.     强类型DataSet

上面讲到了业务对象和强类型DataSet两种领域模型的使用问题。其实强类型DataSet.NET中很好的一种方案,它集成了数据库和面向对象两种优点,如果使用的好的话,会事半功倍,但使用不好的话,麻烦也很大。

在本系统中,强类型DataSet被赋予很多使命:从数据库中获取信息(数据存取层)、业务处理(业务逻辑层)和数据展现(展现层),贯穿了整个系统。这样就使得整个系统对强类型DataSet的数据结构非常依赖,一旦数据库发生变化,所有的代码(从数据存取到展现层)都要修改代码来。并且最要命的是强类型DataSet可以自动感知数据库的变化,自动更新同步。试想,如果你是这个系统的编码人员,会不会时时都提心吊胆呢?

很显然,这是一种糟糕的设计。在分层结构中,任何数据结构都不能贯穿始终,特别是与数据库结构。这回带来难以置信的麻烦。分层,其实就是要隔离这种变化给系统带来的连锁反应。使底层的修改不影响到顶层,反之亦然。

当然这是不是意味着强类型DataSet就不能使用了呢?当然不是的。强类型DataSet是非常好的连接数据存取层和业务逻辑层的纽带,因为它既有数据库结构又有对象特性。所以,只要我们能在两个层次中各自屏蔽细节,依赖于抽象而不是实现,强类型DataSet就可以在系统中发挥重要的作用。

5.     展现层太臃肿

本系统的很大一部分UI都是B/S的,采用ASP.NET构建。但我发现很多的WebPage中包含有大量的界面逻辑和业务逻辑,基本每个WebPage的代码都在几百行,有点甚至上千行。试想,这样的UI维护起来

对于每一个开发者来说,大概都经历过这种痛苦,为了数据库的一个字段的修改,要从底层到顶层,全部修改一便,而且UI的修改是最麻烦的,往往是越改越烦!

其实对于UI的设计模式已经很成熟了,大家都知道MVC模式吧。就是一个很成熟,很实用的UI设计模式。另外还有MVP模式,这个是MVC的基础之上提出来的,跟MVC思想相同,但细节上有所不同而已。MVC模式网上有很多的资料,也有很多有名的应用案例。MVP则被广泛应用在微软P&P团队的很多项目中,诸如:Software Factory系列中都有应用。

下面是MVC模式和MVP模式的对比:

 


另外,关于两种模式的详细对比,可以参考另一位MVP:TreeLee的文章:ASP.NET MVC FrameworkWCSFMVP模式之小小比较

6.     自定义事务

.Net framework 2.0中内置了对事务的支持,不但可以管理进程内的事务(包括SQLServer事务),还可以自动提升至MSDTC来管理分布式事务(包括WCF事务)。所以我们无需再编写任何事物的管理代码。

本系统中使用了Enterprise Library中的Data Access Application Block作为数据存取方案。但却没有很好地利用.Net framework 2.0的事务功能,而是自己写了很多管理事务的代码。例如使用一个TransactionContext类管理事务的执行,在很多数据存取的方法上支持传入TransactionContext类型的参数,用来管理事务边界。

这样不仅需要花费精力维护TransactionContext类,管理事务的执行,也使数据存取接口变的很复杂,臃肿。

其实我们完全可以利用TransactionScope这一.Net framework2.0中的事务处理类还管理事务。最简单的方式是:

Using(TransactionScope cpe = new TranscationScope())

{

           数据操作方法1();

           数据操作方法2();

           …

           数据操作方法N();

}

这样就可以自动提交和回滚事务了,而且可以根据实际情况,如果其中某个方法调用了分布式事务的话,可以自动升级为MSDTC事务。

关于如何使用.Net framework2.0中的事务功能,可以参考:Introducing System.Transactions in the .NET Framework 2.0

7.     其它问题

还有一些其它的小问题,虽然不涉及到系统架构,但也会带来一些负面的影响,包括:

A. 代码重复

a)         很多数据查询方法功能相同,只是返回的数据“格式” 不同(有的返回DataSet,有的返回DataRow,有的返回实体对象),为了调用方便,做了很多重载的方法,但没有考虑代码重复利用,造成大量的代码冗余。

B. 公共模块

a)         设计者把系统中使用到的公共代码和枚举等等组织在一起,放在一个文件中,为各个项目所使用。其实这本来很好,但是我却发现,公共模块同时被三个层次引用,这样也是很不好的。这样会使得系统的分层结构遭到破坏,公共模块难于理解和使用。应该把属于各层专属使用的功能集成到各自的层中,每个层中设一个公共模块,这样既保障了分层的清晰,同时又很好地规划了公共模块。


 (完)

posted on 2008-08-13 11:31  zhaojunqi  阅读(3571)  评论(25编辑  收藏  举报

导航