1、整合思路
1)spring通过单例模式管理SqlSessionFactory
2)通过SqlSessionFactory创建SqlSession(整合自动完成)
3)持久层的mapper都需要由spring进行管理
2、jar包
spring的包
mybatis的包
spring-mybatis整合的包(mybatis-spring-1.2.2.jar)
还用了c3p0连接池
3、sqlSessionFactory
在applicationContext.xml中配置sqlSessionFactory,它在mybatis-sring的整合包下。
<?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"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx.xsd">
<!--加载数据库的配置文件-->
<context:property-placeholder location="classpath:mybatis/db.properties"/>
<!-- 配置c3p0连接池 -->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<!-- 注入属性值 -->
<property name="driverClass" value="${jdbc.driver}"></property>
<property name="jdbcUrl" value="${jdbc.url}"></property>
<property name="user" value="${jdbc.username}"></property>
<property name="password" value="${jdbc.password}"></property>
</bean>
<!--sqlSessionFactory-->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<!--加载mybatis的配置文件-->
<property name="configLocation" value="mybatis/SqlMapConfig.xml"/>
<!--数据源-->
<property name="dataSource" ref="dataSource"/>
</bean>
</beans>
3、持久层的mapper都需要由spring进行管理
3.1 原始Dao开发
原始Dao是写Dao接口和DaoImpl,要实现注入SqlSessionFactory
3.1.1 配置文件
mapper.xml文件不会变化,SqlMapConfig.xml就要做一些删减,把环境和数据源交给spring。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<settings>
<setting name="lazyLoadingEnabled" value="true"/>
<setting name="aggressiveLazyLoading" value="false"/>
</settings>
<!--加载映射文件-->
<mappers>
<mapper resource="sqlmap\User.xml"/>
<package name="cn.itcast.mybatis.sqlMapper"/>
<!--<mapper class="cn.itcast.mybatis.sqlMapper.UserMapper"/>-->
<!--<mapper class="cn.itcast.mybatis.sqlMapper.OrdersMapperCustomMapper"/>-->
</mappers>
</configuration>
核心知识是:spring如何管理接口的实现类
3.1.2 接口实现类
让Impl继承SqlSessionDaoSupport,通过父类内置的方法来得到Factory。
3.1.3 spring配置文件
把DaoImpl的创建交给spring
3.1 测试一下
@Test
public void testSpringAndMybatis() throws Exception {
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("classpath:spring/applicationContext.xml");
UserDao userDao = (UserDao) applicationContext.getBean("userDao");
User user =userDao.findUserById(1);
System.out.println(user);
}
3.2 mapper代理
在3.1的基础上,我们再解决一个问题就行了,如何在spring注册代理mapper的bean呢?答案是又一个轮子
<!--mapper代理方式实现接口-->
<bean id="userMapperBean" class="org.mybatis.spring.mapper.MapperFactoryBean">
<!--mapperInterface:指定哪个接口-->
<property name="mapperInterface" value="cn.itcast.mybatis.sqlMapper.UserMapper"/>
<!--这个类也继承了Supper,指定Factory-->
<property name="sqlSessionFactory" ref="sqlSessionFactory"/>
</bean>
测试一下
@Test
public void testSpringAndMybatis() throws Exception {
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("classpath:spring/applicationContext.xml");
UserMapper userMapper = (UserMapper) applicationContext.getBean("userMapperBean");
User user =userMapper.findUserById(1);
System.out.println(user);
}
无论是哪种方法,在spring中的配置注册mapper代码量都很大,这个问题通过注解方式来解决
4、通过注释的方式管理bean的注册
在spring的applicationconfig配置文件中,开启扫描包
<!--mapper的批量扫描,从mapper包中扫描出接口,自动创建代理对象,也就是实现上面的那种方法,-->
<!--并且在spring容器中注册
-->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<!--指定扫描的包名-->
<!--规范仍然要保持:java文件和xml文件名称一致,且在一个目录下;方法和selectId一致-->
<property name="basePackage" value="cn.itcast.mybatis.sqlMapper"/>
<!--指定sqlSessionFactory,注意:它是String类型的,因此给他value = "一个字符串",
而不是ref=""引用一中封装类型-->
<property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"/>
</bean>
回顾之前的内容,我们在mybatis的核心配置文件中也有开启扫描,目的是标明哪些接口开启了mapper代理,那么现在可以交给spring去做了。可以注释掉。
我们把之前写的bean注释掉,那么当前定义的bean其实是没有id的,我们在getBean()的时候,参数就是接口的类名,首字母小写。
测试代码
@Test
public void testSpringAndMybatis() throws Exception {
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("classpath:spring/applicationContext.xml");
UserMapper userMapper = (UserMapper) applicationContext.getBean("userMapper");
User user =userMapper.findUserById(1);
System.out.println(user);
}