首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Spring @事务性不会导致回滚

问Spring @事务性不会导致回滚
EN

Stack Overflow用户
提问于 2013-09-11 20:25:36
回答 1查看 457关注 0票数 0

在我开始这段似乎很长的段落之前,我想对我可能收到的任何建议表示感谢。-朱约翰

我开发了一个简单的测试来帮助我理解spring的声明性事务管理框架如何与spring的RESTful web服务一起工作。

为此,我开发了以下RESTful控制器:

代码语言:javascript
复制
    @RequestMapping(value="register", method=RequestMethod.POST, produces="application/json", consumes="application/json")
public void accountFacade () {
    tester.accountTest();
}

其中"tester“是以下服务类的bean,并自动进入此控制器。类中的唯一方法是事务性的:

代码语言:javascript
复制
@Transactional
public class TransactionTest extends ActivityStatus {
@Autowired
private ObjectManager objectManager;

@Autowired
private GenericDB gdb;

public static void main(String[] args) {
    ApplicationContext ac = new ClassPathXmlApplicationContext("META-INF/test- context.xml");   
    TransactionTest tester = (TransactionTest) ac.getBean("tester");
    tester.accountTest();
}

@Transactional(readOnly=false, propagation=Propagation.REQUIRED, isolation=Isolation.READ_COMMITTED,
               rollbackFor=RuntimeException.class)
public void accountTest () {
    try {
           String sql = "insert into account set account_id=0, ....";
           gdb.jdbcTemplateInsert(sql);
        
           sql = "insert into login set account_id=....";
           gdb.jdbcTemplateInsert(sql, values);
    } catch (DataAccessException dae) {
        System.out.println("Catching DataAccessException (dae)");
        throw new RuntimeException (dae);
    }
}

在上面,GenericDB是一个提供自定义jdbcTemplate的类。

测试运行是从浏览器调用accountFacade。我有意设置数据,以便第一个SQL成功,第二个SQL失败,从而触发回滚。

问题:最终的结果是,一个记录被插入考虑,并保持,甚至第二次插入失败的预期。

几个注意事项:

  1. 如果我向两个SQL提供正确的数据,那么测试运行就会成功。

  1. 如果我只是作为一个独立的java应用程序从Eclipse运行TransactionTest (请参阅main(.)在针对本地数据库的defn类中,似乎发生了回滚。

  1. 执行确实捕获了一个AccessDataException (请参阅我在" catch“块中的print语句)。因此,我的结论是抛出了“()”。

  1. 由于插入失败而产生的错误消息(调用堆栈)在许多其他行中显示了以下内容: 在org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:110) spring-tx-3.1.1.RELEASE.jar:3.1.1.RELEASE

这表明Spring的事务拦截器正确地“包装”了方法"accountTest“。这似乎意味着我的配置(见下文)是有效的。

ApplicationContext.xml中的相关行:

代码语言:javascript
复制
<tx:annotation-driven transaction-manager="txManager" />
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    <property name="dataSource" ref="dataSource"/>
</bean>
<bean id="tester" class="org.SandRiver.Controllers.TransactionTest">
</bean>

关于我的执行环境的几句话:我在OpenShift的环境中运行了这个应用程序,它包括

  1. JBoss6.1
  2. mysql 5.x (我不知道"x")。
  3. 我使用Maven来更新Spring版本。
EN

回答 1

Stack Overflow用户

发布于 2013-09-20 04:39:58

您需要使用InnoDB而不是MyISAM来支持事务。

要检查表的存储引擎:

代码语言:javascript
复制
mysql> show create table your_tbl_name;

若要使用InnoDB创建表:

代码语言:javascript
复制
CREATE TABLE your_tbl_name (
  col1 VARCHAR(10),
  col2 VARCHAR(10)
)
ENGINE = InnoDB;

希望这能有所帮助。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18750570

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档