目录
本关任务:学习MyBatis框架的基础使用,通过MyBatis框架向MySQL数据库中插入和删除数据。
MyBatis的前身是 Apache 的开源项目iBatis。iBatis一词来源于internet和 abatis的组合,是一个基于Java的持久层框架。2010 年这个项目由Apache software foundation 迁移到 Google code,并更名为MyBatis。 2013 年 11 月, MyBatis源代码迁移到GitHub网站上,目前由GitHub提供维护。
MyBatis的优势在于灵活,它几乎可以代替JDBC,避免了几乎所有的JDBC代码和手动设置参数以及获取结果集。同时提供了接口编程。目前MyBatis的数据访问层 DAO (Data Access Objects))是不需要实现类的,它只需要一个接口和XML(或者注解)。MyBatis提供自动映射、动态SQL、级联、缓存、注解、代码和SQL分离等特性,使用方便,同时也可以对SQL进行优化。因为其具有封装少、映射多样化、支持存储过程、可以进行SQL优化等特点,使得它成为了国内Java 互联网中首选的持久框架。
MyBatis作为持久层框架,会涉及数据库。我们首先定义一个数据库表一一角色表(role),其结构如图示。

图1 角色表
根据这个角色表,我们可以定义一个POJO(Plan Ordinary Java Object),使它的字段和这张表定义的字段一一对应起来,如下面代码所示。
//对应数据库中表role的Role类public class Role{private Integer id;private String roleName;private String remark;/** setter and getter 方法忽略**/}
Mybatis和其他持久层框架都是依靠某种方法,将数据库的表和POJO映射起来的,这样我们就可以通过操作POJO 来完成相关的数据库操作逻辑,同时我们把POJO对象和数据库表相互映射的框架称为对象关系映射(Object Relational Mapping,ORM)框架。要将POJO和数据库映射起来需要给这些框架提供映射规则,所以下一步要提供映射的规则,如下图所示。

