• MySql中的事务问题


    今天非常开心,因为终于将昨天一个让我很郁闷的问题解决了。事情是这样的,根据业务逻辑的要求,需要对两张数据表进行更新,为了保证数据的完整性,就需要使用transaction的概念了。如以下代码所示:
    conn.setAutoCommit(false);
    try
    {
        PreparedStatement insertStatement = conn.prepareStatement("INSERT INTO CUSTOM_ORDER(CUSTOMER, ORDER_LIST) VALUES(?, ?)");
        insertStatement.setString(1, customer);
        insertStatement.setString(2, orderList);
        insertStatement.execute();

        PreparedStatement updateStatement = conn.prepareStatement("UPDATE PLAYER SET ACCOUNT = ACCOUNT - ? WHERE ID = ?");
        updateStatement.setInt(1, sumPrice);
        updateStatement.setString(2, customer);
        updateStatement.execute();
        conn.commit();
    }
    catch(SQLException se)
    {
        conn.rollback();
    }
    finally
    {
        conn.close();
    }

            代码很简单,而且根据我以前的经验来看,这样的代码是可以保证数据完整性的,因为对数据表两个连续的更新是一个事务,当发生异常的时候,事务会回滚。然而,测试的结果出乎意料,即使第二个SQL语句执行发生了异常,第一个SQL产生的更新结果也会体现到数据表中。查阅了很多资料,都没有发现这样的代码会有什么问题,而且Java Tutorial对于事务的介绍所给出的例子跟以上代码十分的类似,讲解中也提到两个preparedStatment只有在commit方法被调用的时候,才会作用于数据库。后来我在第一个execute方法之后设置了断点,竟然发现在执行完该方法之后,CUSTOM_ORDER表中已经多了一条记录了。但是此时,我并没有想到这会跟数据库本身有关,拼命在Google上找与JDBC相关的资料。
            最后,在跟一位朋友讨论这个问题的时候,他问我:“你用的什么数据库啊?”我说是MySql,他马上很肯定的告诉我,MySql不支持事务。“不支持事务?!”我立即去查阅了MySql相关的资料[1],果然,MySql在4.0系列之前确实是没有支持事务的。我的朋友曾在3.x系列版本的MySql下面做了两年的开发,因此才会这样告诉我这样的结论。然而4.x系列是可以支持事务的啊,我用的是4.0.16自然也支持了,为什么还会出现这样的情况呢?
            原来,MySql的数据表分为两类,一类是传统的数据表,另一类则是支持事务的数据表。支持事务的数据表分为两种:InnoDB和BerkeleyDB。我们可以通过以下的命令确认安装的MySql Server是否支持这两种数据表:
            SHOW VARIABLES LIKE 'have_innodb';
            SHOW VARIABLES LIKE 'have_bdb';
    即使MySql Server本身是支持这两种数据表,但是并不代表着创建新表的时候,新表就是属于这两种的。通常,在创建新表的时候,如果没有加以特别的说明,那么创建的新表则是传统的数据表,是不会支持事务的。因此,我的问题也就解决了,因为以上的示例代码操作的是两张没有支持事务的数据表,怎么可能去处理事务呢?
            通常我们可以通过使用如下的方式来创建支持事务的数据表:
            CREATE TABLE TABLE_NAME(FIELD1, FIELD2.... FIELDn) TYPE=INNODB;
    如果原来建好的数据表,我们也可以通过ALTER TABLE命令直接去改变数据表的类型,而不需要备份数据,然后Drop表,再建立新表,再导入数据这样烦琐的步骤。如:
            ALTER TABLE TABLE_NAME TYPE=INNODB;

     

    http://www.cnblogs.com/perhaps/archive/2004/09/15/43405.html

  • 相关阅读:
    Linux系统开发笔记
    软件测试 | Chrome 浏览器+Postman还能这样做接口测试 ?
    yum 在线安装 nginx
    画图3D Paint 3D工作区黑屏
    InfluxDB 存储结构、读、写
    纯前端保存下载文件到本地
    umijs 配置的一些用法和解释 记录
    mongodb在双活(主备)机房的部署方案和切换方案设计
    mongodb oplog详解和格式分析
    麒麟操作系统上安装docker并加载镜像
  • 原文地址:https://www.cnblogs.com/zqonline/p/1333002.html
Copyright © 2020-2023  润新知