为特定的mybatis-spring映射器设置不同的ExecutorType

时间:2014-03-13 10:40:33

标签: java spring spring-batch mybatis

我在mybatis-spring中使用映射器时遇到问题。 (春批) 我需要在BATCH模式下使用带有ExecutorType的SqlSessionTemplate来解决性能问题(我的程序必须在表中执行数千个insert语句)。 但是在我的程序中,我需要记录错误并更新数据库的另一个表中的状态,如果在执行当前步骤时出现问题,则所有内容都是回滚,包括日志,这是不可接受的行为。 我以为我可以简单地设置两个不同的SqlSessionTemplate与不同的ExecutorType,但如果在我的步骤中我使用两个具有不同模板的映射器我得到一个异常,说我不能在事务期间更改ExecutorType,但我不知道如何解决这个问题。 任何帮助表示赞赏。这里有一些XML配置。

<!-- connect to database -->
<bean id="dataSource" class="org.springframework.jdbc.datasource.LazyConnectionDataSourceProxy">
    <property name="targetDataSource">
        <ref local="mainDataSource" />
    </property>
</bean> 


<bean id="mainDataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close" >
    <property name="driverClassName" value="${db.driver}" />
    <property name="url" value="${db.url}" />
    <property name="username" value="${db.user}" />
    <property name="password" value="${db.pass}" />
</bean>

<bean id="infrastructureSqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
    <property name="dataSource" ref="dataSource" />
    <property name="mapperLocations"
        value="classpath*:com/generali/danni/sipo/mdv/dao/mybatis/*Mapper*.xml" />
    <property name="configLocation" value="classpath:mybatis-config.xml" />
</bean>

<bean id="infrastructureSqlSessionTemplateBatch" class="org.mybatis.spring.SqlSessionTemplate">
    <constructor-arg index="0" ref="infrastructureSqlSessionFactory" />
    <constructor-arg index="1" value="BATCH" />
</bean>

<bean id="infrastructureSqlSessionTemplate" class="org.mybatis.spring.SqlSessionTemplate">
    <constructor-arg index="0" ref="infrastructureSqlSessionFactory" />
</bean>

    <bean id="infrastructureAbstractMapper" class="org.mybatis.spring.mapper.MapperFactoryBean"
    abstract="true">
    <property name="sqlSessionTemplate" ref="infrastructureSqlSessionTemplate" /> 
</bean> 

<bean id="infrastructureAbstractMapperBatch" class="org.mybatis.spring.mapper.MapperFactoryBean"
    abstract="true">
    <property name="sqlSessionTemplate" ref="infrastructureSqlSessionTemplateBatch" />
</bean> 

<bean id="erroriMapper" parent="infrastructureAbstractMapper">
    <property name="mapperInterface"
        value="com.mdv.dao.ErroriMapper" />
</bean>

<bean id="stagingFileMapper" parent="infrastructureAbstractMapperBatch">
    <property name="mapperInterface"
        value="com.mdv.dao.StagingFileMapper" />
</bean>

这里我有两个映射器,一个我想在BATCH模式下使用,另一个在SIMPLE模式下。 我怎样才能完成这项任务?每个建议都表示赞赏。 提前谢谢,抱歉我的英语不好。

1 个答案:

答案 0 :(得分:3)

经过多次尝试,我决定改变我的方法来解决这个问题。 我以编程方式定义了一个新的SqlSessionFactory,使用Batch Executor生成一个新的SqlSession并使用了那个。 因为它是一个完全不同的SqlSessionFactory,如果我使用2个不同的ExecutorType,它似乎不会给出问题。 这是一个示例工作代码:

Environment environment = new Environment("TEST", new JdbcTransactionFactory(), dataSource);
        Configuration configuration = new Configuration(environment);
        configuration.addMappers("com.mdv.dao");

        SqlSessionFactory ssf = new SqlSessionFactoryBuilder().build(configuration);
        SqlSession sqlSession = ssf.openSession(ExecutorType.BATCH);
        try {

            StagingFileMapper sfm = sqlSession.getMapper(StagingFileMapper.class);
            for(Record r : staging){
                StagingFile sf = new StagingFile();
                //set your sf fields
                sfm.insert(sf);
            }
            sqlSession.commit();
        } catch (Exception e) {
            //manage exception
        }
        finally{
            sqlSession.close();
        }