让我们来思考,在什么情况下会出现需要同时修改连个表的操作?如何同时修改数据库中两个表数据,并保证两次修改同时成功或者失败。
假如:A表收入表、B表为商品售出记录表,每卖一件商品,B创建一条出售记录,A根据B的主键创建一条收入信息,
A表为的外键是B表的主键,售出一件商品,正确操作应该是:创建B表的一条数据,表示有商品售出,然后A表创建一条数据,表示收钱了,那么如果,B表插入数据成功,但是A表插入数据失败,就会产生一个问题,东西卖了,钱没入账!!!这就尴尬了。
那好,问题产生,我们来解决问题,我们应该怎么做,首先B表要插入数据成功,要不然A是无法插入成功的,当然是判断A表数据插入是否成功,如果成功,那就万事大吉,当A表插入失败的时候,我们就要将之前创建的B表的数据删除。方法有很多,最开始我是在插入A之前保存插入B的信息,如果A插入失败,那么删除B表中的插入数据。
一、当然我最终用的不是这种方法,而是Connetion中的 setAutoCommit()以及rollback() 方法。
二、当然这里就不得不提到commit和rollback是数据库事务的两个概念。(具体可查看:http://blog.163.com/duanshui2009@126/blog/static/13500987820126552025870/ 解释很详细)
三、当对数据库产生不可逆操作时,删除修改增加,Commit表示事物提交,意味着对事务中的操作确定,数据库只有接收到commit信息的时候才会对数据库进行保存。
Rollback表示回滚,意味着对事务的操作否定,会将数据库操作撤销。
四、当然我们在使用jdbc对数据库进行数据操作时,是程序默认自动提交的。conn.setAutoCommit(false);//设置事务的提交方式为非自动提交,参数为true表示为自动提交
明确以上四点,那么我们要做什么?
conn = JDBCUtil.getConnection();
conn.setAutoCommit(false);// 设置事务的提交方式为非自动提交
String sql = "insert into B values(?)";
int count = 0;
psmt = JDBCUtil.createPst(sql);
try {
psmt.setString(1, "B表数据");// 插入B表数据
count = psmt.executeUpdate();// B表插入数据,但是并不提交
String sql1 = "insert into A values(?)";
psmt = JDBCUtil.createPst(sql1);
psmt.setString(1, "A表数据");
count = psmt.executeUpdate();// A表插入数据,但是并不提交
conn.commit();// 一切正常提交
} catch (SQLException e) {// 出现异常,A或者B表数据插入失败
try {
count = 0;
conn.rollback();// 滚回所有操作,将数据库返回到操作前。
} catch (SQLException e1) {
e1.printStackTrace();
}
e.printStackTrace();
} finally {
try {
conn.setAutoCommit(true);// 设置事务提交方式为自动提交,这个不要省,否则下面的数据操作都需要手动提交
} catch (SQLException e) {
e.printStackTrace();
}
JDBCUtil.close(rs, psmt, null, conn);
}
if (count > 0) {
return true;
} else {
return false;
}