前面兩篇文章和讀者聊了 Spring Boot 中最簡單的數據持久化方案 JdbcTemplate,JdbcTemplate 雖然簡單,可是用的並很少,由於它沒有 MyBatis 方便,在 Spring+SpringMVC 中整合 MyBatis 步驟仍是有點複雜的,要配置多個 Bean,Spring Boot 中對此作了進一步的簡化,使 MyBatis 基本上能夠作到開箱即用,本文就來看看在 Spring Boot 中 MyBatis 要如何使用。java
首先建立一個基本的 Spring Boot 工程,添加 Web 依賴,MyBatis 依賴以及 MySQL 驅動依賴,以下:mysql
建立成功後,添加Druid依賴,而且鎖定MySQL驅動版本,完整的依賴以下:git
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId>mybatis-spring-boot-starter</artifactId> <version>2.0.0</version> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid-spring-boot-starter</artifactId> <version>1.1.10</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.28</version> <scope>runtime</scope> </dependency>
如此,工程就算是建立成功了。小夥伴們注意,MyBatis 和 Druid 依賴的命名和其餘庫的命名不太同樣,是屬於 xxx-spring-boot-stater 模式的,這表示該 starter 是由第三方提供的。github
MyBatis 的使用和 JdbcTemplate 基本一致,首先也是在 application.properties 中配置數據庫的基本信息:web
spring.datasource.url=jdbc:mysql:///test01?useUnicode=true&characterEncoding=utf-8 spring.datasource.username=root spring.datasource.password=root spring.datasource.type=com.alibaba.druid.pool.DruidDataSource
配置完成後,MyBatis 就能夠建立 Mapper 來使用了,例如我這裏直接建立一個 UserMapper2,以下:spring
public interface UserMapper2 { @Select("select * from user") List<User> getAllUsers(); @Results({ @Result(property = "id", column = "id"), @Result(property = "username", column = "u"), @Result(property = "address", column = "a") }) @Select("select username as u,address as a,id as id from user where id=#{id}") User getUserById(Long id); @Select("select * from user where username like concat('%',#{name},'%')") List<User> getUsersByName(String name); @Insert({"insert into user(username,address) values(#{username},#{address})"}) @SelectKey(statement = "select last_insert_id()", keyProperty = "id", before = false, resultType = Integer.class) Integer addUser(User user); @Update("update user set username=#{username},address=#{address} where id=#{id}") Integer updateUserById(User user); @Delete("delete from user where id=#{id}") Integer deleteUserById(Integer id); }
這裏是經過全註解的方式來寫 SQL,不寫 XML 文件。sql
@Select、@Insert、@Update 以及 @Delete 四個註解分別對應 XML 中的 select、insert、update 以及 delete 標籤,@Results 註解相似於 XML 中的 ResultMap 映射文件(getUserById 方法給查詢結果的字段取別名主要是向小夥伴們演示下 @Results
註解的用法)。數據庫
另外使用 @SelectKey 註解能夠實現主鍵回填的功能,即當數據插入成功後,插入成功的數據 id 會賦值到 user 對象的id 屬性上。後端
UserMapper2 建立好以後,還要配置 mapper 掃描,有兩種方式,一種是直接在 UserMapper2 上面添加 @Mapper
註解,這種方式有一個弊端就是全部的 Mapper 都要手動添加,要是落下一個就會報錯,還有一個一勞永逸的辦法就是直接在啓動類上添加 Mapper 掃描,以下:mybatis
@SpringBootApplication @MapperScan(basePackages = "org.javaboy.mybatis.mapper") public class MybatisApplication { public static void main(String[] args) { SpringApplication.run(MybatisApplication.class, args); } }
好了,作完這些工做就能夠去測試 Mapper 的使用了。
固然,開發者也能夠在 XML 中寫 SQL,例如建立一個 UserMapper,以下:
public interface UserMapper { List<User> getAllUser(); Integer addUser(User user); Integer updateUserById(User user); Integer deleteUserById(Integer id); }
而後建立 UserMapper.xml 文件,以下:
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-21-mapper.dtd"> <mapper namespace="org.javaboy.mybatis.mapper.UserMapper"> <select id="getAllUser" resultType="org.javaboy.mybatis.model.User"> select * from t_user; </select> <insert id="addUser" parameterType="org.javaboy.mybatis.model.User"> insert into user (username,address) values (#{username},#{address}); </insert> <update id="updateUserById" parameterType="org.javaboy.mybatis.model.User"> update user set username=#{username},address=#{address} where id=#{id} </update> <delete id="deleteUserById"> delete from user where id=#{id} </delete> </mapper>
將接口中方法對應的 SQL 直接寫在 XML 文件中。
那麼這個 UserMapper.xml 到底放在哪裏呢?有兩個位置能夠放,第一個是直接放在 UserMapper 所在的包下面:
放在這裏的 UserMapper.xml 會被自動掃描到,可是有另一個 Maven 帶來的問題,就是 java 目錄下的 xml 資源在項目打包時會被忽略掉,因此,若是 UserMapper.xml 放在包下,須要在 pom.xml 文件中再添加以下配置,避免打包時 java 目錄下的 XML 文件被自動忽略掉:
<build> <resources> <resource> <directory>src/main/java</directory> <includes> <include>**/*.xml</include> </includes> </resource> <resource> <directory>src/main/resources</directory> </resource> </resources> </build>
固然,UserMapper.xml 也能夠直接放在 resources 目錄下,這樣就不用擔憂打包時被忽略了,可是放在 resources 目錄下,必須建立和 Mapper 接口包目錄相同的目錄層級,這樣才能確保打包後 XML 和 Mapper 接口又處於在一塊兒,不然 XML 文件將不能被自動掃描,這個時候就須要添加額外配置。例如我在 resources 目錄下建立 mapper 目錄用來放 mapper 文件,以下:
此時在 application.properties 中告訴 mybatis 去哪裏掃描 mapper:
mybatis.mapper-locations=classpath:mapper/*.xml
如此配置以後,mapper 就能夠正常使用了。注意這種方式不須要在 pom.xml 文件中配置文件過濾。
在 SSM 整合中,開發者須要本身提供兩個 Bean,一個SqlSessionFactoryBean ,還有一個是 MapperScannerConfigurer,在 Spring Boot 中,這兩個東西雖然不用開發者本身提供了,可是並不意味着這兩個 Bean 不須要了,在 org.mybatis.spring.boot.autoconfigure.MybatisAutoConfiguration
類中,咱們能夠看到 Spring Boot 提供了這兩個 Bean,部分源碼以下:
@org.springframework.context.annotation.Configuration @ConditionalOnClass({ SqlSessionFactory.class, SqlSessionFactoryBean.class }) @ConditionalOnSingleCandidate(DataSource.class) @EnableConfigurationProperties(MybatisProperties.class) @AutoConfigureAfter(DataSourceAutoConfiguration.class) public class MybatisAutoConfiguration implements InitializingBean { @Bean @ConditionalOnMissingBean public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception { SqlSessionFactoryBean factory = new SqlSessionFactoryBean(); factory.setDataSource(dataSource); return factory.getObject(); } @Bean @ConditionalOnMissingBean public SqlSessionTemplate sqlSessionTemplate(SqlSessionFactory sqlSessionFactory) { ExecutorType executorType = this.properties.getExecutorType(); if (executorType != null) { return new SqlSessionTemplate(sqlSessionFactory, executorType); } else { return new SqlSessionTemplate(sqlSessionFactory); } } @org.springframework.context.annotation.Configuration @Import({ AutoConfiguredMapperScannerRegistrar.class }) @ConditionalOnMissingBean(MapperFactoryBean.class) public static class MapperScannerRegistrarNotFoundConfiguration implements InitializingBean { @Override public void afterPropertiesSet() { logger.debug("No {} found.", MapperFactoryBean.class.getName()); } } }
從類上的註解能夠看出,噹噹前類路徑下存在 SqlSessionFactory、 SqlSessionFactoryBean 以及 DataSource 時,這裏的配置纔會生效,SqlSessionFactory 和 SqlTemplate 都被提供了。爲何要看這段代碼呢?下篇文章,鬆哥和大夥分享 Spring Boot 中 MyBatis 多數據源的配置時,這裏將是一個重要的參考。
好了,本文就先說到這裏,本文相關案例,你們能夠在 GitHub 上下載:https://github.com/lenve/javaboy-code-samples
關注公衆號【江南一點雨】,專一於 Spring Boot+微服務以及先後端分離等全棧技術,按期視頻教程分享,關注後回覆 Java ,領取鬆哥爲你精心準備的 Java 乾貨!