.NET 业务框架开发实战之六 DAL的重构
  前言:其实这个系列还是之前的".NET 分布式架构开发实战 ",之所以改了名字,主要是因为文章的标题带来了不少的歧义:系列文章中本打算开发一个简化业务发的流程的Framework,然后用这个Framework再来实战,开发一个分布式的应用。改了名字。给大家带来了不便,敬请见谅。

  本篇的议题如下:
   1. 确定DAL的接口的定义。

  系列文章链接:

[原创].NET 分布式架构开发实战之一 故事起源

[原创].NET 分布式架构开发实战之二 草稿设计

[原创].NET 分布式架构开发实战之三 数据访问深入一点的思考

[原创].NET 分布式架构开发实战之四 构建从理想和实现之间的桥梁(前篇)

[原创].NET 分布式架构开发实战五 Framework改进篇

[原创].NET 业务框架开发实战之六 DAL的重构

[原创].NET 业务框架开发实战之七 业务层初步构想

[原创].NET 业务框架开发实战之八 业务层Mapping的选择策略

[原创].NET 业务框架开发实战之九 Mapping属性原理和验证规则的实现策略

[原创].NET 业务框架开发实战之十 第一阶段总结,深入浅出,水到渠成(前篇)

[原创].NET 业务框架开发实战之十 第一阶段总结,深入浅出,水到渠成(后篇)

  之前在开发DAL中,提出了一些思想,也设计了一些接口。现在就把DAL的一些设计完善起来。说是“完善”,并不是说把所有的代码都实现,而是把该定义的接口,方法敲定下来。Richard认为,设计一个架构或者Framework的时候,开始是接口的定义,定义好各层之间交互的接口,然后才是具体代码的实现。

  因为在设计Framework的时候,首先要考虑这个Framework的使用者是谁,希望他们怎么样来使用开发出来的这个Framework。在这里,Richard很明白:Framework的使用者就是自己公司里的开发人员。而且还要使得开发的使用尽量的方便,不要到处去配置一些文档,最好就是把Framework引入进来,稍微配一下就使用。

  在Richard设计的Framework中,就DAL而言,如果希望DAL返回DataTable,DataReader等给BLL,那么需要配置的仅仅只是指明数据库的连接字符串;如果希望DAL返回的数据实体给BLL,那么就得把一张张的表映射成为实体,然后让这些实体继承IDataEntity接口就行了(生成实体可以用ORM工具,或者自己手写代码)。

Richard思考了之前对DAL的设计,在此他做了一些改进。

  首先就是对于IDataContext的重新设计和理解:之前的设计是定义了IDataContext,然后用不同的方式实现这个接口,如LinqDataContext.Provider就是用Linq的方法来返回结果(DataResult)。现在Richard认为IDataContext其实就是用来操作数据库的,所以返回的结果就应该是操作数据之后的结果,如Update操作就返回受影响的行数或者是否更新成功。至于是否要把一些额外的信息包装返回给BLL,就不是IDataContext的实现者的事情了。而且Richard还考虑到了需要在一定程度上支持原生的ADO.NET,起码给ADO.NET预留接口。

  基于此,Richard就把IDataContext定义为一个接口声明,然后再定义了IDataEntityContext,和IDataTableContext来继承IDataContext,他们的关系图如下:

  

  

   其中IDataEntityContext使用Linq和Entity Framework来实现,而IDataTableContext就是用ADO.NET的方式来实现。

  IDataEntityContext接口的和系列文章中定义的一些方法差不多,但是做了修改。其中有一点要提的就是:ICriteria就是所有条件对象要实现的接口(查询对象也是条件对象的一种)。例如,可以根据相应的条件删除,更新数据。

代码

 /// <summary>
    /// 所有的数据实体执行者实现这个借口
    /// </summary>
    public interface IDataEntityContext:IDataContext
    {
        TEntity Add<TEntity>(TEntity entity) where TEntity : IDataEntity;
        List<TEntity> Add<TEntity>(List<TEntity> entityList) where TEntity : IDataEntity;

bool Update<TEntity>(TEntity entity) where TEntity : IDataEntity;
        bool Update<TEntity>(List<TEntity> entityList) where TEntity : IDataEntity;
        bool Update(ICriteria condiftion, object value);

bool Delete<TEntity>(TEntity entity) where TEntity : IDataEntity;
        bool Delete<TEntity>(List<TEntity> entityList) where TEntity : IDataEntity;
        bool Delete(ICriteria condition);

int GetCount(ICriteria condition);
        List<TEntity> Query<TEntity>(ICriteria condition);
        List<TEntity> Query<TEntity>(ICriteria condition, int pageIndex, int pageSize, ref int entityCount) where TEntity : IDataEntity;
        List<object> Query(ICriteria condiftion);
    }

  另外就是多了一个 List<object> Query(ICriteria condiftion);方法,之所以有这个方法,Richard考虑到,可能开发人员想要直接自己写SQL语句去执行,如select avg(Count),sum(Name) from Customer...,开发人员可以写任意的语句,所以返回一个实体类不现实,就返回一个List<object>。

  还有一点就是关于查询对象的改进:以前仅仅只是定义了查询对象的接口,现在用ICriteria 接口中定义来条件对象,而且还可以在条件对象声明是在对数据操作是否采用事务或者缓存。

