Spring整合Mybatis

highlight_shrink:
aside:
abcjs:

1. 回忆Mybatis

目录结构
目录结构

  1. 编写工具类
    package top.qwwq.utils;
    
    import org.apache.ibatis.io.Resources;
    import org.apache.ibatis.session.SqlSession;
    import org.apache.ibatis.session.SqlSessionFactory;
    import org.apache.ibatis.session.SqlSessionFactoryBuilder;
    
    import java.io.IOException;
    import java.io.InputStream;
    
    // SqlSessionFactory --> sqlSession
    public class MybatisUtils {
        private static final SqlSessionFactory sqlSessionFactory;
    
        static {
            try {
                // 使用Mybatis第一步:获取sqlSessionFactory对象
                String resource = "mybatis-config.xml";
                InputStream inputStream = Resources.getResourceAsStream(resource);
                sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
    
        }
    
        // 既然有了 SqlSessionFactory,顾名思义,我们可以从中获得 SqlSession 的实例。
        // SqlSession 提供了在数据库执行 SQL 命令所需的所有方法。你可以通过 SqlSession 实例来直接执行已映射的 SQL 语句
        public static SqlSession getSqlSession(){
            return sqlSessionFactory.openSession();
        }
    
    }
    
    
  2. 编写实体类
    import lombok.Data;
    
    @Data
    public class User {
    private int id;
    private String name;
    private String pwd;
    }
    
  3. 编写核心配置文件
    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE configuration
            PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
            "https://mybatis.org/dtd/mybatis-3-config.dtd">
    <!--核心配置文件-->
    <configuration>
    
        <typeAliases>
            <package name="top.qwwq.pojo"/>
        </typeAliases>
    
        <environments default="development">
            <environment id="development">
                <transactionManager type="JDBC"/>
                <dataSource type="POOLED">
                    <property name="driver" value="com.mysql.cj.jdbc.Driver"/>
                    <property name="url" value="jdbc:mysql://localhost:3306/mybatis?characterEncoding=UTF-8&amp;useUnicode=true&amp;serverTimezone=GMT"/>
                    <property name="username" value="root"/>
                    <property name="password" value="20021001"/>
                </dataSource>
            </environment>
        </environments>
        <!--    每一个mapper.xml都需要在MyBatis核心配置文件中注册-->
        <mappers>
            <mapper resource="mapper/UserMapper.xml"/>
        </mappers>
    </configuration>
    
  4. 编写接口
    package top.qwwq.mapper;
    
    import top.qwwq.pojo.User;
    
    import java.util.List;
    
    public interface UserMapper {
        // 获取全部用户
        List<User> selectUser();
    
    
    }
    
  5. 编写Mapper.xml
    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE mapper
            PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
            "https://mybatis.org/dtd/mybatis-3-mapper.dtd">
    <!--namespace绑定一个对应的Mapper/Dao接口-->
    <mapper namespace="top.qwwq.mapper.UserMapper">
    
        <select id="selectUser" resultType="top.qwwq.pojo.User" >
            select * from mybatis.user
        </select>
    
    </mapper>
    
  6. 测试
    public class Mytest {
        @Test
        public void test(){
            // 第一步: 获取SqlSession对象
            try(SqlSession sqlSession = MybatisUtils.getSqlSession()){
                // 第二步: getMapper(方式一)
                UserMapper mapper = sqlSession.getMapper(UserMapper.class);
                for (User user : mapper.selectUser()) {
                    System.out.println(user);
                }
    
            }
        }
    }
    

2. 整合Mybatis-Spring

官方快速上手 (👈点击这里)

方式一

代码实现

目录结构 👇
目录结构1. 编写spring-dao.xml 由Spring来管理数据源

  1. spring-dao.xml 编写DataSource,让Spring掌管数据源

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xmlns:context="http://www.springframework.org/schema/context"
           xsi:schemaLocation="http://www.springframework.org/schema/beans
            https://www.springframework.org/schema/beans/spring-beans.xsd
            http://www.springframework.org/schema/context
            https://www.springframework.org/schema/context/spring-context.xsd">
    
        <context:annotation-config/>
    
    <!--    DataSource:使用Spring的数据源替换Mybatis的配置 c3p0 dbcp druid
            我们治理使用Spring提供的JDBC : org.springframework.jdbc.datasource
    -->
        <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
            <property name="driverClassName" value="com.mysql.cj.jdbc.Driver"/>
            <property name="url" value="jdbc:mysql://localhost:3306/mybatis?characterEncoding=UTF-8&amp;useUnicode=true&amp;serverTimezone=GMT"/>
            <property name="username" value="root"/>
            <property name="password" value="20021001"/>
        </bean>
    
    <!--    sqlSessionFactory-->
    
    </beans>
    
  2. spring-dao.xml 编写 sqlSessionFactory

    <!--    sqlSessionFactory-->
        <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
            <property name="dataSource" ref="dataSource"/>
    <!--        绑定Mybatis配置文件 (可要可不要)-->
            <property name="configLocation" value="classpath:mybatis-config.xml"/>
            <property name="mapperLocations" value="classpath:mapper/*.xml"/>
        </bean>
    
        <bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
    <!--        只能通过构造器注入sqlSessionFactory,因为它没有set方法-->
            <constructor-arg index="0" ref="sqlSessionFactory"/>
        </bean>
    
  3. spring-dao.xml 编写SqlSessionTemplate

     <bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
         <!-- 只能通过构造器注入sqlSessionFactory,因为它没有set方法-->
         <constructor-arg index="0" ref="sqlSessionFactory"/>
     </bean>
    
  4. UserMapperImpl.java 需要给接口加实现类

    public class UserMapperImpl implements UserMapper{
        // 在原来,我们所有的操作,都是用sqlSession,现在都使用SqlSessionTemplate
        private SqlSessionTemplate sqlSession;
    
        public void setSqlSession(SqlSessionTemplate sqlSession) {
            this.sqlSession = sqlSession;
        }
    
        @Override
        public List<User> selectUser() {
            UserMapper mapper = sqlSession.getMapper(UserMapper.class);
            return mapper.selectUser();
        }
    }
    
  5. spring-dao.xmlUserMapperImpl.java添加到Spring的bean (可以写xml,或者用注解)

     <bean id="userMapper" class="top.qwwq.mapper.UserMapperImpl">
         <property name="sqlSession" ref="sqlSession"/>
     </bean>
    
  6. Mytest.java 将自己写的实现类,注入到Spring中,测试使用

    public class Mytest {
        @Test
        public void test(){
            ApplicationContext context = new ClassPathXmlApplicationContext("spring-dao.xml");
            UserMapper userMapper = context.getBean("userMapper", UserMapper.class);
            for (User user : userMapper.selectUser()) {
                System.out.println(user);
            }
    
        }
    }
    

小结:

需要用到的文件只有 :

  • UserMapper.java (接口) 用来定义方法
    public interface UserMapper {
     // 获取全部用户
     List<User> selectUser();
    }
    
  • UserMapperImpl.java (类) 用来实现接口中的方法 👆上面有这个文件的具体代码
  • User.java (类) pojo实体类 👆上面有这个文件的具体代码
  • UserMapper.xml 绑定 UserMapper.java 接口,用来写SQL语句,也可以直接使用注解来实现
  • mybatis-config.xml Spring整合Mybatis后mybatis-config.xml这个文件可以不需要了,但是通常还是保留,用来给类起别名、存放一些设置信息(比如日志什么的)

方式二

新建一个UserMapper的实现类,然后去继承SqlSessionDaoSupport这个类,这个类会帮你做一些步骤一的工作

public class UserMapperImpl2 extends SqlSessionDaoSupport implements UserMapper{
    @Override
    public List<User> selectUser() {
        SqlSession sqlSession = getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);
        return mapper.selectUser();
    }
}

