MyBatis 是一款优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)为数据库中的记录。

越来越多的企业已经将 MyBatis 使用到了正式的生产环境,本文就使用 MyBatis 的几种方式提供简单的示例,以及如何对数据库密码进行加密,目前有以下章节:

  • 单独使用 MyBatis
  • 集成 Spring 框架
  • 集成 Spring Boot 框架
  • Spring Boot 配置数据库密码加密

1.单独使用

引入 MyBatis 依赖,单独使用,版本是3.5.6

引入依赖

<dependencies>
<!-- https://mvnrepository.com/artifact/org.mybatis/mybatis -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.6</version>
</dependency>
<!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.19</version>
</dependency>
</dependencies>

添加mybatis-config.xml

<?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>
<!-- plugins在配置文件中的位置必须符合要求,否则会报错,顺序如下: properties?, settings?, typeAliases?,
typeHandlers?, objectFactory?,objectWrapperFactory?, plugins?, environments?,
databaseIdProvider?, mappers? -->
<!-- 配置mybatis的缓存,延迟加载等等一系列属性 -->
<settings>
<!-- 全局映射器启用缓存 -->
<setting name="cacheEnabled" value="false" />
<!-- 对于未知的SQL查询,允许返回不同的结果集以达到通用的效果 -->
<setting name="multipleResultSetsEnabled" value="true" />
<!-- 是否开启自动驼峰命名规则映射,数据库的A_COLUMN映射为Java中的aColumn -->
<setting name="mapUnderscoreToCamelCase" value="true" />
<!-- MyBatis利用本地缓存机制(Local Cache)防止循环引用(circular references)和加速重复嵌套查询 -->
<setting name="localCacheScope" value="STATEMENT" />
</settings>
<!-- 指定路径下的实体类支持别名(默认实体类的名称,首字母小写), @Alias注解可设置别名 -->
<typeAliases>
<package name="tk.mybatis.simple.model" />
</typeAliases>
<!-- 配置当前环境信息 -->
<environments default="development">
<environment id="development">
<transactionManager type="JDBC">
<property name="" value=""/>
</transactionManager>
<!-- 配置数据源 -->
<dataSource type="UNPOOLED">
<property name="driver" value="com.mysql.cj.jdbc.Driver"/>
<property name="url" value="jdbc:mysql://localhost:3306/gsfy_user?useUnicode=true&amp;characterEncoding=UTF-8&amp;useSSL=false"/>
<property name="username" value="user"/>
<property name="password" value="password"/>
</dataSource>
</environment>
</environments>
<!-- 指定Mapper接口的路径 -->
<mappers>
<package name="tk.mybatis.simple.mapper"/>
</mappers>
</configuration>

开始使用

Model类

tk.mybatis.simple.model.DbTest.java

package tk.mybatis.simple.model;

public class DbTest {

    public Integer id;
public String text; public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getText() {
return text;
} public void setText(String text) {
this.text = text;
} @Override
public String toString() {
return "DbTest{" +
"id=" + id +
", text='" + text + '\'' +
'}';
}
}

Mapper接口

tk.mybatis.simple.mapper.DbTestMapper

package tk.mybatis.simple.mapper;

import tk.mybatis.simple.model.DbTest;

public interface DbTestMapper {

    DbTest queryById(Integer id);
}

XML映射文件

XML映射文件请放于Mapper接口所在路径下,保证名称相同

tk/mybatis/simple/mapper/DbTestMapper.xml

<?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="tk.mybatis.simple.mapper.DbTestMapper">
<select id="queryById" parameterType="int" resultType="DbTest">
SELECT db_test_id AS id, db_test_text AS text
FROM db_test
WHERE db_test_id = #{id, jdbcType=INTEGER}
</select>
</mapper>

执行示例

package tk.mybatis.simple;

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 tk.mybatis.simple.mapper.DbTestMapper; import java.io.IOException;
import java.io.Reader; public class MyBatisHelper { private static SqlSessionFactory sqlSessionFactory; static {
try {
// MyBatis的配置文件
Reader reader = Resources.getResourceAsReader("mybatis-config.xml");
// 创建一个 sqlSessionFactory 工厂类
sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
reader.close();
} catch (IOException e) {
e.printStackTrace();
}
} public static SqlSession getSqlSession() {
return sqlSessionFactory.openSession();
} public static void main(String[] args) {
// 创建一个 SqlSession 会话
SqlSession sqlSession = MyBatisHelper.getSqlSession();
// 获取 DbTestMapper 接口的动态代理对象
DbTestMapper dbTestMapper = sqlSession.getMapper(DbTestMapper.class);
// 执行查询
System.out.println(dbTestMapper.queryById(1).toString());
}
}

2.集成Spring

在 Spring 项目中,使用 MyBatis 的模板,请注意 Spring 的版本为5.2.10.RELEASE

日志框架使用Log4j2(推荐),版本为2.13.3,性能高于logback和log4j

我的项目模板 Git 地址

工程结构图

  • 其中jquery.min.js文件可以去官网下载

