美文网首页
java动态数据源事务测试(MySQL数据丢失)

java动态数据源事务测试(MySQL数据丢失)

作者: 木巽 | 来源:发表于2023-07-25 13:32 被阅读0次

    测试代码如下:

         @SneakyThrows
        public JsonResult createTable(String tableName,String dsId) {
            if (StringUtils.isEmpty(dsId)) {
                dsId = "1664472893795082241";
            }
            var ds = DruidUtils.getDataSource(dsId);
            var template = new JdbcTemplate(ds);
            //手动事务
            var txManager=new DataSourceTransactionManager(ds);
            DefaultTransactionDefinition transDef = new DefaultTransactionDefinition(); // 定义事务属性
            transDef.setPropagationBehavior(DefaultTransactionDefinition.PROPAGATION_REQUIRED); // 设置传播行为属性
            TransactionStatus status = txManager.getTransaction(transDef); // 获得事务状态
            try {
                TableModel t = new TableModel(tableName);
                t.comment("测试创建的表");
                t.column("id").VARCHAR(64).pkey().comment("主键");
                t.column("name").VARCHAR(50).comment("姓名");
                t.column("age").INTEGER().comment("年龄");
                t.column("create_time").TIMESTAMP().comment("创建时间");
                t.column("create_by").VARCHAR(64).comment("创建人");
                Dialect dialect = Dialect.guessDialect(ds);
                String[] ddlArray = dialect.toDropAndCreateDDL(t);
                for (String ddl : ddlArray) {
                    template.execute(ddl);
                }
                String now = DateUtils.getTime();
                String sql = "insert into " + tableName + " (id,name,age,create_time) values('101','李明',18,'" + now + "')";
                template.execute(sql);
                int j=1/0;
                sql = "insert into " + tableName + " (id,name,age,create_time) values('102','李明2',38,'" + now + "')";
                template.execute(sql);
                sql = "select * from " + tableName;
                JsonResult result = JsonResult.getSuccessResult("common.handleSuccess");
                var data = template.queryForList(sql);
                result.setData(data);
                txManager.commit(status);// 提交
                return result;
            } catch (Exception e) {
                txManager.rollback(status);// 回滚
                return JsonResult.Fail(e.getMessage());
            }
        }
    

    主要就是通过创建DataSourceTransactionManager实例来管理事务,因为不确定是哪个数据源实例,所以不方便用@Transactional注解。测试了MySQLPostgreSQL两种数据库,如果只是两条insert语句中间加一个异常,两种数据库都是可以正常回滚的。如果前面增加了删除表和创建表的SQL语句,PostgreSQL表现正常,MySQL的原来表中的数据却丢失了。看来MySQL的DDL语句在事务中有时无法正常回滚,之前用Seata的时候也遇到过,后来基本放弃Seata了。

    相关文章

      网友评论

          本文标题:java动态数据源事务测试(MySQL数据丢失)

          本文链接:https://www.haomeiwen.com/subject/odhhpdtx.html