代码

 /// <summary>
    /// 所有的条件对象都要从这个接口继承
    /// </summary>
    public interface ICriteria
    {
        string Name { get; set; }
        bool IsCache { get; set; }
        bool IsTransaction { get; set; }
    }

  

  之后Richard又定义了一个IDataProvider,接口,声明如下 :

代码

 /// <summary>
    /// 数据提供者要实现的借口
    /// </summary>
    public interface IDataProvider
    {
        DataResult<TEntity> Add<TEntity>(TEntity entity) where TEntity : IDataEntity;
        DataResult<TEntity> Add<TEntity>(List<TEntity> entityList) where TEntity : IDataEntity;

DataResult<TEntity> Update<TEntity>(TEntity entity) where TEntity : IDataEntity;
        DataResult<TEntity> Update<TEntity>(List<TEntity> entityList) where TEntity : IDataEntity;
        bool Update(ICriteria condiftion, object value);

DataResult<TEntity> Delete<TEntity>(TEntity entity) where TEntity : IDataEntity;
        DataResult<TEntity> Delete<TEntity>(List<TEntity> entityList) where TEntity : IDataEntity;
        bool Delete(ICriteria condiftion);

int GetCount(ICriteria condition);

DataResult<TEntity> GetOne<TEntity>(ICriteria condition) where TEntity : IDataEntity;
        DataResult<TEntity> GetList<TEntity>(ICriteria condition) where TEntity : IDataEntity;
        DataResult<TEntity> GetPageData<TEntity>(ICriteria condition, int pageIndex, int pageSize, ref int entityCount) where TEntity : IDataEntity;
        List<object> GetCustomData(ICriteria condiftion);
    }

   之所以要定义这个接口,其实 Richard就是想让实现了IDataContext的类踏踏实实的去做底层的数据操作,至于数据操作之后的结果以什么形式给BLL,不用IDataContext的实现者来关心,而是用IDataProvider的实现者来关心。

  在IDataProvider的实现者在底层就是调用了IDataContext的实现者的方法,然后在IDataProvider中,对外提供了一些更加友好和方便使用的方法,最后在BLL中直接依赖的就是IDataProvider,而不是IDataContext。

  另外,对于IDataProvider返回的DataResult也做了一些修改:如果返回的是数据实体,即 使用的是IDataEntityContext来提供底层的数据操作,那么DataResult<TEntity>是没有问题的;但是如果使用的是IDataTableContext,那么返回DataResult<TEntity>就不行了,因为IDataTableContext查询方法可能返回的DataTable,或者DataReader.所以,在设计中叶预留了一个接口:让IDataProvider返回的结果实现IDataResult接口,那么ataResult<TEntity>继承这个接口,主要用来返回数据实体,如下:

  

  DAL的设计就到这里,下一篇文章就开始讲述对业务层的一些思考。

  版权为小洋和博客园所有,转载请标明出处给作者。

    http://www.cnblogs.com/yanyangtian

   代码下载  

  

转载于:https://www.cnblogs.com/yanyangtian/archive/2010/06/03/1750444.html

