目录
1、Mybatis简介
MyBatis 是一款优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)为数据库中的记录。
官网–https://mybatis.org/mybatis-3/zh/index.html
1、持久层框架,可自定义 SQL、存储过程以及高级映射(ORM对象关系映射),其实说白了就是映射对象要与数据库中的表以及映射对象属性和表字段。
2、几乎免除所有的 JDBC 代码和设置参数和获取结果集繁琐的操作。
常规JDBC代码如下,
private static void method2() throws Exception{
//1,注册驱动
Class.forName("com.mysql.jdbc.Driver");
//2,获取数据库的连接
//数据传输协议 数据库的ip 端口号 数据库名
String url = "jdbc:mysql://localhost:3306/rgb222";
Connection con = DriverManager.getConnection(url,"root","root");
//3,获取传输器
Statement statement = con .createStatement();
//4,利用传输器执行 增删改的SQL
//executeUpdate()用来执行增删改的SQL,只返回影响行数
int rows = statement.executeUpdate(
"INSERT INTO emp(ename,job) VALUES('rose','美女')");
//5,释放资源
//r.close();//结果集
statement.close();//传输器
con.close();//连接
}
优点:
操作数据库最快的方式就是JDBC. 协议 TCP(一种面向连接的、可靠的、 基于IP的传输层协议)
弊端:
1、 无论如何都必须获取数据库链接,链接池 c3p0 druid HK链接池
2、操作sql语句时,步骤繁琐,且资源必须手动关闭.(学过JDBC的应该都知道)
使用mybatis框架后,直接不用写繁琐JDBC了,因为mybatis已经封装了JDBC,就很棒,现在直接通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO,但是JDBC直接嵌入在项目中,他操作数据库的速度是最快的,相当于没有中间商赚差价。
3、由来:MyBatis 本是apache的一个开源项目iBatis, 然后在2010年由apache software foundation 迁移到了google code,然后就改名为MyBatis了。
1-1、mybatis的特性
1、它没有没有第三方依赖,只要下载两个jar文件和配置几个sql映射文件即可,sql和代码的分离,提高了可维护性。
2、在*.xml里编写动态sql,来满足操作数据库的所有需求,统一管理并优化。
3、提供对象关系映射标签,支持对象关系组建维护
4、提供映射标签,支持对象与数据库的orm字段关系映射
5、解除sql与程序代码的耦合:通过提供DAO层(dao是和数据交互的),将业务逻辑和数据访问逻辑分离,这样设计的会更清晰,也易维护,单元测试也会更简单。
补充说明:
1、持久化:计算机在计算时,数据都是在内存中运行,只要断电数据也会清空,因此要求需要将内存数据保存在磁盘中去,这样断电也不怕了
2、持久层:是指程序通过Dao与数据交互的层级代码的具体操作(层级代码:Controller层、Service层,除了Dao层,也有开发人员用Mapper层,两个是同样的东西比如我就比较喜欢用Mapper)
总结:mybatis是持久层框架,采用ORM思想去实现以对象的方式操作数据了,但是它只完成了结果集映射,sql还是得需要自己写的。
2、Mybatis案例
1、新建一个module,把上一个demo中的pom里的依赖先复制过来
2、然后把mybatis的两个依赖也同样复制进去
<!--mybatis依赖包-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.2.0</version>
</dependency>
<!--jdbc依赖包-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
3、完整的pom文件如下:
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.gt</groupId>
<artifactId>springboot_mybatis_demo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>springboot_mybatis_demo</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<spring-boot.version>2.4.1</spring-boot.version>
</properties>
<dependencies>
<!--mybatis依赖包-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.2.0</version>
</dependency>
<!--jdbc依赖包-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!--插件lombok 动态的生成set/get/构造方法 -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.8.1</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
<encoding>UTF-8</encoding>
</configuration>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>2.4.1</version>
<configuration>
<mainClass>com.gt.SpringbootMybatisDemoApplication</mainClass>
</configuration>
<executions>
<execution>
<id>repackage</id>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
4、同样的在新建的项目里,创建pojo包以及Demo_User类,
Demo_User类的代码如下:
package com.gt.pojo;
import com.sun.jmx.snmp.SnmpInt;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;
import java.io.Serializable;
@Data
@NoArgsConstructor
@AllArgsConstructor
@Accessors(chain = true)
public class Demo_User implements Serializable {
private Integer id;
private String name;
private Integer age;
private String sex;
}
5、前面总结中说过ORM思想,现在用*.xml文件来配置
在xml文件中粘贴下面的xml配置信息,这种配置信息在官网直接复制就行,只需简单的修改就OK了,不用自己写
<?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>
<!--环境配置标签 默认加载的环境有且只能写一个-->
<environments default="development">
<!--编辑开发环境 id是加载环境的唯一标识符 加载环境的值和id的必须相同,否则加载不了-->
<environment id="development">
<!-- 利用jdbc来作为控制事务的事物管理器 -->
<transactionManager type="JDBC"/>
<!-- 数据源来自数据库连接池来整合数据 -->
<dataSource type="POOLED">
<!-- 数据库驱动 高版本的数据库必须要添加CJ,比如:com.mysql.cj.jdbc.Driver,我的是高版本5.8以上-->
<property name="driver" value="com.mysql.jdbc.Driver"/>
<!--链接路径 jdbc:mysql数据库服务器地址且表示本机:数据库端口3306/数据库名jt?时区配置;指定字符的编码;解码格式。 allowMultiQueries=true表示
1、可以在 sql 语句后携带分号,实现多语句执行
超时自动连接 2、可以执行批处理,同时发出多个 SQL 语句-->
<property name="url" value="jdbc:mysql://127.0.0.1:3306/jt?serverTimezone=GMT%2B8&useUnicode=true&characterEncoding=utf8&autoReconnect=true&allowMultiQueries=true"/>
<!-- 数据库用户名 root-->
<property name="username" value="root"/>
<!-- 数据库密码 root -->
<property name="password" value="root"/>
</dataSource>
</environment>
</environments>
</configuration>
2-1、创建Mapper持久层(也叫Dao层)
1、定义mapper接口
2、Demo_User_Mapepr接口中代码如下
package com.gt.mapper;
import com.gt.pojo.Demo_User;
import java.util.List;
/**
* mapper 持久层是用来交互数据的,所以用接口,降低了耦合度
* 思想:哪个用这个接口哪个实现这个接口
*
* 重点:mybatis是以xml文件去进行实现类的
*/
public interface Demo_User_Mapper {
//测试查询表数据
public List<Demo_User> findA();//把Demo_User类作为对象封装到list集合,方法名findA
}
3、创建mapper配置文件
然后创建一个Demo_UserMapper.xml映射文件
官网同样的也提供了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">
<!--namespace是mybatis映射文件的唯一标识,须与接口对应-->
<mapper namespace="org.mybatis.example.BlogMapper">
!--id 表示接口方法,resultType 结果集类型映射路径-->
<select id="selectBlog" resultType="Blog">
select * from Blog where id = #{id}
</select>
</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">
<!--namespace是mybatis映射文件的唯一标识,与接口一一对应,也就是要映射接口的路径,我的类是Demo_User_Mapper
,有同学如果和我不一样,那么写你自己就行-->
<mapper namespace="com.gt.mapper.Demo_User_Mapper"><!--特别提示;namespace的接口名字有且只有一个,不允许重复的-->
<!--id:绑定接口方法名即可,resultType:结果集类型映射路径-->
<select id="findA" resultType="com.gt.pojo.Demo_User">
select id,name ,age,sex from demo_user <!-- SQL的查询语句,并且mybatis规定SQL是不能加分号的 -->
</select>
</mapper>
4、再去mybatis.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>
<!--环境配置标签 默认加载的环境有且只能写一个-->
<environments default="development">
<!--编辑开发环境 id是加载环境的唯一标识符 加载环境的值和id的必须相同,否则加载不了-->
<environment id="development">
<!-- 利用jdbc来作为控制事务的事物管理器 -->
<transactionManager type="JDBC"/>
<!-- 数据源来自数据库连接池来整合数据 -->
<dataSource type="POOLED">
<!-- 数据库驱动 高版本的数据库必须要添加CJ,比如:com.mysql.cj.jdbc.Driver,我的是高版本5.8以上-->
<property name="driver" value="com.mysql.jdbc.Driver"/>
<!--链接路径 jdbc:mysql数据库服务器地址且表示本机:数据库端口3306/数据库名jt?时区配置;指定字符的编码;解码格式。 allowMultiQueries=true表示
1、可以在 sql 语句后携带分号,实现多语句执行
超时自动连接 2、可以执行批处理,同时发出多个 SQL 语句-->
<property name="url" value="jdbc:mysql://127.0.0.1:3306/jt?serverTimezone=GMT%2B8&useUnicode=true&characterEncoding=utf8&autoReconnect=true&allowMultiQueries=true"/>
<!-- 数据库用户名 root-->
<property name="username" value="root"/>
<!-- 数据库密码 root -->
<property name="password" value="root"/>
</dataSource>
</environment>
</environments>
<!-- 加载mapper映射文件,mybatis规定<mappers>标签必须放在这个位置,不能乱放
1、通过resource属性去绑定xml映射文件
-->
<mappers>
<mapper resource="mybatis_xml/mapper/Demo_UserMapper.xml"/>
</mappers>
</configuration>
2-2、从xml中构建SqlSessionFactory
SqlSessionFactory是创建SqlSession的工厂
SqlSessionFactory是MyBatis的关键对象,它是个单个数据库映射关系经过编译后的内存镜像.SqlSessionFactory对象的实例可以通过SqlSessionFactoryBuilder对象类获得,而SqlSessionFactoryBuilder则可以从XML配置文件或一个预先定制的Configuration的实例构建出SqlSessionFactory的实例.每一个MyBatis的应用程序都以一个SqlSessionFactory对象的实例为核心
SqlSessionFactoryBuilder是创建工厂的工人
从 XML 文件中构建 SqlSessionFactory 的实例非常简单,建议使用类路径下的资源文件进行配置。 但也可以使用任意的输入流(InputStream)实例,比如用文件路径字符串或 file:// URL 构造的输入流。MyBatis 包含一个名叫 Resources 的工具类,它包含一些实用方法,使得从类路径或其它位置加载资源文件更加容易。
总结:
1、它是单个数据库映射关系经过编译后的内存镜像,通过xml的路径去加载。
2、再通过io流获取加载资源,然后SqlSessionFactory对象的实例可以通过SqlSessionFactoryBuilder对象来构建
3、SqlSessionFactoryBuilder则可以通过XML配置文件构建出SqlSessionFactory的实例。
4、SqlSessionFactory是线程安全的
2-2-1、创建测试类
代码如下:
官网提供的代码(和我们项目接口,类是不一样的,下列代码只是个模板):
//指定要加载的xml配置文件路径
String resource = "org/mybatis/example/mybatis-config.xml";
//通过io流获取资源加载
InputStream inputStream = Resources.getResourceAsStream(resource);
//通过SqlSessionFactoryBuilder动态的生成SqlSessionFactory
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
//有了 SqlSessionFactory,顾名思义,我们可以从中获得 SqlSession 的实例
try (SqlSession session = sqlSessionFactory.openSession()) {
BlogMapper mapper = session.getMapper(BlogMapper.class);
Blog blog = mapper.selectBlog(101);
}
根据项目修改的代码如下
package com.gt;
import com.gt.mapper.Demo_User_Mapper;
import com.gt.pojo.Demo_User;
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 org.junit.jupiter.api.Test;
import java.io.IOException;
import java.io.InputStream;
import java.util.List;
public class MybatisTest {
//springboot 单独提供单元测试 @Test修饰符必须是public 并且不能有返回值
@Test
public void find() throws IOException {//抛出IO异常
//指定要加载的xml配置文件路径
String resource = "mybatis_xml/mybatis.xml";
//通过io流获取资源加载
InputStream inputStream = Resources.getResourceAsStream(resource);
//通过SqlSessionFactoryBuilder动态的生成SqlSessionFactory
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
//有了 SqlSessionFactory,我们可以从中获得 SqlSession 的实例,
//可以把SqlSession看成获取的是数据库链接
SqlSession session = sqlSessionFactory.openSession();
//获取Demo_User_Mapper接口
Demo_User_Mapper mapper = session.getMapper(Demo_User_Mapper.class);
//接口谁用谁实现
List<Demo_User> demo_users = mapper.findA();
//打印出数据
System.out.println(demo_users);
//关闭连接
session.close();
}
}
2-2-2、完成测试:
2-2-3、结果有如下
出现该结果,表示我们的xml配置文件,mapper映射文件,以及测试代码都没问题。