数据访问这样写,不写SQL即可实现增、删、改、查,跨Oracle/SQLServer多种数据库
长江支流 2007-04-12 03:14:34 一年没写BLOG了,这几天网通的奥运项目初验通过了,暂时可以轻松一下。
今天刚刚写完这个BLOG,又准备让我搞一个解析PD的XML文件的东东,把表结构和数据字典取出来直接配置到数据库的实体属性数据字典系统表中。
分享一下:
http://blog.csdn.net/flygoldfish
先来看一段代码,想想它是来实现什么的?
public class EntityTest:WebMIS.Data.EntityAccess.DBEntity
{
private int _ID = -1;
private string _Name = "test";
public int ID
{
get{return _ID;}
set{_ID=value;}
}
public string Name
{
get{return _Name;}
set{_Name=value;}
}
public EntityTest():base("TableNameOfEntityTest","ID"){}
public override IList GetFields()
{
return new string[]{"ID","Name"};
}
public override IList GetFieldValues()
{
return new object[]{_ID,_Name};
}
public override IList GetPrimaryKeyValues()
{
return new string[]{"ID"};
}
public override void LoadFrom(System.Data.DataRow entityDataRow)
{
_ID = int.Parse(entityDataRow["ID"].ToString());
_Name = entityDataRow["Name"].ToString();
}
}
public class EntityTestManagement:WebMIS.Data.EntityAccess.EntityAccess
{
public EntityTestManagement(EntityTest entity):base(entity){}
protected override WebMIS.Data.EntityAccess.IExeSql DoReturnDataAccessInstance()
{
return null; //只要实现IExeSql并返回,即可完成跨数据库操作
}
}
也许大家看出来了,EntityTest完成一个实体定义,一般来说对应于数据库表的字段。EntityTest继承于WebMIS.Data.EntityAccess.DBEntity,其实是实现了IEntityMap接口。
不写一个SQL语句,不再多写一行程序,就实现数据的增、删、改、查,这就是这样做的目的。 那么,如何达到这个目的呢?
只要把实现了IEntityMap接口的实体对象,作为WebMIS.Data.EntityAccess.EntityAccess的构造函数参数即可达到目的。
为什么会这样?这其它就是总结的结果。
因为我在做数据处时的时候,定义了实体,每个实体操作总是要写Insert、Update、Delete、FillByPK...这类的方法,而且总是会用到表的字段。这样重复做了几次之后,想想是不是应该抽象一下,并把它重构。于是发现了规律性,把Insert、Update、Delete、FillByPK提到基类WebMIS.Data.EntityAccess.EntityAccess中。
提到基类中后,问题又来了,Insert、Update、Delete、FillByPK用到的表、字段它们从何来?于是,将它们抽象出来,定义到接口中,于是IEntityMap接口诞生了,从中可以找到用到的表和字段,于是就可以同它们动态的生成需要的SQL语句,为了防止注入式攻击和非法字符引发错误,于是采用参数形式解释SQL语句。
这样,问题又来了,是不是执行SQL语句的数据库连接数据访问层就在EntityAccess中实现。答案是否定的,原因如下:
1>偶合性
为了让EntityAccess独立,放到哪里就运行到哪你,所以需要把真正招行SQL语句的代码独立出来。
2>跨数据访问
如果写死了,就可能只为一种数据库服务限制死,所以需要把真正招行SQL语句的代码独立出来,这样,谁提供数据执行应适应谁的数据库。
于是,定义 IExeSql 接口。