[原创].NET 业务框架开发实战之六 DAL的重构相关推荐

  1. [原创].NET 业务框架开发实战之十 第一阶段总结,深入浅出,水到渠成(前篇)...

    .NET 业务框架开发实战之十 第一阶段总结,深入浅出,水到渠成(前篇) 前言:这个系列有段时间没有动了.主要是针对大家的反馈在修改代码.在修改的过程中,也有了一些新的体会,这里和大家分享一下,同时也 ...

  2. [原创].NET 业务框架开发实战之九 Mapping属性原理和验证规则的实现策略

    .NET 业务框架开发实战之九 Mapping属性原理和验证规则的实现策略 前言:之前的讨论一直关注在怎么从DAL中获取数据,以及数据的Mapping问题.实际上,一个业务框架最主要的作用就是简化业务 ...

  3. [原创].NET 业务框架开发实战之十 第一阶段总结,深入浅出,水到渠成(后篇)...

    .NET 业务框架开发实战之十 第一阶段总结,深入浅出,水到渠成(后篇) 前言:接着上篇来. 系列文章链接: [原创].NET 分布式架构开发实战之一 故事起源 [原创].NET 分布式架构开发实战之 ...

  4. [原创].NET 分布式架构开发实战五 Framework改进篇

    原文:[原创].NET 分布式架构开发实战五 Framework改进篇 .NET 分布式架构开发实战五 Framework改进篇 前言:本来打算这篇文章来写DAL的重构的,现在计划有点改变.之前的文章 ...

  5. [原创].NET 分布式架构开发实战之一 故事起源

    阅读: 1320 评论: 18 作者: 小洋(燕洋天工作室) 发表于 2010-05-23 09:03 原文链接 .NET 分布式架构开发实战之一 故事起源 前言:本系列文章主要讲述一个实实在在的项目 ...

  6. 企业级业务系统开发实战-序言

    前些年一直在做微软的解决方案实施与软件开发的工作.在学习.项目实施.开发与管理的过程中学到了别人不少好的东西,也自身总结了大量的经验,希望能够通过一个系列来跟大家分享关于软件开发方面的内容. 这个开发 ...

  7. php实战开发管理系统,深入浅出PHP框架Thinkphp实战开发(权限管理、CMS内容管理系统)...

    Thinkphp课程大纲: ThinkPHP 是一个免费开源的,快速.简单的面向对象的 轻量级PHP开发框架 ,创立于2006年初,遵循Apache2开源协议公布,是为了敏捷WEB应用开发跟简化企业应 ...

  8. python接口自动化测试书籍_蜗牛出版之《接口自动化测试开发实战教程》书籍详解!...

    各位老铁,大家好~ 上周,我们通过一篇分享,给大家详细介绍了蜗牛创想的出版业务. 还不了解的小伙伴请戳:除了培训和研发,我们还有一项90%的人都未曾关注到的业务! 本周开始,我们将对已经出版的< ...

  9. Camera开发系列之六-使用mina框架实现视频推流

    章节 Camera开发系列之一-显示摄像头实时画面 Camera开发系列之二-相机预览数据回调 Camera开发系列之三-相机数据硬编码为h264 Camera开发系列之四-使用MediaMuxer封 ...

最新文章

  1. on 和where条件的放置详解
  2. mysql upload_关于mysql数据库里的 upload子查询问题
  3. [MSSQL]COALESCE与ISNULL函数
  4. centos linux7修改主机名,CentOS7操作系统下永久修改主机名
  5. rabbitmq接口异常函数方法_分布式系统消息中间件——RabbitMQ的使用进阶篇
  6. java启动servlet_Java Servlet 运行原理分析
  7. BUUCTF Web [极客大挑战 2019]EasySQL
  8. 分段式多级离心泵_D型卧式多级泵结构组成及工作原理
  9. java常见的定时任务
  10. perl中的文件句柄
  11. java gd库_[转]gd库的安装
  12. 实用EXCEL之考勤数据的表合并
  13. FSViewer 一款功能强大的看图软件
  14. Android架构学习之路三-MVX
  15. 【错误记录】Android Studio 编译报错 ( Module was compiled with an incompatible version of Kotlin. The binary )
  16. PDF裁剪页面及调整页面大小的方法
  17. 李宏毅2021年机器学习笔记———卷积神经网络
  18. Android工程师面试准备知识点
  19. 自动剪辑视频的软件,视频自动剪辑生成软件如何剪辑视频和制作视频
  20. IDEA maven mvn install无法引用手动导入的jar包的解决方式 图文详细

热门文章

  1. 复述-简历-面试-常见问答整理
  2. Docker容器开机自动启动
  3. php 获取视频首帧,从视频中提取特定帧的最快方法(PHP/ffmpeg/anything)
  4. 8K分辨率7680*4320
  5. 有了商城源码如何部署到本地服务器_怎么将本地做好的网站部署到服务器上?...
  6. api 文件夹index.js 集合写法
  7. 小汤学编程之JavaEE学习day03——JSP组成结构、JSP原理、JSP生命周期、JSP九大内置对象、四大作用域、JSP的MVC模式
  8. Win10远程连接自己的电脑提示“登陆没有成功”的解决方案
  9. 跟ASP.NET MVC一起使用jQuery
  10. Unity下一轮最大的变革-Entity Component System C# Jobs System