本文介绍Spring集成Mybatis配置文件各个部分的具体含义:
1、数据源
<bean id="dataSource"
class="org.apache.commons.dbcp2.BasicDataSource"
destroy-method="close">
<property name="url" value="jdbc:mysql://localhost:3306/test"/>
<property name="username" value="root"/>
<property name="password" value="root"/>
<property name="driverClassName" value="com.mysql.jdbc.Driver"/>
</bean>
数据源是必不可少的,数据源负责提供与数据库的连接,DataSource接口有很多种实现:
- 上面配置文件中配置的是dbcp数据连接池的数据源实现;
- 像Spring也对DataSource也有多种实现,比如SimpleDriverDataSource,这个数据源是一个普通的不带连接池的数据源。
2、SqlSessionFactory配置
<bean id="sqlSessionFactory"
class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="mapperLocations" value="classpath:mybatis/mapper/*.xml"/>
</bean>
对于SqlSessionFactory的配置稍微复杂一些,我们一步一步看源码:
public class SqlSessionFactoryBean implements FactoryBean<SqlSessionFactory>, InitializingBean, ApplicationListener<ApplicationEvent>{...}
上面是bean的class类SqlSessionFactoryBean的类声明:
实现FactoryBean<SqlSessionFactory>接口:
接口说明:
一般情况下,Spring通过反射机制利用<bean>的class属性指定实现类实例化Bean,在某些情况下,实例化Bean过程比较复杂,如果按照传统的方式,则需要在<bean>中提供大量的配置信息。配置方式的灵活性是受限的,这时采用编码的方式可能会得到一个简单的方案。Spring为此提供了一个org.springframework.bean.factory.FactoryBean的工厂类接口,用户可以通过实现该接口定制实例化Bean的逻辑。
FactoryBean是一个工厂Bean,是一个接口,实现该接口(支持泛型),可以生成某一个类型Bean实例,它最大的一个作用是:可以让我们自定义Bean的创建过程。不同于普通Bean的是:它是实现了FactoryBean<T>接口的Bean,根据该Bean的ID从BeanFactory中获取的实际上是FactoryBean的getObject()返回的对象,而不是FactoryBean本身。
明确了此接口的意义后,我们来看对于该接口方法的实现:
@Override
public SqlSessionFactory getObject() throws Exception {
if (this.sqlSessionFactory == null) {
afterPropertiesSet();
}
return this.sqlSessionFactory;
}
- 此时看到SqlSessionFactoryBean这个bean最终生成或者产生的是一个SqlSessionFactory实例,进一步追源码可以看到SqlSessionFactory的生产是在:
@Override
public void afterPropertiesSet() throws Exception {
notNull(dataSource, "Property 'dataSource' is required");
notNull(sqlSessionFactoryBuilder, "Property 'sqlSessionFactoryBuilder' is required");
state((configuration == null && configLocation == null) || !(configuration != null && configLocation != null),
"Property 'configuration' and 'configLocation' can not specified with together");
this.sqlSessionFactory = buildSqlSessionFactory();
}
....
protected SqlSessionFactory buildSqlSessionFactory() throws IOException {
.....
return this.sqlSessionFactoryBuilder.build(configuration);
}
到这一步也就明确了SqlSessionFactory这个Bean在spring中是如何被创建出来的。
接下来看一下SqlSessionFactory这个bean的意义:
- SqlSessionFactory是MyBatis的关键对象,它是个单个数据库映射关系经过编译后的内存镜像;
- SqlSessionFactory是单例的;
- 从命名上也可以看出SqlSessionFactory可以获取操作数据的SqlSession实例(是SqlSession的工厂);
- 与最原始的jdbc粗略类比的话,SqlSessionFactory相当于Connection,SqlSession就相当于Statement。
接下来看一下需要配置的属性:
- dataSource:SqlSessionFactoryBean Bean必须传入的属性,这个属性会在创建具体的SqlSessionFactory时传入构造函数中。
- mapperLocations:用来配置sql mapper的xml文件的路径,支持扫描式加载SQL映射文件。
- 当然配置项是非常多的,此处仅列举必备的和常用的,后续继续补充。
3、MapperScannerConfigurer配置
前述已经配置好了SqlSessionFactory和sql mapper的映射文件,接下来就需要配置dao层的接口,将dao层的接口纳入spring的管理,需要如下配置:
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="com.test.database.mybatis"/>
<property name="sqlSessionFactory" ref="sqlSessionFactory"/>
</bean>
MapperScannerConfigurer是一个转换器,可以将映射的dao接口直接转换为Spring容器中的Bean,这样就可以在Service中注入映射接口的Bean了,就不用去实现这些dao层接口了,直接注入使用就可以了,这也是为什么dao层的接口都不需要添加注解,因为在配置MapperScannerConfigurer这个bean时已经指明了需要处理的接口。
接下来看一下需要配置的属性:
- basePackage:配置基础包名,MapperScannerConfigurer将扫描basePackage所指定的包下的所有接口类(包括子包),如果他们在SQL映射文件中定义过,则将他们动态定义为一个Spring Bean。
- sqlSessionFactory:配置sqlSessionFactory的bean,这个很好理解了,既然要去对应SQL映射文件,而SQL映射文件的定义又是在上述所说的sqlSessionFactory中,所以得有这一个配置。
4、总结
上述总结了spring集成mybatis时配置文件的最小配置,并粗略对配置的各个bean进行了说明。