您的位置:首页 > 编程语言 > Java开发

spring + hibernate + mysql 事务不回滚

2012-11-20 14:52 330 查看
首先声明,这个问题涉及到的数据库是MySQL。这是个很奇怪的问题,事务怎么会不回滚呢?实际上这是个愚蠢的问题,是经验不足导致的,越是奇怪的问题解决起来就越容易。不回滚的根本原因不在Hibernate,更不是SSH框架,而在MySQL本身。

查看MySQL数据库使用的存储引擎:mysql>show variables like '%storage_engine%';结果:+----------------+--------+ |Variable_name |Value| +----------------+--------+ |storage_engine|InnoDB| +----------------+--------+ 1
row in set

查看MySQL提供什么存储引擎:mysql>show engines;结果:+------------+---------+----------------------------------------------------------------+--------------+------+------------+
| Engine | Support | Comment | Transactions | XA | Savepoints | +------------+---------+----------------------------------------------------------------+--------------+------+------------+ | MyISAM | YES | Default engine as of MySQL 3.23 with great performance
| NO | NO | NO | | CSV | YES | CSV storage engine | NO | NO | NO | | MRG_MYISAM | YES | Collection of identical MyISAM tables | NO | NO | NO | | BLACKHOLE | YES | /dev/null storage engine (anything you write to it disappears) | NO | NO | NO | | FEDERATED |
NO | Federated MySQL storage engine | NULL | NULL | NULL | | InnoDB | DEFAULT | Supports transactions, row-level locking, and foreign keys | YES | YES | YES | | ARCHIVE | YES | Archive storage engine | NO | NO | NO | | MEMORY | YES | Hash based, stored in
memory, useful for temporary tables | NO | NO | NO | +------------+---------+----------------------------------------------------------------+--------------+------+------------+ 8 rows in set

从结果上看,当前数据库的默认存储引擎是InnoDB(注意观察Support这一列的值),不过有的数据库却不是,它们默认的是MyISAM。非但如此,在Support一栏中还显示NO,就是说连InnoDB都不支持。这就是为什么不回滚的原因:InnoDB支持事务,而MyISAM不支持!其实MyISAM是MySQL默认的存储引擎,在安装MySQL时如果没有指定存储引擎,那么MySQL会默认使用MyISAM,因为它不支持事务,也许效率会比InnoDB高一些。

如果使用的是MyISAM,那么需要将其改为InnoDB,具体方法如下:1、打开“MySQL_HOME/my.ini”,找到[mysqld],在它的下面有一句话是“skip-innodb”,将其注释掉,即改为:#skip-innodb。2、在[mysqld]下加上一句“default_table_type=INNODB”(如果写成default-storage-engine=INNODB也可以,两者之间的区别我还没有研究过)3、重启MySQL服务(注意:是重启服务,不是光退出数据库就完事了!)4、再次执行mysql>
show engines;可以看见默认存储引擎已经变成InnoDB了。5、原来已经存在的表,如果想使用事务,要修改它的存储引擎,在默认是InnoDB的情况下删除重建。当不想删除的时候,执行alter table 表名 ENGINE = InnoDB;之后执行show table status from 数据库名 where name='表名';可以查看表状态,看存储引擎是否被修改了。

在使用了InnoDB引擎之后,再次运行代码,回滚成功!
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: