宝剑锋从磨砺出,梅花香自苦寒来。这篇文章主要讲述SpringBoot | 3.2 整合MyBatis #yyds干货盘点#相关的知识,希望能为你提供帮助。
@TOC
前言通过前一篇的学习,我们知道可以使用JDBC操作数据库,但在实际生产中,我们一般使用MyBatis。在本篇,可以学习到SpringBoot如何整合MyBatis框架,以及相关自动配置原理。
MyBatis是目前java持久层最为主流的技术之一,它可以避免几乎所有的JDBC代码和手动设置参数以及获取结果集。同时,MyBatis是基于一种SQL到POJO的模型,需要我们提供SQL、映射关系以及POJO。由于本笔记为SpringBoot系列笔记,故重点放在SpringBoot整合使用MyBatis。
注:在说明注解时,第一点加粗为注解中文含义,第二点为一般加在哪身上,缩进或代码块为示例,如:
@注解
- 中文含义
- 加在哪
- 其他……
语句示例
//代码示例
1.1 初始化导向初始化导向指在新建SpringBoot项目工程时进行导入:
文章图片
1.2 手动导入手动导入只需要在SpringBoot的pom.xml文件里添加下面场景即可:
<
dependency>
<
groupId>
org.mybatis.spring.boot<
/groupId>
<
artifactId>
mybatis-spring-boot-starter<
/artifactId>
<
version>
2.1.4<
/version>
<
/dependency>
2. *MyBatis自动配置原理加入MyBatis场景后,我们可以发现该场景里有:
文章图片
【SpringBoot | 3.2 整合MyBatis #yyds干货盘点#】通过前面的文章,我们知道SpringBoot会先找到对应场景的自动配置类,在这里是
MybatisAutoConfiguration
@Configuration
@ConditionalOnClass( SqlSessionFactory.class, SqlSessionFactoryBean.class )
@ConditionalOnBean(DataSource.class)
@EnableConfigurationProperties(MybatisProperties.class) // MyBatis配置项绑定类
@AutoConfigureAfter( DataSourceAutoConfiguration.class, MybatisLanguageDriverAutoConfiguration.class )
public class MybatisAutoConfiguration
从源码中,我们可以得到以下信息:
- 跟
MybatisProperties
配置类绑定,
- 配置属性的前缀为
mybatis
@ConfigurationProperties(prefix = "mybatis") public class MybatisProperties
- 配置属性的前缀为
- 全局配置文件:使用Mybatis需要进行全局配置;
- SqlSessionFactory: 用来生成
SqlSession
;- SqlSession是MyBatis操作的核心,是一个功能性代码,通常使用单例模式(在MyBatis的生命周期中只存在一个
SqlSessionFactory
);
- SqlSession是MyBatis操作的核心,是一个功能性代码,通常使用单例模式(在MyBatis的生命周期中只存在一个
- SqlSession:自动配置了
SqlSessionTemplate
,可以生成SqlSession
; - @Import(AutoConfiguredMapperScannerRegistrar.class):导入的类里有定义如何操作
@Mapper
注解的接口;- @Mapper: 只要写的操作MyBatis的接口标注了
@Mapper
就会被自动扫描进容器。
- @Mapper: 只要写的操作MyBatis的接口标注了
文章图片
3. 全局配置文件准备工作:
- 配置全局配置文件位置( 在
application.yaml
中指定Mapper配置文件的位置,以及指定全局配置文件的信息,建议配置在mybatis.configuration
);
mybatis: #全局配置文件位置 config-location: classpath:mybatis/mybatis-config.xml #sql映射文件位置 mapper-locations: classpath:mybatis/mapper/*.xml #定义别名扫描的包,需要与@Alias联合使用 type-aliases-package: …… #具体类需要与@MappedJdbcTypes联合使用 type-handlers-package: …… #执行器(Executor),可以配置STMPLE、REUSE、BATCH、默认为STMPLE executor-type: ……configuration: #配置MyBatis插件(拦截器等) interceptors: …… #级联延迟加载配置属性 aggressive-lazy-loading: ……
- 注意
config-location
与mapper-locations
不能同在,理由如下: - 当需要使用mybatis-config.xml配置文件的时需要配置
config-location
,config-location
的作用是确定mybatis-config.xml文件位置;而mapper-locations
是用来注册xxxmapper.xml文件。如果使用了mybatis-config.xml,并且里面配置了mapper,那就不需要mapper-locations
。
- 注意
- 编写mapper接口,使用标准
@Mapper
注解( 也可以在启动类上加上@MapperScan
替换@Mapper )
- 映射配置;
- 用在接口类上
- 在接口类上添加了@Mapper,在编译之后会生成相应的接口实现类;
- 如果有多组接口需要编译成实现类,需要在每个接口上标注一个@Mapper;
@Mapper public interface UserDAO //代码
- 映射扫描配置;
- 用在主启动类下;
- 指定要变成实现类的接口所在的包,然后包下面的所有接口在编译之后都会生成相应的实现类;
- 将MyBatis所需的对应接口扫描到Spring IOC容器中;
- 可以解决@Mapper标注过多问题,直接在主启动类上加上一个@MapperScan即可;
@SpringBootApplication //@MapperScan("com.dlhjw.mapper") @MapperScan( //指定扫描包 basePackages = "com.dlhjw.mapper", //指定SqlSessionFactory,如果sqlSessionTemplate被指定,则作废 sqlSessionFactoryRef = "sqlSessionFactory", //指定sqlSessionTemplate,将忽略sqlSessionFactory的配置(优先级高) sqlSessionTemplateRef = “sqlSessionTemplate”, //限制扫描接口,不常用 //markerInterface = class.class, annotationClass = Repository.class ) public class SpringbootMybatisDemoApplication public static void main(String[] args) SpringApplication.run(SpringbootMybatisDemoApplication.class, args);
- 通过
MapperFactoryBean
装配MyBatis; - 使用
MapperScannerConfigurer
; - 使用MyBatis接口(因为
SqlSessionFactory
是SpringBoot自动生成好了,所以直接拿来使用);
1. 通过MapperFactoryBean装配MyBatis:
@Autowired
SqlSessionFactory sqlSessionFactory = null;
//定义一个MyBatis的Mapper接口
@Bean
public MapperFactoryBean<
MyBatisUserDao>
initMyBatisUserDao()
MapperFactoryBean<
MyBatisUserDao>
bean = new MapperFactoryBean<
>
();
bean.setMapperInterface(UserDAO.class);
bean.setSessionFactory(sqlSessionFactory);
return beam;
2. 使用MapperScannerConfigurer:
@Bean
public MapperScannerConfigurer mapperScannerConfig()
//定义扫描器实例
MapperScannerConfigurer mapperScannerConfigurer = new MapperScannerConfigurer();
//加载SqlSessionFactory,SpringBoot会自动生产,SqlSessionFactory实例
mapperScannerConfigurer.setSqlSessionFactoryBeanName("sqlSessionFactory");
//定义扫描的包
mapperScannerConfigurer.setBeanPackage("com.dlhjw.mapper");
//限定被标注@Repository的接口才被扫描
mapperScannerConfigurer.setAnnotationClass(Repository.class);
//通过继承某个接口限制扫描,一般使用不多
//mapperScannerConfigurer.setMarkerInterface(....);
return mapperScannerConfigurer;
3. 使用MyBatis接口:
public interface MyBatisUserService
public User getUser(Long id);
@Service
public class MyBatisUserServiceImpl implements MyBatisUserService
//因为在启动文件application.yaml配置了对应接口,所以直接依赖注入即可
@Autowired
private MyBatisUserDao myBatisUserDao = null;
@Override
public User getUser(Long id)
return myBatisUserDao.getUser(id);
3.1 配置模式1. 导入mybatis官方starter;
2. 编写mapper接口,使用
@Mapper
或@MapperScan
注解;3. 配置全局配置文件(springboot自动配置好了);
<
?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="mapUnderscoreToCamelCase" value="https://www.songbingjia.com/android/true"/>
<
/settings>
<
/configuration>
配置mybatis.configuration下面的所有,就是相当于改mybatis全局配置文件中的值;
mybatis:
#注意:只能有一个全局配置,下面语句不能存在
#config-location: classpath:mybatis/mybatis-config.xml
mapper-locations: classpath:mybatis/mapper/*.xml
configuration:
map-underscore-to-camel-case: true#推荐
4. 配置映射文件(编写sql映射文件并绑定mapper接口);
<
?xml version="1.0" encoding="UTF-8" ?>
<
!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<
mapper namespace="com.dlhjw.admin.mapper.AccountMapper">
<
!-- public Account getAcct(Long id) -->
<
select id="getAcct" resultType="com.dlhjw.admin.bean.Account">
select * from account_tbl where id=#id
<
/select>
<
/mapper>
3.2 注解模式@Select
- 选择;
- 标注在mapper接口上;
- 用来代替原来xml里的\\< select> 标签,参数为原生的sql;
2. 编写mapper接口,使用
@Mapper
或@MapperScan
注解;3. 接口的方法上标注
@Select
注解,代替原来xml里的&
lt;
select&
gt;
标签;@Mapper
public interface CityMapper
@Select("select * from city where id=#id")
public City getById(Long id);
4. 在service层里编写业务方法;
public interface CityService
City getById(Long id);
@Service
public class CityServiceImpl implements CityService @Autowired
CityMapper cityMapper;
public City getById(Long id)
return cityMapper.getById(id);
5. 在Controller层里编写表示层相关方法;
*Controller相关知识参考下章。
@Controller
public class IndexController @Autowired
CityService cityService;
@ResponseBody
@GetMapping("/city")
public City getCityById(@RequestParam("id") Long id)
return cityService.getById(id);
3.3 混合模式1. 导入mybatis官方starter;
2. 编写mapper接口,使用
@Mapper
或@MapperScan
注解;@Mapper
public interface CityMapper @Select("select * from city where id=#id")
public City getById(Long id);
public void insert(City city);
3. 为insert方法配置xml文件;
<
mapper namespace="com.atguigu.admin.mapper.CityMapper">
<
!--useGeneratedKeys:使用自增主键,可以返回自增主键值keyProperty:自增属性的id -->
<
insert id="insert" useGeneratedKeys="true" keyProperty="id">
insert intocity(`name`,`state`,`country`) values(#name,#state,#country)
<
/insert>
<
/mapper>
4. 在service层里编写业务方法;
public interface CityService
City getById(Long id);
void saveCity(City city);
@Service
public class CityServiceImpl implements CityService @Autowired
CityMapper cityMapper;
public City getById(Long id)
return cityMapper.getById(id);
public void saveCity(City city)
counter.increment();
cityMapper.insert(city);
5. 在Controller层里编写表示层相关方法;
*Controller相关知识参考下章。
@Controller
public class IndexController @Autowired
CityService cityService;
@ResponseBody
@PostMapping("/city")
public City saveCity(City city)
cityService.saveCity(city);
return city;
@ResponseBody
@GetMapping("/city")
public City getCityById(@RequestParam("id") Long id)
return cityService.getById(id);
6. *将上述
insert
用注解方式改成注解模式*此步骤不是必要的。
@Mapper
public interface CityMapper
@Insert("insert intocity(`name`,`state`,`country`) values(#name,#state,#country)")
@Options(useGeneratedKeys = true,keyProperty = "id")
public void insert(City city);
@Insert
- 插入语句;
- 用在mapper接口上;
- 用来代替原来xml里的< insert> 标签,参数为原生的插入insert相关的sql;
- 选择的参数;
- 用在mapper接口上;
- 用来代替原来xml里的< insert> 标签的参数配置,参数为相关的配置属性;
useGeneratedKeys
表示使用自增主键,可以返回自增主键值;keyProperty
表示自增属性的id。
- 引入
mybatis-starter
; - 配置
application.yaml
中,指定mapper-location
位置即可; - 编写
Mapper
接口并标注@Mapper
注解;- 简单方法直接注解方式;
- 复杂方法编写
mapper.xml
进行绑定映射;
@MapperScan("com.dlhjw.admin.mapper")
简化,其他的接口就可以不用标注@Mapper
注解。
新人制作,如有错误,欢迎指出,感激不尽!
:::
::: hljs-center
欢迎关注公众号,会分享一些更日常的东西!
:::
::: hljs-center
如需转载,请标注出处!
:::
::: hljs-center
文章图片
:::
推荐阅读
- #yyds干货盘点# Kubernetes 最小调度单元 Pod 的使用进阶及实践(05)
- #yyds干货盘点# mybatis源码解读(transaction包(事务管理功能))
- Linux中Shell重定向
- #私藏项目实操分享#专为初学者打造—Spring框架学习笔记
- #yyds干货盘点# SpringBoot 发送邮箱验证码(HTML模板)
- #yyds干货盘点#Python图像处理,cv2模块,OpenCV实现人脸检测
- #指尖人生#面向对象设计常用的设计模式-桥接模式
- JDK、JRE和JVM之间有什么区别()
- set,multiset,unordered_set,unordered_multiset之间的差异