没事儿时,就用C#写了一个免配置的DB访问组件。基本结构是这样的----------------------------------------------
public interface IDBEngine
{
/// 保存数据
int insert(Object pojo) ;/// 更新数据
int update(Object pojo);/// 删除数据
int delete(Object pojo);
/// 提取结果集
ArrayList select(Object pojo);/// 提取结果集到DataTable
DataTable selectIntoDataTable(Object pojo);/// 提取结果集
ArrayList select(Object pojo, Pagination pagination);/// 提取连接
OleDbConnection getConnection();/// 打开事务
void beginTrans();/// 提交
void commit();/// 回滚
void rollback();/// 执行单条SQL
void executeSQL(String SQL);/// 带返回执行存储过程语句
ArrayList executeProcedureCall(String SQL, Object[] param, Object voclass);/// 不带返回执行存储过程语句
void executeProcedureCall(String SQL, Object[] param);int getInt(string SQL);int getColumnMaxValue(string TableName, string ColumnName);DataTable executeSqlProcedureCall(String SQL, object[] param);/// 执行一条SQL语句,将返回记录集放入POJO并返回POJO列表
ArrayList SelectFromSQL(string SQL, object pojo);/// 执行一条SQL语句,将返回记录集放入POJO并返回POJO列表,同时分页
ArrayList SelectFromSQL(string SQL, object pojo, Pagination pagination);/// 注销对象
void Release();/// 得到当前事务状态
int getTransStates();/// 得到数据库类型
string getDBType();/// 得到数据库当前时间
string getDBDateTime();----------------------------------所有的实体bean都要与对应的数据库表同名,字段名列名就是加get\set
并且必须要继承以下类
public class BasePojo
{//设置查询条件
public void setCondtion(Condtion c)//获取查询条件
public Condtion getCondtion()
//设置排序
public void setOrderBy_DESC(string FiledName)
public void setOrderBy_ASC(string FiledName)
public string getOrderBy()-----------------------------------我在写这个之前看了speedframework的结构,也没有太仔细看,糊里糊涂的就写了这个组件目前我看到的缺点:1、没有自主的分页功能,要依靠数据库里的一个分页存储过程(我自己也感觉这样比较垃圾,而且我只写了oracle和mssql下的分页存储过程)2、没有cache3、没有connection pool,主要是因为MS的驱动里自带了。4、实体类完全反映了数据库中的表或视图的结构。------------------------
以下有我调用时的一些示例public int CancelAssignedSalePlanCollect(SalePlan.v_SalePlan_Collect sale_plan)
{
Engine db = Engine.getInstance(); try
{
//检查计划是否已经审核
string SQL = "SELECT count(*) FROM T_ProducePlan WHERE stat != 1 AND collect_id = " + sale_plan.getId();
if (db.getInt(SQL) > 0)
{
//计划已经审核,无法取消
db.Release();
return 0;
} db.beginTrans(); //删除相关计划
T_ProducePlan produce_plan = new T_ProducePlan();
produce_plan.setCondtion(new Condtion(" and collect_id = " + sale_plan.getId()));
this.Remove(produce_plan, db); WriteLog(Config.BaseInfo.getInstance().LogString_Remove, "[删除生产计划] 删除所有汇总ID是“" + sale_plan.getId() + "”生产计划");
//将原销售计划汇总更新状态成“未分配”
SalePlan.SalePlanManager spm = new SalePlan.SalePlanManager(db);
SalePlan.v_SalePlan_Collect pln = new SalePlan.v_SalePlan_Collect();
pln.setStat("1");
pln.setCondtion(new CSDN.DBQuery.Condtion(" and id = " + sale_plan.getId()));
spm.modifyCollectSalePlan(pln, db); WriteLog(Config.BaseInfo.getInstance().LogString_Modify, "[修改市场需求汇总] 修改ID是" + sale_plan.getId() + "的市场需求汇总,其状态更改为“未分配”"); db.commit(); db.Release(); return 1;
}
catch (Exception ex)
{
if (db.getTransStates() == 1)
{
db.rollback();
}
Utils.LogWriter.Error("取消一个销售计划汇总所分配的生产计划时出错:" + ex.Message);
return -1;
} }-------------------------------------
想请高手给我指点一下,这个组件在设计结构上都有哪些缺陷,我应该怎么要改进它。只管说,我知道和Hibernate比,它一无是处
public interface IDBEngine
{
/// 保存数据
int insert(Object pojo) ;/// 更新数据
int update(Object pojo);/// 删除数据
int delete(Object pojo);
/// 提取结果集
ArrayList select(Object pojo);/// 提取结果集到DataTable
DataTable selectIntoDataTable(Object pojo);/// 提取结果集
ArrayList select(Object pojo, Pagination pagination);/// 提取连接
OleDbConnection getConnection();/// 打开事务
void beginTrans();/// 提交
void commit();/// 回滚
void rollback();/// 执行单条SQL
void executeSQL(String SQL);/// 带返回执行存储过程语句
ArrayList executeProcedureCall(String SQL, Object[] param, Object voclass);/// 不带返回执行存储过程语句
void executeProcedureCall(String SQL, Object[] param);int getInt(string SQL);int getColumnMaxValue(string TableName, string ColumnName);DataTable executeSqlProcedureCall(String SQL, object[] param);/// 执行一条SQL语句,将返回记录集放入POJO并返回POJO列表
ArrayList SelectFromSQL(string SQL, object pojo);/// 执行一条SQL语句,将返回记录集放入POJO并返回POJO列表,同时分页
ArrayList SelectFromSQL(string SQL, object pojo, Pagination pagination);/// 注销对象
void Release();/// 得到当前事务状态
int getTransStates();/// 得到数据库类型
string getDBType();/// 得到数据库当前时间
string getDBDateTime();----------------------------------所有的实体bean都要与对应的数据库表同名,字段名列名就是加get\set
并且必须要继承以下类
public class BasePojo
{//设置查询条件
public void setCondtion(Condtion c)//获取查询条件
public Condtion getCondtion()
//设置排序
public void setOrderBy_DESC(string FiledName)
public void setOrderBy_ASC(string FiledName)
public string getOrderBy()-----------------------------------我在写这个之前看了speedframework的结构,也没有太仔细看,糊里糊涂的就写了这个组件目前我看到的缺点:1、没有自主的分页功能,要依靠数据库里的一个分页存储过程(我自己也感觉这样比较垃圾,而且我只写了oracle和mssql下的分页存储过程)2、没有cache3、没有connection pool,主要是因为MS的驱动里自带了。4、实体类完全反映了数据库中的表或视图的结构。------------------------
以下有我调用时的一些示例public int CancelAssignedSalePlanCollect(SalePlan.v_SalePlan_Collect sale_plan)
{
Engine db = Engine.getInstance(); try
{
//检查计划是否已经审核
string SQL = "SELECT count(*) FROM T_ProducePlan WHERE stat != 1 AND collect_id = " + sale_plan.getId();
if (db.getInt(SQL) > 0)
{
//计划已经审核,无法取消
db.Release();
return 0;
} db.beginTrans(); //删除相关计划
T_ProducePlan produce_plan = new T_ProducePlan();
produce_plan.setCondtion(new Condtion(" and collect_id = " + sale_plan.getId()));
this.Remove(produce_plan, db); WriteLog(Config.BaseInfo.getInstance().LogString_Remove, "[删除生产计划] 删除所有汇总ID是“" + sale_plan.getId() + "”生产计划");
//将原销售计划汇总更新状态成“未分配”
SalePlan.SalePlanManager spm = new SalePlan.SalePlanManager(db);
SalePlan.v_SalePlan_Collect pln = new SalePlan.v_SalePlan_Collect();
pln.setStat("1");
pln.setCondtion(new CSDN.DBQuery.Condtion(" and id = " + sale_plan.getId()));
spm.modifyCollectSalePlan(pln, db); WriteLog(Config.BaseInfo.getInstance().LogString_Modify, "[修改市场需求汇总] 修改ID是" + sale_plan.getId() + "的市场需求汇总,其状态更改为“未分配”"); db.commit(); db.Release(); return 1;
}
catch (Exception ex)
{
if (db.getTransStates() == 1)
{
db.rollback();
}
Utils.LogWriter.Error("取消一个销售计划汇总所分配的生产计划时出错:" + ex.Message);
return -1;
} }-------------------------------------
想请高手给我指点一下,这个组件在设计结构上都有哪些缺陷,我应该怎么要改进它。只管说,我知道和Hibernate比,它一无是处
直接用sqlhelper楼上正解这种东西本来就不存在答案,你认为好用就行了
/// 保存数据
int insert(Object pojo) ;/// 更新数据
int update(Object pojo);/// 删除数据
int delete(Object pojo);
/// 提取结果集
ArrayList select(Object pojo);/// 提取结果集(按分页)
ArrayList select(Object pojo, Pagination pagination);我是这样做的,不过考虑到特殊情况下使用了比较复杂的,我没有在SqlGeneral里实现的SQL,所以加了一下的方法:-----------------------/// 执行一条SQL语句,将返回记录集放入POJO并返回POJO列表
ArrayList SelectFromSQL(string SQL, object pojo);/// 执行一条SQL语句,将返回记录集放入POJO并返回POJO列表,同时分页
ArrayList SelectFromSQL(string SQL, object pojo, Pagination pagination);又想到了可能有人喜欢用Datatable,所以加了:/// 提取结果集到DataTable
DataTable selectIntoDataTable(Object pojo);---------------------------但就像你说的,以上这些方法的确是不应该加上的,它们让这个东西看起来不伦不类了!但要实现比较复杂的sql的话,除非定义一个自己的查询语言,就像HQL或DLINQ那样的,除此之外我还没想出有什么好办法,你是怎么做的呢?
如果有兴趣,我们可以私聊。我正在ORM方面的框架。也碰了你上面的一些问题,对单关键字分页好做,但是多关键字分页不好处理。
ArrayList select(Object pojo, Pagination pagination);我把分页信息传递进来,就调用存储过程来做了,和框架是分开的!这有点不符合ORM,不过速度比较快,此外也是因为我没有太好的办法,由于太懒,Hibernate的分页方式我都没有研究过,但以前研究过Apache的一个分页标签,叫做displaytag!
分页和缓存也不能算是缺点,因为很难做到通用。大部分情况下,ORM主要作用是减少代码量和规范接口,不可能做到全能的。
请给一个正解光说不练假把式呵呵。小弟C#新手。