引入依赖

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion> <groupId>tk.mybatis.simple</groupId>
<artifactId>mybatis-spring</artifactId>
<packaging>war</packaging> <properties>
<!-- MyBatis 版本号 -->
<mybatis.version>3.5.6</mybatis.version>
<!-- Jackson 版本号 -->
<jackson.version>2.11.3</jackson.version>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties> <dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-framework-bom</artifactId>
<version>5.2.10.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-bom</artifactId>
<version>2.13.3</version>
<scope>import</scope>
<type>pom</type>
</dependency>
</dependencies>
</dependencyManagement> <dependencies>
<!-- MyBatis 相关 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>1.3.2</version>
</dependency>
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>${mybatis.version}</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.19</version>
</dependency>
<!-- druid 数据源-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.2.3</version>
</dependency>
<!-- pagehelper 分页插件 -->
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper</artifactId>
<version>5.2.0</version>
</dependency>
<dependency>
<groupId>com.github.jsqlparser</groupId>
<artifactId>jsqlparser</artifactId>
<version>3.2</version>
</dependency> <!--web-->
<!--支持 Servlet-->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
<scope>provided</scope>
</dependency>
<!--支持 JSP-->
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.1</version>
<scope>provided</scope>
</dependency>
<!--支持 JSTL-->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency> <!--Spring 上下文,核心依赖-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
</dependency>
<!--Spring JDBC-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
</dependency>
<!--Spring 事务-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
</dependency>
<!--Spring 面向切面编程-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
</dependency>
<!--spring-aop 依赖-->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.2</version>
</dependency>
<!--JSR 250 公共注解-->
<dependency>
<groupId>javax.annotation</groupId>
<artifactId>javax.annotation-api</artifactId>
<version>1.2</version>
</dependency>
<!--Java 事务接口-->
<dependency>
<groupId>javax.transaction</groupId>
<artifactId>javax.transaction-api</artifactId>
<version>1.2</version>
</dependency> <!--Spring Web 核心-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
<!--Spring MVC-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
</dependency>
<!--spring mvc-json依赖-->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>${jackson.version}</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>${jackson.version}</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>${jackson.version}</version>
</dependency> <!-- 日志文件管理包 -->
<!-- log4j2 start -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
</dependency>
<!-- 保证 web 应用正常清理 log 资源 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-web</artifactId>
</dependency>
<dependency> <!-- 桥接:slf4j 到 log4j2 的桥梁 -->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
</dependency>
<dependency> <!-- 后向兼容:log4j1.x 平滑升级到 log4j2 -->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-1.2-api</artifactId>
</dependency>
<dependency> <!-- 桥接:commons-logging(jcl) 到 log4j2 的桥梁 -->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-jcl</artifactId>
</dependency>
<!-- slf4j 日志切面,相当于一个适配器 -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.7</version>
</dependency>
<!-- 高性能并发编程框架 log4j2 使用 -->
<dependency>
<groupId>com.lmax</groupId>
<artifactId>disruptor</artifactId>
<version>3.4.2</version>
</dependency>
<!-- log4j2 end --> <!-- 上传组件包 -->
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.4</version>
</dependency>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.8.0</version>
</dependency>
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
<version>1.15</version>
</dependency>
</dependencies> <build>
<finalName>study-ssm</finalName>
<plugins>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
<encoding>UTF-8</encoding>
</configuration>
</plugin>
</plugins>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
<resource>
<directory>src/main/resources/META-INF/spring</directory>
<includes>
<include>spring-mybatis.xml</include>
<include>spring-mvc.xml</include>
</includes>
<filtering>false</filtering>
</resource>
<resource>
<directory>src/main/resources</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
</resources>
</build> </project>

添加spring-mvc.xml

<?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:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.1.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc-4.0.xsd">
<!-- 自动扫描该包,将 Spring Bean 注册到 Spring 的上下文中 -->
<context:component-scan base-package="tk.mybatis.simple" /> <!--避免 IE 执行 AJAX 时,返回 JSON 出现下载文件 -->
<bean id="mappingJacksonHttpMessageConverter"
class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
<property name="supportedMediaTypes">
<list>
<value>text/html;charset=UTF-8</value>
</list>
</property>
</bean>
<!-- 启动 SpringMVC 的注解功能,完成请求和注解 POJO 的映射 -->
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter ">
<property name="messageConverters">
<list>
<ref bean="mappingJacksonHttpMessageConverter" /> <!-- JSON转换器 -->
</list>
</property>
</bean> <!-- 配置文件上传,如果没有使用文件上传可以不用配置,pom 中也不必引入上传组件包 -->
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<!-- 默认编码 -->
<property name="defaultEncoding" value="utf-8" />
<!-- 文件大小最大值 100M -->
<property name="maxUploadSize" value="104857600" />
<!-- 内存中的最大值 4M-->
<property name="maxInMemorySize" value="40960" />
<!-- 启用是为了推迟文件解析,以便捕获文件大小异常 -->
<property name="resolveLazily" value="true"/>
</bean> <!-- 定义 ViewResolver(视图解析器),配置多个需要使用 order 属性排序,InternalResourceViewResolver 放在最后-->
<bean class="org.springframework.web.accept.ContentNegotiationManagerFactoryBean">
<property name="favorParameter" value="true" />
<property name="parameterName" value="format"/>
<property name="ignoreAcceptHeader" value="true" />
<property name="mediaTypes">
<value>
<!-- 告诉视图解析器,返回的类型为 json 格式 -->
json=application/json
xml=application/xml
html=text/html
</value>
</property>
<property name="defaultContentType" value="text/html" /> </bean> <!-- 定义跳转的文件的前后缀,视图名称解析器 -->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<!-- 自动给后面 action 的方法 return 的字符串加上前缀和后缀,变成一个可用的地址 -->
<property name="prefix" value="/WEB-INF/jsp/" />
<property name="suffix" value=".jsp" />
</bean> <!-- 扩充了注解驱动,可以将请求参数绑定到控制器参数 -->
<mvc:annotation-driven />
<!-- 让一些静态的不被 SpringMVC 的拦截器拦截 -->
<mvc:default-servlet-handler/>
<!-- 静态资源 -->
<mvc:resources location="static/" mapping="/static/**"/> </beans>

添加mybatis-config.xml

<?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>
<!-- plugins在配置文件中的位置必须符合要求,否则会报错,顺序如下: properties, settings, typeAliases, plugins,
objectFactory, objectWrapperFactory, reflectorFactory, environments, databaseIdProvider, typeHandlers, mappers -->
<!-- 配置mybatis的缓存,延迟加载等等一系列属性 -->
<settings>
<!-- 全局的开启或关闭配置文件中的所有映射器已经配置的任何缓存,关闭二级缓存,默认开启 -->
<setting name="cacheEnabled" value="false" />
<!-- 开启一级缓存,缓存级别为SESSION(默认),如果缓存级别为STATEMENT将不会再同一个SqlSession中缓存 -->
<setting name="localCacheScope" value="STATEMENT" />
<!-- 通过resultMap标签内的association标签可使用延迟加载 -->
<!-- 查询时,关闭关联对象即时加载以提高性能,开启延迟加载,默认关闭,关闭表示直接加载,查询时就进行关联查询 -->
<setting name="lazyLoadingEnabled" value="true" />
<!-- 设置关联对象加载的形态,关闭侵入式延迟加载,在访问主对象时不进行查询关联对象,而是在真正访问关联对象时才进行关联查询,以提高性能 -->
<!-- 3.4.1及之前的版本默认为开启,表示查询时不进行关联查询,访问主对象时才进行关联查询 -->
<setting name="aggressiveLazyLoading" value="false" />
<!-- 允许使用列标签代替列名 -->
<setting name="useColumnLabel" value="true" />
<!-- 不允许使用自定义的主键值(比如由程序生成的UUID 32位编码作为键值),数据表的PK生成策略将被覆盖 -->
<setting name="useGeneratedKeys" value="false" />
<!-- 是否开启自动驼峰命名规则(camel case)映射,即从经典数据库列名A_COLUMN到经典Java属性名aColumn的类似映射 -->
<setting name="mapUnderscoreToCamelCase" value="true" />
</settings>
<!-- 指定路径下的实体类支持别名(默认实体类的名称 全小写), @Alias 注解可设置别名 -->
<typeAliases>
<package name="tk.mybatis.simple.model" />
</typeAliases>
<plugins>
<!-- PageHelper 分页插件,配置参考:https://github.com/pagehelper/Mybatis-PageHelper -->
<plugin interceptor="com.github.pagehelper.PageInterceptor">
<!-- 使用哪种方言的分页方式,默认会检测数据库连接,自动选择合适的分页方式 -->
<property name="helperDialect" value="mysql"/>
<!-- 默认值为 false,该参数对使用 RowBounds 作为分页参数时有效。
当该参数设置为 true 时,会将 RowBounds 中的 offset 参数当成 pageNum 使用,可以用页码和页面大小两个参数进行分页 -->
<property name="offsetAsPageNum" value="true" />
<!-- 默认值为false,该参数对使用 RowBounds 作为分页参数时有效。
当该参数设置为true时,使用 RowBounds 分页会进行 count 查询 -->
<property name="rowBoundsWithCount" value="true" />
<!-- 默认值为 false,当该参数设置为 true 时,
如果 pageSize=0 或者 RowBounds.limit = 0 就会查询出全部的结果(相当于没有执行分页查询,但是返回结果仍然是 Page 类型)-->
<property name="pageSizeZero" value="true" />
</plugin>
</plugins>
</configuration>

