LINQ to SQL建立独立的BLL实体层

真正使用ASP.NET是去年下半年。在没有使用LINQ之前,并没有对DOTNET系统进行分层。因为有很多困难,比如对于数据访问层(DAL),需要借助于外部的ORM工具如NHibernate等,我根本不熟悉。于是所有的代码都写在ASPX.VB里面了,而且使用SQL语句与ADO.NET+RecordSet进行数据库操作。到现在系统已经很难维护了。

自从今年上半年学习了LINQ之后,发现LINQ to SQL自动为我们生成了DAL层。于是随着SQL语句的被取代,系统分层的难度降低了不少,自然开始进行层次划分。

今天和同事讨论分层次的问题。我的同事并不是专业程序员,我们两个人现在一起开发一个公司内部的应用系统,以前用SQL语句操作数据库也是因为他只熟悉这么做,才那么做的。我对他讲分层的好处,他说也没什么好处呀,代码写起来还麻烦。我说“现在麻烦一点,以后维护起来就方便了”。我用“蝴蝶效应”来描述直接使用SQL语句来访问数据库的危险性;用“捡了芝麻丢了西瓜”来描述他想写一个函数,通过获取LINQ to SQL query返回的anonymous type的字段名来自动绑定GridView的做法,因为真正的代码优化是架构性的,而不是一两个投机取巧的方法。在解释了许多之后,我总结了一句话:“现在不是分不分层次的问题,而是如何更好的分层次的问题”。没有层次的系统是不可维护的,而不可维护的系统是没有用的系统。

未建立独立BLL实体层的架构

现在在使用LINQ to SQL的时候,虽然建立了BLL层,但是只是在LINQ to SQL自动生成的实体类的基础上添加了对数据的Shaping逻辑。在跨表操作的时候,由于LINQ查询返回的是Anonymous Type而不是强类型,这就导致通过函数返回了IQueryable之后无法通过对象属性(无法使用“.”符号调用成员属性)操作数据。所以许多跨表操作的业务逻辑不得不在表现层进行。可以用下图表示现有的架构:

image

其中的Data Object Model以及Data Entities是由LINQ to SQL自动生成的。

建立独立BLL实体层的架构

而真正的三层架构的图应该是:

image

这两幅图参照Manning《LINQ in Action》中的图绘制。如果下一层次改动了,上面的层次会随之震动。从这两幅图上可以直观的看到,通过定义Business Entities,可以隔离DAL Entities改变对表现层的影响。如果要完全的将LINQ DAL Entity与表现层隔离,那么就必须定义一套完整的BLL Entity对象集。对于Large-Scale系统,这样是有必要的。

建立业务层次的实体类,这样在表现层只需要在这些对象的基础上进行操作了。但是这样要求自定义许多Business Entity Classes。这样是否维护量太大呢?先不考虑这个,来个具体的示例:

class CustomerBLL{MyCustomId, MyCustomName }

Dim customers as IQueryable(of CustomerBLL)
customers = From customer in db.Customers _
                   Select newc = New MyCustomObject With { _
                        .MyCustomId = customer.CustomerId _
                        .MyCustomName = customer.CustomerName _
                   }

这样就建立了一个BLL层的Object Class。在BLL Entity对象中一般不需要添加LINQ DAL Entity的那些lazy-load等特性。

一些问题

If you create a DAL with LINQ to SQL and have your methods return something like IQueryable<T>, you don’t return data but you do return queries. 那么对于创建了自定义类型的LINQ语句来说,是否也是这样呢?暂时的考虑是“是这样”,因为这样的语法并没有超出上述的原理的范畴。

posted @ 2009-08-28 13:00  汗水房  阅读(563)  评论(0编辑  收藏  举报