数据访问这样写,不写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 接口。

...全文
1532 31 打赏 收藏 转发到动态 举报
写回复
用AI写文章
31 条回复
切换为时间正序
请发表友善的回复…
发表回复
amandag 2007-04-17
  • 打赏
  • 举报
回复
up
lxwin01 2007-04-17
  • 打赏
  • 举报
回复
认真思考,多做实践。
IDataBase database=new OracleDataBase(oracleConfig);
User user=new User(...,new UserDetail(..));
IDataProvider userProvider=database.GetDataProvider(user);
userProvider.Insert(user);
User和UserDetail相应信息插入到Oracle中。
将来如果碰到不知道的数据库,自己可以根据框架进行实现,无法确定自己的框架(少定接口,多写抽象类,小功能类)到一定时候框架就慢慢浮显上来了。
长江支流 2007-04-16
  • 打赏
  • 举报
回复
适合自己的就是好的。不能说哪个强哪个弱
YunAo2008 2007-04-16
  • 打赏
  • 举报
回复
up
曲滨_銘龘鶽 2007-04-16
  • 打赏
  • 举报
回复
上面那种封装,对于简单的标准的sql操作还可以
如果遇到,插入自动编号,oracle 和 sqlservice 就不一样了
插入后取得主键,在往子表插入的那种操作,很多数据库都不一样。
这只是很容易碰到的问题。


如果要兼容全部数据库要满足

1) 如果你都是单一表操作而且只用标准sql ,或全部数据库都支持的
就能基本能完成你的业务。

2)数据库的设计,包括字段的类型都是每个数据库通用的
如: sqlservice 有bool 型,oracle 没有
Oracle 有数组,sqlservice 没有
如果你实体类里有bool 的 oracle 取数据的时候就和sqlservice 不一样
sqlservice 不用强制转化类型直接 (bool) 转化即可
oracle 就的强制转化一下,而且oracle 的全部数字类型在.net 下都是decmail



lxwin01 2007-04-14
  • 打赏
  • 举报
回复
对于Petshop讨论。
http://community.csdn.net/Expert/topic/5449/5449122.xml?temp=.4689447
newnan 2007-04-14
  • 打赏
  • 举报
回复
petshop4。0也对不同数据库进行了封装,不知道有你的好吗?
lxwin01 2007-04-14
  • 打赏
  • 举报
回复
http://community.csdn.net/Expert/topic/5169/5169703.xml?temp=.0698511
多考虑解藕,因为在满足不同需要时,ORM有时是很必要,但对于性能上有要求的框架是否能够满足自动ORM和半ORM.

public class User
{
[Relation(Typeof(UserDetail),RelationType.OneToOne)]
public UserDetail detail{get;set;}
.....
}

public class UserDetail
{
....
}

User user=new User(...,new UserDetail(..));
ISqlSimpleInsertBuilder sqlInsertBuilder=new SqlServerSimpleInsertBuilderSqlBuidler();
string sqlInsert=sqlInsertBuilder.Parse(user);
database.Execute(sqlInsert);

ISqlSimpleSelectBuilder sqlSelectBuilder=new SqlServerSimpleSelectBuilderSqlBuilder();
string sqlSelect=sqlSelectBuilder.Parse(ConditionsType.Custom,"User.UserId=UserDetial.UserId And UserDetial.Age>30");
DataSet ds=database.Select(sqlSelect);
如果要ORM,在上面架构一层将结果进行映射,对于SqlBuilder有地方不满意完全可以进行重构。

//ISqlComplexBuilder sqlBuilder=new SqlServerComplexSqlBuidler();
//StringCollection sqls=sqlBuilder.InsertParse(user);
xiang_li5257 2007-04-14
  • 打赏
  • 举报
回复
mark
lcw321321 2007-04-14
  • 打赏
  • 举报
回复
mark
jinanjiang 2007-04-13
  • 打赏
  • 举报
回复
study
xiaotupansy 2007-04-13
  • 打赏
  • 举报
回复
侃侃
LoveCleverDog 2007-04-13
  • 打赏
  • 举报
回复
mark
eeyyllehs 2007-04-13
  • 打赏
  • 举报
回复
楼主好人啊
GXY2005 2007-04-13
  • 打赏
  • 举报
回复
算是公益广告!
任老先生 2007-04-13
  • 打赏
  • 举报
回复
NBear
用这个解决方案!

NBear V3

Description:
A rapid/high performance/distributed/ORM framework based on .NET 2.0.
V3 of NBear is a super big re-design based on the experience of V2, which reserves the IoC and Web module of V2 and bring a new ORM (in NBear.Common/NBear.Common.Design and NBear.Data) implementaion. ORM of NBear is very easy to use, you should be able to use it in real development in 10 minutes.

License: BSD
Copyright: 2005-2008 Teddy.CN
Contact: Teddy (shijie.ma(at)gmail.com)
Blog: http://teddyma.cnblogs.com
Download: http://sf.net/projects/nbear


Acknowledgement

Thanks alex(http://qpg2006.cnblogs.com) !
The first version of NBear.MQ (NBear.IoC in v2+ enhanced this function much) in NBear V1 refers
much of alex's QPG framework. It is also alex's suggestion to create a this kind of component
into NBear. Without you, we will never see NBear.MQ.

-

Folder Structure:

src - Full source code of NBear
dist - Distributed binary dlls of NBear
lib - Depending dlls of NBear
cases - Full functional cases based on NBear
doc - Documents.
tutorials - Step by Step tutorials
anan221 2007-04-13
  • 打赏
  • 举报
回复
jf
长江支流 2007-04-13
  • 打赏
  • 举报
回复
http://blog.csdn.net/flygoldfish/archive/2007/04/12/1561792.aspx
amandag 2007-04-13
  • 打赏
  • 举报
回复
学习
yumanqing 2007-04-12
  • 打赏
  • 举报
回复
UP有空看看
加载更多回复(11)

110,561

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