添加spring-mybatis.xml

<?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:tx="http://www.springframework.org/schema/tx" xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
http://www.springframework.org/schema/aop
https://www.springframework.org/schema/aop/spring-aop.xsd">
<!-- 定义一个数据源 -->
<bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource"
init-method="init" destroy-method="close">
<property name="url" value="jdbc:mysql://127.0.0.1:3306/test?useUnicode=true&amp;characterEncoding=utf8"/>
<property name="driverClassName" value="com.mysql.cj.jdbc.Driver"/>
<property name="username" value="root"/>
<property name="password" value="password"/>
<property name="filters" value="stat,log4j,wall"/>
<!-- 最大连接池数量 -->
<property name="maxActive" value="20"/>
<property name="minIdle" value="20"/>
<!-- 初始化时建立物理连接的个数 -->
<property name="initialSize" value="5"/>
<!-- 获取连接时最大等待时间 -->
<property name="maxWait" value="10000"/>
<!-- 在指定时间间隔内执行一次空闲连接回收器 -->
<property name="timeBetweenEvictionRunsMillis" value="3600000"/>
<!-- 池中的连接空闲指定时间后被回收 -->
<property name="minEvictableIdleTimeMillis" value="120000"/>
<property name="testWhileIdle" value="true"/>
<property name="testOnBorrow" value="false"/>
</bean> <!-- Spring 和 MyBatis 整合 -->
<bean id="mySqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<!-- 引入 MyBatis 配置文件 -->
<property name="configLocation" value="classpath:mybatis-config.xml"/>
<!-- 自动扫描 XML 映射文件 -->
<property name="mapperLocations" value="classpath:tk/mybatis/simple/mapper/*.xml"/>
</bean> <!-- 通过 MapperScannerConfigurer 类自动扫描 Mapper 接口 -->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<!-- Mapper 接口所在包路径 -->
<property name="basePackage" value="tk.mybatis.simple.mapper"/>
<!--引用上面的 SqlSessionFactoryBean 对象 -->
<property name="sqlSessionFactoryBeanName" value="mySqlSessionFactory"/>
</bean> <!-- 事务管理器 -->
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<!-- 指定数据源 -->
<property name="dataSource" ref="dataSource"/>
</bean>
<!-- 设置为上面定义事务管理器,默认值为 transactionManager -->
<tx:annotation-driven transaction-manager="txManager"/> <!-- 配置事务传播特性  -->
<tx:advice id="transactionAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="insert*" rollback-for="java.lang.Exception"/>
<tx:method name="delete*" rollback-for="java.lang.Exception"/>
<tx:method name="update*" rollback-for="java.lang.Exception"/>
<tx:method name="*" read-only="true"/>
</tx:attributes>
</tx:advice>
<!--  配置哪些类的哪些方法参与事务 -->
<aop:config>
<aop:advisor advice-ref="transactionAdvice" pointcut="execution(* tk.mybatis.*.service..*Service*.*(..))"/>
</aop:config>
<aop:aspectj-autoproxy/> </beans>

添加log4j2.xml

<?xml version="1.0" encoding="UTF-8"?>
<configuration status="INFO" monitorInterval="30">
<appenders>
<!-- 参考官方地址:https://logging.apache.org/log4j/2.x/ -->
<!-- 这个输出控制台的配置 -->
<Console name="Console" target="SYSTEM_OUT">
<!-- 设置输出日志级别(高于 level),匹配才打印 -->
<ThresholdFilter level="INFO" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 打印日志的格式 -->
<PatternLayout pattern="%d{yyyy-MM-dd HH:mm:ss,SSS}:%4p %t (%F:%L) - %m%n"/>
</Console>
<!-- 定义一个日志输入文件 RollingFile,按天或者超过 100M 分割会进行分割 -->
<RollingFile name="RollingFile" fileName="logs/trace.log"
append="true" filePattern="logs/$${date:yyyy-MM}/trace-%d{yyyy-MM-dd}-%i.log.gz">
<!-- 需要接收的日志的级别(高于 level) -->
<ThresholdFilter level="INFO" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 日志的格式 -->
<PatternLayout pattern="%d{yyyy-MM-dd HH:mm:ss,SSS}:%4p %t (%F:%L) - %m%n"/>
<Policies>
<TimeBasedTriggeringPolicy/>
<SizeBasedTriggeringPolicy size="100 MB"/>
</Policies>
</RollingFile>
<!-- 定义一个日志输入文件 RollingErrorFile,按天或者超过 100M 分割会进行分割 -->
<RollingFile name="RollingErrorFile" fileName="logs/error.log"
append="true" filePattern="logs/$${date:yyyy-MM}/error-%d{yyyy-MM-dd}-%i.log.gz">
<!-- 需要接收的日志的级别(高于 level) -->
<ThresholdFilter level="WARN" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 日志的格式 -->
<PatternLayout pattern="%d{yyyy-MM-dd HH:mm:ss,SSS}:%4p %t (%F:%L) - %m%n"/>
<Policies>
<TimeBasedTriggeringPolicy/>
<SizeBasedTriggeringPolicy size="100 MB"/>
</Policies>
</RollingFile>
</appenders>
<loggers>
<!--过滤掉 Spring 和 Mybatis 的一些无用的 DEBUG 信息 -->
<logger name="org.springframework" level="INFO"/>
<logger name="org.mybatis" level="INFO"/>
<root level="INFO" includeLocation="true">
<appender-ref ref="Console"/>
<appender-ref ref="RollingFile"/>
<appender-ref ref="RollingErrorFile"/>
</root>
</loggers>
</configuration>

