随笔 - 145  文章 - 0  评论 - 6  阅读 - 18万

MyBatis与Spring整合

目标

本文主要目标是介绍MyBatis如何与Spring整合,MyBatis在Spring中使用的几种方式,为后面分析整合的源码奠定基础。

方式一. 使用SqlSessionTemplate

SqlSessionTemplate也是一个SqlSession实例,与sqlSessionFactory.openSession()方法返回的DefaultSqlSession实例,主要区别有两点

  • SqlSessionTemplate是线程安全的,可以供多个DAO类共享,而DefaultSqlSession线程不安全。
  • SqlSessionTemplate不支持事务API,调用rollbakc,commit方法会抛出异常,同时也不支持close方法,这些方法作用全都由Spring管理,会基于Spring 的事务配置来自动提交、回滚、关闭 session。

为了获取SqlSessionTemplate实例,我们需要一个SqlSessionFactory。我们可以借助mybatis-spring包提供的SqlSessionFactoryBean来获取一个SqlSessionFactory,MyBatis中的配置全都可以由这个类来配置。SqlSessionFactoryBean实现了FactoryBean,这是Spring中一种特殊的bean,当我们在XML配置中配置一个FactoryBean时,使用容器的getBean方法获取的对象实际是FactoryBean接口中getObject()返回的对象。

XML关键配置如下

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
    <!-- 注入连接池 -->
    <property name="dataSource" ref="dataSource"/>
    <!--主配置 -->
    <property name="configuration">
        <bean class="org.apache.ibatis.session.Configuration">
            <property name="mapUnderscoreToCamelCase" value="true"/>
        </bean>
    </property>
    <!-- 加载mybatis映射文件 -->
    <property name="mapperLocations" value="classpath:mappers/AddressMapper.xml"/>
</bean>

<!-- SqlSessionTemplate配置 -->
<bean id="sessionTemplate" class="org.mybatis.spring.SqlSessionTemplate">
    <constructor-arg index="0" name="sqlSessionFactory" ref="sqlSessionFactory" />
</bean>

测试代码

@RunWith(SpringRunner.class)
@ContextConfiguration(locations = "classpath:sqlsession/by-sqlsession.xml")
public class SqlSessionFactoryTest {

    /** 注入SqlSessionTemplate **/
    @Autowired
    private SqlSessionTemplate sqlSessionTemplate;

    @Test
    public void executeByTemplate() {
        // 注意不能显示调用commit、rollback、close方法
        AddressMapper addressMapper = sqlSessionTemplate.getMapper(AddressMapper.class);
        addressMapper.selectByPrimaryKey(1);
    }
}

可以看到此种方式需要手动获取SqlSession以及绑定的接口实例来执行数据库操作,比较麻烦。

方式二. 手动生成接口代理类

为了简化MyBatis的使用,mybatis-spring可以为我们创建一个接口的代理实现类交给Spring容器管理,这样我们便不再需要和SqlSession打交道,不再需要知道MyBatis的底层API。这时便需要MapperFactoryBean这个类出场了,看名字就知道它是一个创建Mapper接口的一个FactoryBean。

XML关键配置如下

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
    <!-- 注入连接池 -->
    <property name="dataSource" ref="dataSource"/>
    <!--主配置 -->
    <property name="configuration">
        <bean class="org.apache.ibatis.session.Configuration">
            <property name="mapUnderscoreToCamelCase" value="true"/>
        </bean>
    </property>
    <!-- 加载mybatis映射文件 -->
    <property name="mapperLocations" value="classpath:mappers/AddressMapper.xml"/>
</bean>

<!-- 为指定接口生成代理实现类 -->
<bean id="addressMapper" class="org.mybatis.spring.mapper.MapperFactoryBean">
    <property name="mapperInterface" value="com.wangtao.spring.manual.AddressMapper"/>
    <property name="sqlSessionFactory" ref="sqlSessionFactory"/>
</bean>

测试代码

@RunWith(SpringRunner.class)
@ContextConfiguration("classpath:manual/spring-manual.xml")
public class AddressMapperTest {

    /** 直接注入接口实例 **/
    @Autowired
    private AddressMapper addressMapper;

    @Test
    public void selectByPrimarykey() {
        addressMapper.selectByPrimaryKey(1);
    }
}

可以看到现在使用MyBatis操作数据库已经非常方便了,只需要一个接口以及映射文件就行了,但是如果Mapper接口非常多,配置生成接口代理就得一个一个去指定,显得很麻烦。

方式三. 自动扫描,生成接口代理类。

使用方式二,需要自己手动一个一个的去配置接口,但是我们可以指定一个包名,让MyBatis自动去扫描这个包下的接口,并生成代理实例放到Spring容器中。

XML关键配置如下

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
    <!-- 注入连接池 -->
    <property name="dataSource" ref="dataSource"/>
    <!--主配置 -->
    <property name="configuration">
        <bean class="org.apache.ibatis.session.Configuration">
            <!--下划线转驼峰-->
            <property name="mapUnderscoreToCamelCase" value="true"/>
        </bean>
    </property>
    <!-- 加载mybatis映射文件 -->
    <property name="mapperLocations" value="classpath:mappers/*.xml"/>
</bean>

<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
    <!-- 指定需要扫描的包名 -->
    <property name="basePackage" value="com.wangtao.spring.autoscan"/>
    <property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"/>
</bean>

测试代码

@RunWith(SpringRunner.class)
@ContextConfiguration("classpath:autoscan/spring-scan.xml")
public class UserMapperTest {

    @Autowired
    private AddressMapper addressMapper;

    @Test
    public void selectByPrimarykey() {
        addressMapper.selectByPrimaryKey(1);
    }
}

总结

本文介绍了MyBatis与Spring的整合时使用的几种方式,可以看到与Spring整合后可以非常方便地管理事务,事务全都交给Spring管理,而且通过接口绑定的方式时完全不用知道MyBatis的API,关注业务代码即可。

posted on   wastonl  阅读(449)  评论(0编辑  收藏  举报
编辑推荐:
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?
· 【译】Visual Studio 中新的强大生产力特性
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 【设计模式】告别冗长if-else语句:使用策略模式优化代码结构
< 2025年3月 >
23 24 25 26 27 28 1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30 31 1 2 3 4 5

点击右上角即可分享
微信分享提示