图2 映射规则
MyBatis支持XML和注解两种方式提供映射规则,这里采用XML方式。下面的XML配置文件指定了数据库表role和POJO对象Role对应起来的规则。
selectid, roleName, remarkfrom rolewhere id = #{id,jdbcType=INTEGER}update roleset roleName = #{roleName,jdbcType=VARCHAR},remark = #{remark,jdbcType=VARCHAR}where id = #{id,jdbcType=INTEGER}
这里resultMap元素用于定义映射规则,指定POJO中的属性和数据库表中的对应关系,而增、删、查、改对应着insert、delete、select、update四个元素。要注意的是,mapper元素中的namespace属性要和一个接口的全限定名保持一致,这里的接口是RoleMapper,而里面SQL元素的id要和接口定义的方法名完全保持一致,定义MyBatis映射文件RoleMapper,代码如下。
public interface RoleMapper {Role selectByPrimaryKey(Integer id);int updateByPrimaryKey(Role record);}
在selectByPrimaryKey中,我们传递的参数是Integer类型的id,这与 XML 文件中parameterType的值是对应起来的。把传递给selectByPrimaryKey的参数赋值给SQL语句,采用的方式是#{列名,列的数据类型},Mybatis框架会自动完成参数的赋值工作。
我们可以看到,定义的MyBatis映射文件是一个接口,那要不要创建一个接口的实现类呢?答案是不需要。定义了映射规则(XML文件)和映射文件(Java接口),接下来就可以完成对角色类的增、删、改和查,如下代码片段所示。
public class MybatisTest {public static void main(String[] args) {SqlSessionFactory sqlSessionFactory = null;SqlSession sqlSession = null;try {//mybatis-config.xml里指定所使用的MySQL地址和数据库信息Reader reader = Resources.getResourceAsReader("mybatis-config.xml");sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);sqlSession = sqlSessionFactory.openSession();// 上面代码是获取MyBatis操作数据库的session对象//操作数据库开始//先获取对应的RoleMapper对象RoleMapper roleMapper = sqlSession.getMapper(RoleMapper.class);//查询表role中id为1的记录Role role = roleMapper.selectByPrimaryKey(1);//输出查询结果System.out.println(role);} catch (Exception e) {e.printStackTrace();} finally {//关闭session对象,释放数据库连接if (null != sqlSession) {sqlSession.commit();sqlSession.close();}}}}
可以看到,在获取了表role对应的RoleMapper类的对象后,操作数据库就只需要调用RoleMapper的方法即可。
框架的相关依赖已经配置好,请根据提示,在右侧编辑器补充 Begin-End 区间代码,完成通过 MyBatis 对role表插入和删除功能。
RoleMapper.java中声明两个方法,插入数据的方法int insertRole(Role record)和通过主键id删除表role中记录的方法int deleteById(int id)。XML映射文件中补全insertRole和deleteById两个方法对应的映射规则。测试代码首先会调用insertRole方法插入数据,然后调用selectByPrimaryKey方法查询插入的数据,最后调用deleteById方法删除: 预期输出:
Role{id=1001, RoleName='RoleName1001', remark='remark1001'}测试通过
测试框架主要代码如下:
RoleMapper roleMapper = sqlSession.getMapper(RoleMapper.class);//定义一个role对象Role insertRole=new Role();insertRole.setId(1001);insertRole.setRoleName("RoleName1001");insertRole.setRemark("remark1001");//插入role对象roleMapper.insertRole(insertRole);//通过id查询,是否插入成功Role role = roleMapper.selectByPrimaryKey(1001);System.out.println(role);//删除操作roleMapper.deleteById(1001);//查询是否删除成功role = roleMapper.selectByPrimaryKey(1001);if(role==null){System.out.println("测试通过");}
RoleMapper.java
- package net.educoder.mapper;
-
- import net.educoder.pojo.Role;
-
- public interface RoleMapper {
- /********** Begin *********/
- //插入数据
- int insertRole(Role record);
- //通过id删除
- int deleteById(Integer id);
- /********** End *********/
-
- //查询
- Role selectByPrimaryKey(Integer id);
- //更新
- int updateByPrimaryKey(Role record);
-
- }
RoleMapper.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="net.educoder.mapper.RoleMapper">
- <resultMap id="BaseResultMap" type="net.educoder.pojo.Role">
- <id column="id" jdbcType="INTEGER" property="id" />
- <result column="roleName" jdbcType="VARCHAR" property="roleName" />
- <result column="remark" jdbcType="VARCHAR" property="remark" />
- </resultMap>
- <!--在Begin和End之间补充代码-->
- <!-- ********** Begin ********* -->
- <!--删除元素,id对应RoleMapper中的insertRole方法-->
- <insert id="insertRole" parameterType="net.educoder.pojo.Role">
- insert into role
- values (#{id,jdbcType=INTEGER},#{roleName,jdbcType=VARCHAR},#{remark,jdbcType=VARCHAR})
- </insert>
- <!--删除元素,id对应RoleMapper中的deleteById方法-->
- <delete id="deleteById" parameterType="java.lang.Integer">
- delete from role where id = #{id, jdbcType=INTEGER}
- </delete>
- <!-- ********** End ********* -->
- <!-- 通过select元素声明一个查询语句-->
- <select id="selectByPrimaryKey" parameterType="java.lang.Integer" resultMap="BaseResultMap">
- select
- id, roleName, remark
- from role
- where id = #{id,jdbcType=INTEGER}
- </select>
- <!-- 通过update元素声明一个更新语句-->
- <update id="updateByPrimaryKey" parameterType="net.educoder.pojo.Role">
- update role
- set roleName = #{roleName,jdbcType=VARCHAR},
- remark = #{remark,jdbcType=VARCHAR}
- where id = #{id,jdbcType=INTEGER}
- </update>
- </mapper>