添加web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://java.sun.com/xml/ns/javaee"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
version="3.0">
<display-name>Archetype Created Web Application</display-name> <!-- Spring 和 MyBatis 的配置文件 -->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-mybatis.xml</param-value>
</context-param> <!-- 编码过滤器,Spring 提供了 CharacterEncodingFilter 过滤器
这个过滤器就是针对于每次浏览器请求进行过滤的,然后再其之上添加了父类没有的功能即处理字符编码 -->
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<async-supported>true</async-supported>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping> <!-- 在容器(Tomcat、Jetty)启动时会被 ContextLoaderListener 监听到,从而调用其 contextInitialized() 方法,初始化 Root WebApplicationContext 容器 -->
<!-- 声明 Spring Web 容器监听器 -->
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<!-- 防止 Spring 内存溢出监听器 -->
<listener>
<listener-class>org.springframework.web.util.IntrospectorCleanupListener</listener-class>
</listener> <!-- 1.SpringMVC 配置 前置控制器(SpringMVC 的入口)
DispatcherServlet 是一个 Servlet,所以可以配置多个 DispatcherServlet -->
<servlet>
<!-- 在 DispatcherServlet 的初始化过程中,框架会在 web 应用 的 WEB-INF 文件夹下,
寻找名为 [servlet-name]-servlet.xml 的配置文件,生成文件中定义的 Bean. -->
<servlet-name>SpringMVC</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<!-- 配置需要加载的配置文件 -->
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-mvc.xml</param-value>
</init-param>
<!-- 程序运行时从 web.xml 开始,加载顺序为:context-param -> Listener -> Filter -> Structs -> Servlet
设置 web.xml 文件启动时加载的顺序(1 代表容器启动时首先初始化该 Servlet,让这个 Servlet 随 Servlet 容器一起启动)
load-on-startup 是指这个 Servlet 是在当前 web 应用被加载的时候就被创建,而不是第一次被请求的时候被创建 -->
<load-on-startup>1</load-on-startup>
<async-supported>true</async-supported>
</servlet>
<servlet-mapping>
<!-- 这个 Servlet 的名字是 SpringMVC,可以有多个 DispatcherServlet,是通过名字来区分的
每一个 DispatcherServlet 有自己的 WebApplicationContext 上下文对象,同时保存在 ServletContext 中和 Request 对象中
ApplicationContext(Spring 容器)是 Spring 的核心
Context 我们通常解释为上下文环境,Spring 把 Bean 放在这个容器中,在需要的时候,可以 getBean 方法取出-->
<servlet-name>SpringMVC</servlet-name>
<!-- Servlet 拦截匹配规则,可选配置:*.do、*.action、*.html、/、/xxx/* ,不允许:/* -->
<url-pattern>/</url-pattern>
</servlet-mapping> <welcome-file-list>
<!-- 浏览器输入到项目名,默认打开如下配置页面 -->
<welcome-file>index.jsp</welcome-file>
</welcome-file-list> </web-app>

开始使用

Model类

tk.mybatis.simple.model.DbTest.java

package tk.mybatis.simple.model;

public class DbTest {

    public Integer id;
public String text; public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getText() {
return text;
} public void setText(String text) {
this.text = text;
} @Override
public String toString() {
return "DbTest{" +
"id=" + id +
", text='" + text + '\'' +
'}';
}
}

Mapper接口

tk.mybatis.simple.mapper.DbTestMapper

package tk.mybatis.simple.mapper;

import tk.mybatis.simple.model.DbTest;

public interface DbTestMapper {

    DbTest queryById(Integer id);
}

XML映射文件

XML映射文件请放于Mapper接口所在路径下,保证名称相同

tk/mybatis/simple/mapper/DbTestMapper.xml

<?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="tk.mybatis.simple.mapper.DbTestMapper">
<select id="queryById" parameterType="int" resultType="DbTest">
SELECT db_test_id AS id, db_test_text AS text
FROM db_test
WHERE db_test_id = #{id, jdbcType=INTEGER}
</select>
</mapper>

Controller类

package tk.mybatis.simple.controller;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;
import tk.mybatis.simple.mapper.DbTestMapper;
import tk.mybatis.simple.model.DbTest; @Controller
@RequestMapping(value = "/test")
public class DbTestController { private static final Logger logger = LogManager.getLogger(DbTestController.class); @Autowired
private DbTestMapper dbTestMapper; @GetMapping("/")
public String index() {
return "welcome";
} @GetMapping("/query")
public ModelAndView query(@RequestParam("id") Integer id) {
DbTest dbTest = dbTestMapper.queryById(id);
logger.info("入参:{},查询结果:{}", id, dbTest.toString());
ModelAndView mv = new ModelAndView();
mv.setViewName("result");
mv.addObject("test", dbTest);
return mv;
}
}

index.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html lang="zh-CN">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>首页</title>
</head>
<body>
<h3>Hello World!</h3>
<form method="get" action="<c:url value="/test/"/>">
<button class="btn btn-default" type="submit">
<span>开始测试</span>
</button>
</form>
</body>
</html>

welcome.jsp

<%--
Created by IntelliJ IDEA.
User: jingp
Date: 2019/6/5
Time: 15:17
To change this template use File | Settings | File Templates.
--%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html lang="zh-CN">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>查询</title> </head>
<body>
<h3>查询数据库</h3>
<form method="get" action="<c:url value="/test/query"/>">
<div class="input-group">
<span class="input-group-addon">ID:</span>
<input type="number" name="id" class="form-control" required>
</div>
<button class="btn btn-default" type="submit">
<span>查询</span>
</button>
</form> <script src="../../static/jquery.min.js"></script>
</body>
</html>

result.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html lang="zh-CN">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>结果</title>
</head>
<body>
<h4>查询结果:${test.toString()}</h4>
<form method="post" action="<c:url value="/"/>">
<button class="btn btn-default" type="submit">
<span>退出</span>
</button>
</form> <script src="../../static/jquery.min.js"></script>
</body>
</html>

运行程序

配置好Tomcat,然后启动就可以了,进入页面,点击开始测试,然后查询数据库就可以通过MyBatis操作数据库了

3.集成SpringBoot

引入依赖

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.3.RELEASE</version>
</parent>
<modelVersion>4.0.0</modelVersion> <groupId>tk.mybatis.simple</groupId>
<artifactId>mybatis-spring-boot</artifactId>
<packaging>jar</packaging> <properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties> <dependencyManagement>
<dependencies>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-bom</artifactId>
<version>2.13.3</version>
<scope>import</scope>
<type>pom</type>
</dependency>
</dependencies>
</dependencyManagement> <dependencies>
<!-- Spring Boot 核心包,包括自动装配,日志,以及YAML文件解析 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- 提供全栈的 WEB 开发特性,包括 Spring MVC 依赖和 Tomcat 容器 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- 提供通用单元测试依赖,包括 JUnit, Hamcrest , Mockito -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency> <!-- lombok 工具 -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.22</version>
<scope>provided</scope>
</dependency> <!-- MyBatis 相关 -->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.1.4</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.19</version>
</dependency>
<!-- druid 数据源-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.2.3</version>
</dependency>
<!-- pagehelper 分页插件 -->
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper-spring-boot-starter</artifactId>
<version>1.3.0</version>
</dependency> <!-- 日志文件管理包 -->
<!-- log4j2 start -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
</dependency>
<!-- 保证 web 应用正常清理 log 资源 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-web</artifactId>
</dependency>
<dependency> <!-- 桥接:slf4j 到 log4j2 的桥梁 -->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
</dependency>
<dependency> <!-- 后向兼容:log4j1.x 平滑升级到 log4j2 -->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-1.2-api</artifactId>
</dependency>
<dependency> <!-- 桥接:commons-logging(jcl) 到 log4j2 的桥梁 -->
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-jcl</artifactId>
</dependency>
<!-- slf4j 日志切面,相当于一个适配器 -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.7</version>
</dependency>
<!-- 高性能并发编程框架 log4j2 使用 -->
<dependency>
<groupId>com.lmax</groupId>
<artifactId>disruptor</artifactId>
<version>3.4.2</version>
</dependency>
<!-- log4j2 end --> <!-- JSON 工具 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.54</version>
</dependency>
</dependencies> <build>
<finalName>basic</finalName>
<!-- 配置相关插件 -->
<plugins>
<!-- appassembler-maven-plugin -->
<!-- mvn clean package appassembler:assemble -Dmaven.test.skip=true -Dmaven.javadoc.skip=true -->
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>appassembler-maven-plugin</artifactId>
<version>1.10</version>
<configuration>
<!-- 生成linux和windows两种执行脚本 -->
<platforms>
<platform>unix</platform>
<platform>windows</platform>
</platforms>
<!-- jar存放的目录 -->
<repositoryName>lib</repositoryName>
<!-- jar包存放在指定目录的规则,默认是${groupId}/${artifactId}的目录格式,flat表示直接把jar放到目录下 -->
<repositoryLayout>flat</repositoryLayout>
<!-- 配置文件存放的目录 -->
<configurationDirectory>conf</configurationDirectory>
<!-- copy配置文件到上面目录 -->
<copyConfigurationDirectory>true</copyConfigurationDirectory>
<!-- 从哪里copy配置文件(默认src/main/config) -->
<configurationSourceDirectory>src/main/resources</configurationSourceDirectory>
<includeConfigurationDirectoryInClasspath>true</includeConfigurationDirectoryInClasspath>
<!-- ${project.build.directory}:target, 文件存放的根目录 -->
<assembleDirectory>${project.build.directory}/basic-assemble</assembleDirectory>
<programs>
<program>
<!-- 启动类 -->
<mainClass>com.fullmoon.study.Application</mainClass>
<!-- 生成的文件名称:basic.sh -->
<id>basic</id>
<!-- 配置JVM参数 -->
<jvmSettings>
<extraArguments>
<!--<extraArgument>-server</extraArgument>-->
<extraArgument>-XX:+HeapDumpOnOutOfMemoryError</extraArgument>
<extraArgument>-XX:HeapDumpPath=/app/dump</extraArgument>
<extraArgument>-Xmx512m</extraArgument>
<extraArgument>-Xms512m</extraArgument>
</extraArguments>
</jvmSettings>
</program>
</programs>
</configuration>
</plugin>
<!-- 编译插件 -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
</plugins>
<!-- 指定 resources -->
<resources>
<resource>
<directory>src/main/resources</directory>
<includes>
<include>*.properties</include>
<include>*.xml</include>
<include>*.yml</include>
</includes>
<filtering>false</filtering>
</resource>
<resource>
<directory>src/main/resources/mapper</directory>
<targetPath>mapper/</targetPath>
<includes>
<include>*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
</resources>
</build> </project>

添加mybatis-config.xml

MyBatis 的配置文件

<?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>
<!-- plugins在配置文件中的位置必须符合要求,否则会报错,顺序如下: properties, settings, typeAliases, plugins,
objectFactory, objectWrapperFactory, reflectorFactory, environments, databaseIdProvider, typeHandlers, mappers -->
<!-- 配置mybatis的缓存,延迟加载等等一系列属性 -->
<settings>
<!-- 全局的开启或关闭配置文件中的所有映射器已经配置的任何缓存,关闭二级缓存,默认开启 -->
<setting name="cacheEnabled" value="false" />
<!-- 开启一级缓存,缓存级别为SESSION(默认),如果缓存级别为STATEMENT将不会再同一个SqlSession中缓存 -->
<setting name="localCacheScope" value="STATEMENT" />
<!-- 通过resultMap标签内的association标签可使用延迟加载 -->
<!-- 查询时,关闭关联对象即时加载以提高性能,开启延迟加载,默认关闭,关闭表示直接加载,查询时就进行关联查询 -->
<setting name="lazyLoadingEnabled" value="true" />
<!-- 设置关联对象加载的形态,关闭侵入式延迟加载,在访问主对象时不进行查询关联对象,而是在真正访问关联对象时才进行关联查询,以提高性能 -->
<!-- 3.4.1及之前的版本默认为开启,表示查询时不进行关联查询,访问主对象时才进行关联查询 -->
<setting name="aggressiveLazyLoading" value="false" />
<!-- 允许使用列标签代替列名 -->
<setting name="useColumnLabel" value="true" />
<!-- 不允许使用自定义的主键值(比如由程序生成的UUID 32位编码作为键值),数据表的PK生成策略将被覆盖 -->
<setting name="useGeneratedKeys" value="false" />
<!-- 是否开启自动驼峰命名规则(camel case)映射,即从经典数据库列名A_COLUMN到经典Java属性名aColumn的类似映射 -->
<setting name="mapUnderscoreToCamelCase" value="true" />
</settings>
</configuration>

添加application.yml

Spring Boot 的配置文件

server:
port: 9092
servlet:
context-path: /mybatis-spring-boot-demo
tomcat:
accept-count: 200
min-spare-threads: 200
spring:
application:
name: mybatis-spring-boot-demo
profiles:
active: test
servlet:
multipart:
max-file-size: 100MB
max-request-size: 100MB
datasource:
druid:
driver-class-name: com.mysql.cj.jdbc.Driver # 不配置则会根据 url 自动识别
initial-size: 5 # 初始化时建立物理连接的个数
min-idle: 20 # 最小连接池数量
max-active: 20 # 最大连接池数量
max-wait: 10000 # 获取连接时最大等待时间,单位毫秒
validation-query: SELECT 1 # 用来检测连接是否有效的 sql
test-while-idle: true # 申请连接的时候检测,如果空闲时间大于 timeBetweenEvictionRunsMillis,则执行 validationQuery 检测连接是否有效
test-on-borrow: false # 申请连接时执行 validationQuery 检测连接是否有效
min-evictable-idle-time-millis: 120000 # 连接保持空闲而不被驱逐的最小时间,单位是毫秒
time-between-eviction-runs-millis: 3600000 # 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒
filters: stat,log4j,wall # 配置过滤器,stat-监控统计,log4j-日志,wall-防御 SQL 注入
connection-properties: 'druid.stat.mergeSql=true;druid.stat.slowSqlMillis=5000' # StatFilter配置,打开合并 SQL 功能和慢 SQL 记录
web-stat-filter: # WebStatFilter 配置
enabled: true
url-pattern: '/*'
exclusions: '*.js,*.gif,*.jpg,*.bmp,*.png,*.css,*.ico,/druid/*'
stat-view-servlet: # StatViewServlet 配置
enabled: true
url-pattern: '/druid/*'
reset-enable: false
login-username: druid
login-password: druid
aop-patterns: 'com.fullmoon.study.service.*' # Spring 监控配置
mybatis:
type-aliases-package: tk.mybatis.simple.model
mapper-locations: classpath:mapper/*.xml
config-location: classpath:mybatis-config.xml
pagehelper:
helper-dialect: mysql
reasonable: true # 分页合理化参数
offset-as-page-num: true # 将 RowBounds 中的 offset 参数当成 pageNum 使用
supportMethodsArguments: true # 支持通过 Mapper 接口参数来传递分页参数
# 测试环境
---
spring:
profiles: test
datasource:
druid:
url: jdbc:mysql://127.0.0.1:3306/test?useUnicode=true&amp;characterEncoding=utf8
username: root
password: password

注意上面 mybatis 的相关配置,XML 映射文件是存放于 classpath 下的 mapper 文件夹下面的

添加log4j2.xml

<?xml version="1.0" encoding="UTF-8"?>
<configuration status="INFO" monitorInterval="30">
<appenders>
<!-- 参考官方地址:https://logging.apache.org/log4j/2.x/ -->
<!-- 这个输出控制台的配置 -->
<Console name="Console" target="SYSTEM_OUT">
<!-- 设置输出日志级别(高于 level),匹配才打印 -->
<ThresholdFilter level="INFO" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 打印日志的格式 -->
<PatternLayout pattern="%d{yyyy-MM-dd HH:mm:ss,SSS}:%4p %t (%F:%L) - %m%n"/>
</Console>
<!-- 定义一个日志输入文件 RollingFile,按天或者超过 100M 分割会进行分割 -->
<RollingFile name="RollingFile" fileName="logs/trace.log"
append="true" filePattern="logs/$${date:yyyy-MM}/trace-%d{yyyy-MM-dd}-%i.log.gz">
<!-- 需要接收的日志的级别(高于 level) -->
<ThresholdFilter level="INFO" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 日志的格式 -->
<PatternLayout pattern="%d{yyyy-MM-dd HH:mm:ss,SSS}:%4p %t (%F:%L) - %m%n"/>
<Policies>
<TimeBasedTriggeringPolicy/>
<SizeBasedTriggeringPolicy size="100 MB"/>
</Policies>
</RollingFile>
<!-- 定义一个日志输入文件 RollingErrorFile,按天或者超过 100M 分割会进行分割 -->
<RollingFile name="RollingErrorFile" fileName="logs/error.log"
append="true" filePattern="logs/$${date:yyyy-MM}/error-%d{yyyy-MM-dd}-%i.log.gz">
<!-- 需要接收的日志的级别(高于 level) -->
<ThresholdFilter level="WARN" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 日志的格式 -->
<PatternLayout pattern="%d{yyyy-MM-dd HH:mm:ss,SSS}:%4p %t (%F:%L) - %m%n"/>
<Policies>
<TimeBasedTriggeringPolicy/>
<SizeBasedTriggeringPolicy size="100 MB"/>
</Policies>
</RollingFile>
</appenders>
<loggers>
<!--过滤掉 Spring 和 Mybatis 的一些无用的 DEBUG 信息 -->
<logger name="org.springframework" level="INFO"/>
<logger name="org.mybatis" level="INFO"/>
<root level="INFO" includeLocation="true">
<appender-ref ref="Console"/>
<appender-ref ref="RollingFile"/>
<appender-ref ref="RollingErrorFile"/>
</root>
</loggers>
</configuration>

开始使用

在 Spring Boot 项目的启动类上面添加 @MapperScan("tk.mybatis.simple.mapper") 注解,指定 Mapper 接口所在的包路径,启动类如下:

@SpringBootApplication
@EnableTransactionManagement
@MapperScan("tk.mybatis.simple.mapper")
public class Application {
public static void main(String[] args){
SpringApplication.run(Application.class, args);
}
}

然后在 classpath 下的 mapper 文件夹(根据 application.yml 配置文件中的定义)添加 XML 映射文件,即可开始使用 MyBatis了

其中 @EnableTransactionManagement 注解表示开启事务的支持(@SpringBootApplication 注解在加载容器的时候已经开启事务管理的功能了,也可不需要添加该注解)

在需要事务的方法或者类上面添加 @Transactional 注解即可,引入spring-boot-starter-jdbc依赖,注入的是 DataSourceTransactionManager 事务管理器,事务的使用示例如下:

@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
public int insertFeedback(UserFeedbackInfo requestAddParam) {
try {
// ... 业务逻辑
} catch (Exception e) {
// 事务回滚
TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
return 0;
}
}

4.SpringBoot配置数据库密码加密?

4.1 借助Druid数据源

Druid 数据源支持数据库密码进行加密,在 Spring Boot 中配置方式如下:

加密数据库密码,通过 Druid 的 com.alibaba.druid.filter.config.ConfigTools 工具类对数据库密码进行加密(RSA 算法),如下:

public static void main(String[] args) throws Exception {
ConfigTools.main(new String[]{"you_password"});
}

或者执行以下命令:

java -cp druid-1.0.16.jar com.alibaba.druid.filter.config.ConfigTools you_password

输出:

privateKey:MIIBVgIBADANBgkqhkiG9w0BAQEFAASCAUAwggE8AgEAAkEA6+4avFnQKP+O7bu5YnxWoOZjv3no4aFV558HTPDoXs6EGD0HP7RzzhGPOKmpLQ1BbA5viSht+aDdaxXp6SvtMQIDAQABAkAeQt4fBo4SlCTrDUcMANLDtIlax/I87oqsONOg5M2JS0jNSbZuAXDv7/YEGEtMKuIESBZh7pvVG8FV531/fyOZAiEA+POkE+QwVbUfGyeugR6IGvnt4yeOwkC3bUoATScsN98CIQDynBXC8YngDNwZ62QPX+ONpqCel6g8NO9VKC+ETaS87wIhAKRouxZL38PqfqV/WlZ5ZGd0YS9gA360IK8zbOmHEkO/AiEAsES3iuvzQNYXFL3x9Tm2GzT1fkSx9wx+12BbJcVD7AECIQCD3Tv9S+AgRhQoNcuaSDNluVrL/B/wOmJRLqaOVJLQGg==
publicKey:MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBAOvuGrxZ0Cj/ju27uWJ8VqDmY7956OGhVeefB0zw6F7OhBg9Bz+0c84RjzipqS0NQWwOb4kobfmg3WsV6ekr7TECAwEAAQ==
password:PNak4Yui0+2Ft6JSoKBsgNPl+A033rdLhFw+L0np1o+HDRrCo9VkCuiiXviEMYwUgpHZUFxb2FpE0YmSguuRww==

然后在 application.yml 中添加以下配置:

spring:
datasource:
druid:
password: ${password} # 加密后的数据库密码
filters: config # 配置 ConfigFilter ,通过它进行解密
# 提示需要对数据库密码进行解密
connection-properties: 'config.decrypt=true;config.decrypt.key=${publickey}'
publicKey: MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBAJvQUB7pExzbzTpaQCCY5qS+86MgYWvRpqPUCzjFwdMgrBjERE5X5oojSe48IGZ6UtCCeaI0PdhkFoNaJednaqMCAwEAAQ==

这样就OK了,主要是在 ConfigFilter 过滤器中,会先对密码进行解密,然后再设置到 DataSource 数据源

4.2 借助Jasypt加密包

Jasypt是一个 Java 库,可以让开发人员将基本的加密功能添加到项目中,而无需对加密的工作原理有深入的了解

接下来讲述的在 Spring Boot 项目中如何使用Jasypt,其他使用方法请参考Jasypt Github地址

引入依赖

<!-- jasypt 加密工具,https://github.com/ulisesbocchio/jasypt-spring-boot -->
<dependency>
<groupId>com.github.ulisesbocchio</groupId>
<artifactId>jasypt-spring-boot-starter</artifactId>
<version>3.0.3</version>
</dependency>

添加注解

在启动类上面添加@EnableEncryptableProperties注解,使整个 Spring 环境启用 Jasypt 加密功能,如下:

@SpringBootApplication
@EnableEncryptableProperties
public class Application {
public static void main(String[] args){
SpringApplication.run(Application.class, args);
}
}

获取密文

需要通过 Jasypt 官方提供的 jar 包进行加密,如下:

import com.ulisesbocchio.jasyptspringboot.properties.JasyptEncryptorConfigurationProperties;
import org.jasypt.encryption.pbe.PooledPBEStringEncryptor;
import org.jasypt.encryption.pbe.config.PBEConfig;
import org.jasypt.encryption.pbe.config.SimpleStringPBEConfig; /**
* @author jingping.liu
* @date 2020-11-20
* @description Jasypt 安全框架加密类工具包
*/
public class JasyptUtils { /**
* 生成一个 {@link PBEConfig} 配置对象
* <p>
* 注意!!!
* 可查看 Jasypt 全局配置对象 {@link JasyptEncryptorConfigurationProperties} 中的默认值
* 这里的配置建议与默认值保持一致,否则需要在 application.yml 中定义这里的配置(也可以通过 JVM 参数的方法)
* 注意 password 和 algorithm 配置项,如果不一致在启动时可能会解密失败而报错
*
* @param salt 盐值
* @return SimpleStringPBEConfig 加密配置
*/
private static SimpleStringPBEConfig generatePBEConfig(String salt) {
SimpleStringPBEConfig config = new SimpleStringPBEConfig();
// 设置 salt 盐值
config.setPassword(salt);
// 设置要创建的加密程序池的大小,这里仅临时创建一个,设置 1 即可
config.setPoolSize("1");
// 设置加密算法, 此算法必须由 JCE 提供程序支持,默认值 PBEWITHHMACSHA512ANDAES_256
config.setAlgorithm("PBEWithMD5AndDES");
// 设置应用于获取加密密钥的哈希迭代次数
config.setKeyObtentionIterations("1000");
// 设置要请求加密算法的安全提供程序的名称
config.setProviderName("SunJCE");
// 设置 salt 盐的生成器
config.setSaltGeneratorClassName("org.jasypt.salt.RandomSaltGenerator");
// 设置 IV 生成器
config.setIvGeneratorClassName("org.jasypt.iv.RandomIvGenerator");
// 设置字符串输出的编码形式,支持 base64 和 hexadecimal
config.setStringOutputType("base64");
return config;
} /**
* 通过 {@link PooledPBEStringEncryptor} 进行加密密
*
* @param salt 盐值
* @param message 需要加密的内容
* @return 加密后的内容
*/
public static String encrypt(String salt, String message) {
PooledPBEStringEncryptor encryptor = new PooledPBEStringEncryptor();
SimpleStringPBEConfig pbeConfig = generatePBEConfig(salt);
// 生成加密配置
encryptor.setConfig(pbeConfig);
System.out.println("----ARGUMENTS-------------------");
System.out.println("message: " + message);
System.out.println("salt: " + pbeConfig.getPassword());
System.out.println("algorithm: " + pbeConfig.getAlgorithm());
System.out.println("stringOutputType: " + pbeConfig.getStringOutputType());
// 进行加密
String cipherText = encryptor.encrypt(message);
System.out.println("----OUTPUT-------------------");
System.out.println(cipherText);
return cipherText;
} public static String decrypt(String salt, String message) {
PooledPBEStringEncryptor encryptor = new PooledPBEStringEncryptor();
// 设置解密配置
encryptor.setConfig(generatePBEConfig(salt));
// 进行解密
return encryptor.decrypt(message);
} public static void main(String[] args) {
// 随机生成一个 salt 盐值
String salt = UUID.randomUUID().toString().replace("-", "");
// 进行加密
encrypt(salt, "message");
}
}

