MyBatis
简介
- MyBatis是一种持久层框架,用于简化JDBC开发
- 持久层:将数据保存到数据库
- Java EE:表现层、业务层、持久层
- 框架是一个半成品软件。
- 在框架基础上构建软件编写更加高效、规范、通用、可扩展
- JDBC操作繁琐
MyBatis快速入门
创建user表、添加数据
创建模块、导入坐标
编写MyBatis核心配置文件
编写SQL映射文件
编码
-
安装
-
<dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>x.x.x</version> </dependency>
-
目前(2022年10月3日)版本最新为3.5.11
-
-
从XML文件中构建SqlSessionFactory
-
<environments default="development"> <environment id="development"> <transactionManager type="JDBC"/> <dataSource type="POOLED"> <!--数据库连接信息--> <property name="driver" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql:///127.0.0.1:3306"/> <property name="username" value="root"/> <property name="password" value="123456"/> </dataSource> </environment> <environment id="test"> <transactionManager type="JDBC"/> <dataSource type="POOLED"> <!--数据库连接信息--> <property name="driver" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql:///127.0.0.1:3306"/> <property name="username" value="root"/> <property name="password" value="123456"/> </dataSource> </environment> </environments>
-
-
sql映射
-
编码
-
public static void main(String[] args) throws IOException { //获取sqlsession factory String resource = "mybatis-config.xml"; InputStream inputStream = Resources.getResourceAsStream(resource); SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream); //获取sqlsession对象 SqlSession sqlSession = sqlSessionFactory.openSession(); UserMapper userMapper = sqlSession.getMapper(UserMapper.class); List<User> users= userMapper.selectAll(); System.out.println(users); //释放资源 sqlSession.close(); }
Mapper代理开发
-
目的
- 解决硬编码问题
- 简化后期sql
-
定义与sql映射文件同名的Mapper接口
-
package org.example; public interface UserMapper { }
-
-
设置SQL映射文件的namespace属性为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="UserMapper"> <select id="selectAll" resultType="org.example.User"> select * from tb_user; </select> </mapper>
-
-
在Mapper接口中定义方法。方法名是sql文件的id,保持参数和返回值类型一致
-
Type interface org.example.UserMapper is not known to the MapperRegistry.解决方案
-
将Mapper文件中的namespace进行更改,为包名+接口
-
<mapper namespace="org.example.UserMapper"> <select id="selectAll" resultType="org.example.User"> select * from tb_user; </select> </mapper>
-
-
<mappers> <!--Mapper代理方式--> <package name="org.example"> </mappers>
MyBatis配置文件
environments
-
配置多个环境信息
-
默认使用的环境 ID(比如:default=“development”)。
-
每个 environment 元素定义的环境 ID(比如:id=“development”)。
-
事务管理器的配置(比如:type=“JDBC”)。
-
数据源的配置(比如:type=“POOLED”)。
-
<environments default="development"> <environment id="development"> <transactionManager type="JDBC"> <property name="..." value="..."/> </transactionManager> <dataSource type="POOLED"> <property name="driver" value="${driver}"/> <property name="url" value="${url}"/> <property name="username" value="${username}"/> <property name="password" value="${password}"/> </dataSource> </environment> </environments>
别名
<typeAliases>
<package name="packagename"/>
</typeAliases>
识别包
MyBatis 会在包名下面搜索需要的 Java Bean.
<typeAliases>
<typeAlias alias="Author" type="domain.blog.Author"/>
<typeAlias alias="Blog" type="domain.blog.Blog"/>
<typeAlias alias="Comment" type="domain.blog.Comment"/>
<typeAlias alias="Post" type="domain.blog.Post"/>
<typeAlias alias="Section" type="domain.blog.Section"/>
<typeAlias alias="Tag" type="domain.blog.Tag"/>
</typeAliases>
MyBatisX插件
配置文件完成增删改查
查询
-
查询所有数据
-
编写接口方法:Mapper接口
-
package org.example; import pojo.Brand; import java.util.List; public interface BrandMapper { List<Brand> selectAll(); }
-
参数:无
-
返回:List<>
-
-
编写SQL语句
-
注意在这步mybatis中添加mappers配置
-
<?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="org.example.BrandMapper"> <select id="selectAll" resultType="pojo.Brand"> select * from tb_brand; </select> </mapper>
-
-
执行方法
-
public class MyBatisTest { @Test public void testAll() throws IOException { String resource = "mybatis-config.xml"; InputStream inputStream = Resources.getResourceAsStream(resource); SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream); //获取sqlsession对象 SqlSession sqlSession = sqlSessionFactory.openSession(); BrandMapper brandMapper = sqlSession.getMapper(BrandMapper.class); List<Brand> brands= brandMapper.selectAll(); System.out.println(brands); } }
-
sql字段
-
<sql id="brand_col"> id,brand_name as brandName,company_name as companyName,ordered,description,status </sql> <select id="selectAll" resultType="pojo.Brand"> select <include refid="brand_col"></include> from tb_brand; </select>
-
-
查看详情
-
也可以用resultMap进行映射
-
<resultMap id="resultBrand" type="pojo.Brand"> <result column="brand_name" property="brandName"/> <result column="company_name" property="companyName"/> </resultMap> <select id="selectAll" resultMap="resultBrand"> select * from tb_brand; </select>
-
根据参数查询
-
<select id="selectById" resultMap="resultBrand"> select * from tb_brand where id = #{id}; </select>
-
参数占位符
- **#{} **, 会将其替换为?。防止sql注入
- ${} 。直接拼接
-
-
多参数查询
-
List<Brand> selectByCondition(@Param("status")int status,@Param("companyName") String com,@Param("brandName") String brand);
-
通过封装对象传参
-
List<Brand> selectByCondition(Brand brand);
-
-
通过map集合
-
int status = 1; String brandName="%华为%"; String companyName = "%华为%"; Map map = new HashMap(); map.put("status",status); map.put("brandName",brandName); map.put("companyName",companyName);
-
-
-
动态sql
-
<if test="title != null"> AND title like #{title} </if>
-
<select id="findActiveBlogLike" resultType="Blog"> SELECT * FROM BLOG WHERE state = ‘ACTIVE’ <choose> <when test="title != null"> AND title like #{title} </when> <when test="author != null and author.name != null"> AND author_name like #{author.name} </when> <otherwise> AND featured = 1 </otherwise> </choose> </select> where:选择一个
-
<select id="findActiveBlogLike" resultType="Blog"> SELECT * FROM BLOG <where> <if test="state != null"> state = #{state} </if> <if test="title != null"> AND title like #{title} </if> <if test="author != null and author.name != null"> AND author_name like #{author.name} </if> </where> </select> where 元素只会在子元素返回任何内容的情况下才插入 “WHERE” 子句。而且,若子句的开头为 “AND” 或 “OR”,where 元素也会将它们去除。
-
<update id="updateAuthorIfNecessary"> update Author <set> <if test="username != null">username=#{username},</if> <if test="password != null">password=#{password},</if> <if test="email != null">email=#{email},</if> <if test="bio != null">bio=#{bio}</if> </set> where id=#{id} </update>
-
用于动态更新语句的类似解决方案叫做 set。set 元素可以用于动态包含需要更新的列,忽略其它不更新的列。
添加
void add(Brand brand);
-
<insert id="add"> insert into tb_brand(brand_name,company_name,ordered,description,status) values (#{brandName},#{companyName},#{ordered},#{description},#{status}); </insert>
-
MyBatis需要手动添加事务
-
-
sqlSession.commit();
提交事务
修改
<update id="updateById">
update tb_brand
set
company_name = #{companyName},
description = #{description}
where
id = #{id}
</update>
删除
void delById(int id);
-
<delete id="delById"> delete from tb_brand where id=#{id}; </delete>
-
批量删除
-
void deleteByIds(@Param("ids")int[] ids);
-
<delete id="deleteByIds"> delete from tb_brand where id in <foreach collection="ids" item = "id" open="(" close=")" separator=","> #{id} </foreach> ; </delete>
-
测试效果
-
-
如果接口中不写@Param,XML中
collection="array"
参数传递
-
aramNameResolver类
进行参数封装 -
POJO类型。属性名对应占位符
-
Map集合。属性名对应占位符
-
Collection。
-
List
-
Array
-
单个其他类型参数
-
多个参数
- MyBatis将多个参数封装为Map
map.put("arg0",参数值1)
,map.put("param1",参数值1)
map.put("arg1",参数值2)
,map.put("param2",参数值2)
- 可以使用默认的这个参数名字
- @Param(“key”) value
注解完成增删改查
@Select(" select *\n" +
" from tb_brand;")
List<Brand> selectAll();
@Select(" select *\n" +
" from tb_brand\n" +
" where id = #{i};")
Brand selectById(int id);
- 对于简单的需求,注解方便
- 但是不推荐复杂的sql语句