把UserMapperImpl2类注册到Spring

<bean id="userMapper2" class="top.qwwq.mapper.UserMapperImpl2">
   <property name="sqlSessionFactory" ref="sqlSessionFactory"/>
</bean>

AI小提醒:

方式二 和 方式一 的不同

SqlSessionDaoSupport和直接使用SqlSessionFactory的主要区别在于SqlSessionDaoSupport提供了一些额外的便利性,尤其是在处理SqlSession生命周期方面。

  1. 生命周期管理:当你使用SqlSessionDaoSupport时,你不需要手动打开和关闭SqlSession。这是因为SqlSessionDaoSupport在每次请求时都会自动打开一个新的SqlSession,并在请求结束时自动关闭这个SqlSession。这意味着你不需要在你的代码中管理SqlSession的生命周期,这可以使你的代码更简洁,也可以减少因为忘记关闭SqlSession而导致的资源泄露的可能性。

  2. 依赖注入SqlSessionDaoSupport提供了一个设置SqlSessionFactory的方法,这意味着你可以使用Spring的依赖注入功能来注入SqlSessionFactory。这使得你的DAO类和Spring框架的集成更紧密,也使得你的DAO类更容易测试,因为你可以在测试时注入一个模拟的SqlSessionFactory

  3. 模板编程SqlSessionDaoSupport是Spring的模板编程风格的一部分。这种风格的主要思想是将一些常见的、重复的代码(如打开和关闭SqlSession)封装在模板类中,然后让用户的类继承这个模板类。这种方式可以减少代码重复,使代码更易于维护。

