日期:2014-05-18  浏览次数:20700 次

关于DAO设计模式的疑问,事务该放在业务层处理还是DAO层
我现在在学校安排的一家公司实习兼培训,今天和公司教我们的工程师讨论了一下DAO设计模式,关于事务处理该放在哪个层,公司的工程师说事务处理是放在DAO层的方法中,我认为事务应该放在业务层,当然我没有开发经验,但是我觉得在DAO层处理事务的话有些不合理,我觉得DAO层只是实现对于表的最基本的增删改查,而业务就是对数据库的一系列增删改查,在业务层通过调用DAO层的方法来完成相应的业务功能,比如转账,转出账户的余额需要减去转出的钱,转入账户的余额需要加上转入的钱,下面的代码可能不严谨,但仅仅是做为例子来讲解我的意思

/**
*实体类
*/
public class Account{
private Integer userId;//用户ID
private Double Balance;//账户余额
....//get set方法
}
/**
*DAO接口
*/
public Interface AccountDAO{
public boolean update(Account a);
}
/**
*实现类
*/
public class AccountDAOImpl implements AccountDAO{
public void update(Account a){
   //HibernateSessionFactory是myeclipse自动生成的一个获取Hibernate Session的类,
   //它将session保存在一个静态ThreadLocal变量中,这这样对于每个线程,DAO实现类的方法
   //都能取得同一个session
   Session session = HibernateSessionFactory.getSession();
   session.update(a);
}
}

按照我的意思是在业务层里调用DAO层进行一系列的数据库操作,整个业务当做事务处理

//就不写接口了
public class BankServices{
   AccountDAO ad = new AccountDAOImpl();
   //转账业务方法
   //from 出账账户, to 进账账户
   public boolean Transfer(Account from, Account to){
     session = HibernateSessionFactory.getSession();
     Transaction ts = null;
     try{
         ts = session.beginTransaction();
         ad.update(from);
         ad.update(to);
         ts.commit();
     }catch(Exception e){
         ts.rollback();
     }finally{
         session.close();
     }
     
   }
}

而按照他的说话是,业务层不处理事务,我问他像这个转账需要涉及到两个数据库操作怎么处理事务,他说要在AccountDAO里再写一个方法Transfer(),然后给DAO写一个代理类,在代理类里关闭连接,像这样。

public class AccountDAOImpl implements AccountDAO{
Session session = null;
Transaction ts = null;
public AccountDAOImpl(){

}
public AccountDAOImpl(Session session){
    this.session = session;
}
public void Transfer(Account from, Account to){
    try{
        ts = session.beginTransaction();        
        session.update(from);
        session.update(to);
        ts.commit();
    }catch(Exception e){
        ts.rollback();
    }
}
}

/**
*代理类
*/
public class AccountDAOProxy implements AccountDAO{

AccountDAOImpl adi = null;
public AccountDAOProxy(){
    Session session = HibernateSessionFactory.getSession();
   &nbs