如何使用

直接在 application.yml 配置文件中添加 Jasypt 配置和生成的密文

jasypt:
encryptor:
password: salt # salt 盐值,需要和加密时使用的 salt 一致
algorithm: PBEWithMD5AndDES # 加密算法,需要和加密时使用的算法一致
string-output-type: hexadecimal # 密文格式,,需要和加密时使用的输出格式一致
spring:
datasource:
druid:
username: root
password: ENC(cipherText) # Jasypt 密文格式:ENC(密文)

salt 盐值也可以通过 JVM 参数进行设置,例如:-Djasypt.encryptor.password=salt

启动后,Jasypt 会先根据配置将 ENC(密文) 进行解密,然后设置到 Spring 环境中

后续会继续添加如何实现动态数据源的相关内容

MyBatis 使用手册的更多相关文章

  1. MyBatis 开发手册

    这一遍看Mybatis的原因是怀念一下去年的 10月24号我写自己第一个项目时使用全配置文件版本的MyBatis,那时我们三个人刚刚大二,说实话,当时还是觉得MyBatis挺难玩的,但是今年再看最新版 ...

  2. MyBatis极速入门开发手册(2017-2-6更新)

    前言: 本篇文章对我的学习内容做一个归纳梳理,同时也记录一些学习过程中遇上的问题及注意事项等等,可以帮助新入门的朋友们消除一些误区与盲区,希望能帮上一些正在学习的朋友们.在编写时会引用一些mybati ...

  3. MyBatis的几种批量操作

    MyBatis中批量插入 方法一: <insert id="insertbatch" parameterType="java.util.List"> ...

  4. 161102、MyBatis中批量插入

    方法一: <insert id="insertbatch" parameterType="java.util.List"> <selectKe ...

  5. Mybatis第一天(其他)

    Mybatis第一天 框架课程 课程计划 第一天: Mybatis的介绍 Mybatis的入门 使用jdbc操作数据库存在的问题 Mybatis的架构 Mybatis的入门程序 Dao的开发方法 原始 ...

  6. MyBatis的关于批量数据操作的测试

    摘录自:http://www.linuxidc.com/Linux/2012-05/60863.htm MyBatis的前身就是著名的Ibatis,不知何故脱离了Apache改名为MyBatis.My ...

  7. MyBatis 查询映射自定义枚举

    背景                  MyBatis查询若想映射枚举类型,则需要从 EnumTypeHandler 或者 EnumOrdinalTypeHandler 中选一个来使用         ...

  8. JAVAEE——Mybatis第一天:入门、jdbc存在的问题、架构介绍、入门程序、Dao的开发方法、接口的动态代理方式、SqlMapConfig.xml文件说明

    1. 学习计划 第一天: 1.Mybatis的介绍 2.Mybatis的入门 a) 使用jdbc操作数据库存在的问题 b) Mybatis的架构 c) Mybatis的入门程序 3.Dao的开发方法 ...

  9. Mybatis学习笔记之一(环境搭建和入门案例介绍)

    一.Mybatis概述 1.1 Mybatis介绍 MyBatis 本是apache的一个开源项目iBatis, 2010年这个项目由apache software foundation 迁移到了go ...