相比之下,直接使用SqlSessionFactory则需要手动管理SqlSession的生命周期,也需要手动注入SqlSessionFactory。然而,这也意味着你有更大的灵活性,因为你可以控制何时打开和关闭SqlSession,也可以选择不使用Spring的依赖注入。

总的来说,选择使用SqlSessionDaoSupport还是直接使用SqlSessionFactory主要取决于你的具体需求。如果你希望代码更简洁,或者你正在使用Spring框架,那么SqlSessionDaoSupport可能是一个好选择。如果你需要更大的灵活性,或者你不想让你的DAO类与Spring框架紧密集成,那么直接使用SqlSessionFactory可能是一个好选择。


在代码层面上,使用SqlSessionDaoSupport和直接使用SqlSessionFactory的主要区别在于如何管理SqlSession的生命周期,以及如何进行依赖注入。

  1. 生命周期管理:当你使用SqlSessionDaoSupport时,你不需要手动打开和关闭SqlSession。例如:

    public class MyDao extends SqlSessionDaoSupport {
        public MyObject getMyObject(int id) {
            return getSqlSession().selectOne("MyMapper.getMyObject", id);
        }
    }
    

    在上面的代码中,getSqlSession()方法由SqlSessionDaoSupport提供,并且它会自动管理SqlSession的生命周期。

    相比之下,当你直接使用SqlSessionFactory时,你需要手动打开和关闭SqlSession。例如:

    public class MyDao {
        private SqlSessionFactory sqlSessionFactory;
    
        public void setSqlSessionFactory(SqlSessionFactory sqlSessionFactory) {
            this.sqlSessionFactory = sqlSessionFactory;
        }
    
        public MyObject getMyObject(int id) {
            try (SqlSession sqlSession = sqlSessionFactory.openSession()) {
                return sqlSession.selectOne("MyMapper.getMyObject", id);
            }
        }
    }
    

    在上面的代码中,SqlSession是通过sqlSessionFactory.openSession()手动打开的,并且在try-with-resources语句中自动关闭。

  2. 依赖注入:当你使用SqlSessionDaoSupport时,你可以使用Spring的依赖注入功能来注入SqlSessionFactory。例如:

    <bean id="myDao" class="org.mybatis.spring.support.SqlSessionDaoSupport">
        <property name="sqlSessionFactory" ref="sqlSessionFactory" />
    </bean>
    

    在上面的配置中,SqlSessionFactory是通过Spring的<property>配置注入的。

    相比之下,当你直接使用SqlSessionFactory时,你也可以使用Spring的依赖注入功能来注入SqlSessionFactory,但是你需要在你的DAO类中提供一个设置SqlSessionFactory的方法。例如:

    <bean id="myDao" class="com.example.MyDao">
        <property name="sqlSessionFactory" ref="sqlSessionFactory" />
    </bean>
    

    在上面的配置中,SqlSessionFactory是通过Spring的<property>配置注入的,但是这需要你的DAO类提供一个setSqlSessionFactory(SqlSessionFactory sqlSessionFactory)方法。


Spring整合Mybatis
http://localhost:8090//archives/TA5Y1JLh
作者
EnderKC
发布于
2024年12月23日
许可协议