异常处理
巧用异常实现事务处理
事务的概念
数据库事务(Database Transaction) ,是指作为单个逻辑工作单元执行的一系列操作,要么完全地执行,要么完全地不执行。 事务处理可以确保除非事务性单元内的所有操作都成功完成,否则不会永久更新面向数据的资源。通过将一组相关操作组合为一个要么全部成功要么全部失败的单元,可以简化错误恢复并使应用程序更加可靠。一个逻辑工作单元要成为事务,必须满足所谓的ACID(原子性、一致性、隔离性和持久性)属性。事务是数据库运行中的逻辑工作单位,由DBMS中的事务管理子系统负责事务的处理。
分析:本项目中的事务处理(service层)可以通过try/catch模块实现,通过捕获sql异常以及手工抛出逻辑异常,
如果没有异常产生,在try模块最后提交事务
否则在catch模块(有异常)实现事务回滚。
实现:
dao层:
数据访问层出现的sqlexception抛出
service层:
1.捕获dao层抛出的sql异常,抛向view层
2.对dao层拿到的结果进行逻辑判断,若为false则抛出带信息的exception
回滚事务并把异常抛向view层
view层:
捕获并打印异常信息
这里注意一点:exception是所有异常的基类,可以捕获任意异常!
存款系统的转账功能:service层
@Override
public void transfer(User user, User targetu, double money)
throws Exception {
Connection conn = ConnectionFactory.getConnection();
try {
// 取消自动提交事务
conn.setAutoCommit(false);
User u = ud.queryByUname(conn, user.getUname());
System.out.println(u);
if (u.getMoney() < money) {
//若余额少于转账额度抛出异常,catch捕获并回滚
throw new Exception("余额不足,请充值");
}
ud.updateMoneyByUname(conn, user.getUname(), -money);
User u1 = ud.queryByUname(conn, targetu.getUname());
if (u1 == null) {
//若转账对象不存在抛出异常,catch捕获并回滚
throw new Exception("用户不存在");
}
ud.updateMoneyByUname(conn, u1.getUname(), money);
Record record = new Record();
record.setUid(u.getId());
record.setContent(u.getUname() + "向" + u1.getUname() + "转账了"
+ money);
rd.insert(conn, record);
//执行到最后一步说明没有异常情况,就提交事务,service层走完
conn.commit();
} catch (SQLException e) {
//e.printStackTrace();
//捕获异常并回滚事务然后抛出异常
conn.rollback();
throw e;
}