随机推荐

  1. go 结构体与方法

    go 结构体与方法   go 结构体相当于 python 中类的概念,结构体用来定义复杂的数据结构,存储很多相同的字段属性 结构体的定义 1.结构体的定义以及简单实用 package main imp ...

  2. 第五章 NFS、rsync等统一用户相关操作

    一.统一用户 1.httpd2.NFS挂载目录3.rsync 1.所有服务器统一创建用户 [root@web01 ~]# groupadd www -g 666[root@web01 ~]# user ...

  3. 第十二章 Linux三剑客之老三—grep

    一.Linux grep 命令用于查找文件里符合条件的字符串. Linux系统中的grep命令是一种功能强大的文本搜索工具,它能使用正则表达式搜索文本,并把匹配的行打印出来.grep全称是Global ...

  4. 优化Mysql数据库的8个方法

    通过8个方法优化Mysql数据库:创建索引.复核索引.索引不会包含含有NULL值的列.使用短索引.排序的索引问题.like语句操作.不要在列上进行运算.不使用NOT  IN 和<>操作 1 ...

  5. APP脱壳方法三

    第一步 手机启动frida服务 第二步 手机打开要脱壳的app 第三步编辑hook代码 agent.js /* * Author: hluwa <hluwa888@gmail.com> * ...

  6. Helium文档10-WebUI自动化-Text识别网页上的任何文本或标签

    前言 Text关键字的作用是识别网页上的文字,在一般UI查找中使用率非常高,但是需要注意,如果网页上有相同的文字,那么只能识别到第一个 入参介绍 以下是Text的源码 有5个如参:后面4个参数是上下左 ...

  7. Helium文档8-WebUI自动化-wait_until等待元素出现

    前言 wait_until等待某个条件为真才继续往下执行.默认的超时时间为10s,每0.5查询一次,这俩参数选填.可以设置超时时间和轮询间隔. 可以作为添加后校验元素是否存在的场景 入参介绍 def ...

  8. tp5伪静态--宝塔

    location / { if (!-e $request_filename) { rewrite ^(.*)$ /index.php?s=$1 last; break; } }

  9. Sublime Text:性感无比的代码编辑器安装破解配置教程

    代码编辑器或者文本编辑器,对于程序员来说,就像剑与战士一样,谁都想拥有一把可以随心驾驭且锋利无比的宝剑,而每一位程序员,同样会去追求最适合自己的强大.灵活的编辑器,相信你和我一样,都不会例外. 我用过 ...

  10. BP神经网络算法程序实现鸢尾花(iris)数据集分类

    作者有话说 最近学习了一下BP神经网络,写篇随笔记录一下得到的一些结果和代码,该随笔会比较简略,对一些简单的细节不加以说明. 目录 BP算法简要推导 应用实例 PYTHON代码 BP算法简要推导 该部 ...