Mybatis入门功法第一式

mybatis简介

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

工作原理:

  1. 加载配置

    Mybatis将sql映射加载成为一个个的MappedStatement对象(包括传入参数的映射配置,执行的sql语句,结果映射配置),将其存储在内存中

  2. SQL解析

    当API接口层收到调用请求时,会接收到传入的SQL的ID和传入的参数对象(可以是Map,实体类或者基本数据类型)mybatis会根据sql的ID找到对应的MappedStatement,然后根据传入的参数对象对MappedStatement进行解析,解析之后得到最终执行的sql语句和参数

  3. SQL执行

    将最终得到的sql语句和参数拿到数据库进行执行,得到执行结果

  4. 结果映射

    扫描二维码关注公众号,回复: 11931629 查看本文章

    将操作数据库的结果按照结果映射配置进行转换,可以转换为map,实体类或者基本数据类型,将转换的结果返回

SqlSessionFactoryBuider

​ 此组件根据Mybaits主配置文件构建SqlSessionFactory

SqlSessionFactory

​ 每一个mybatis应用程序都以一个SqlSessionFactory为核心,此组件负责常见SqlSession对象

SqlSession

​ 此组件包含所有执行的sql语句操作的方法,用于执行已经映射的sql语句

Mybatis配置文件

SqlMapConfig.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">
		<environment id="development">
			<transactionManager type="JDBC" />
			<dataSource type="POOLED">
				<property name="driver" value="com.mysql.jdbc.Driver" />
				<property name="url"
					value="jdbc:mysql://localhost:3306/jektong?useUnicode=true&amp;characterEncoding=utf-8" />
				<property name="username" value="jektong" />
				<property name="password" value="123456" />
			</dataSource>
		</environment>
	</environments>
</configuration>

SqlMapper.xml

映射文件,用于配置sql语句的映射信息

<?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">
<mapper namespace="">
</mapper>

Mybatis基本操作

搭建mybatis环境

为工程添加mybatis依赖包,在src下添加mybatis的主配置文件SqlMapConfig.xml,指定数据库连接参数和框架参数利用Mybatis提供API,获取SqlSession对象

获取SqlSession对象

String path = "主配置文件URL";
Reader reader = Resources.getResourceAsReader(path);

构建SqlSessionFactory对象

SqlSessionFactoryBuilder ssfb = new SqlSessionFactoryBuilder();
SqlSessionFactory ssf = ssfb.buld(reader);
SqlSession ss = ssf.openSession();

利用SqlSession实现CRUD操作

根据数据表编写实体类,编写SqlMapper.xml映射文件,定义SQL操作和映射信息

获取SqlSeesion对象,执行增删改查操作,提交事务,释放SqlSession对象资源

MybatisUtil.java

package com.jektong.util;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import com.jektong.entity.Emp;
/**
 * @author jektong
 * @Date 2020-10-12 11:24:12
 */
public class MybatisUtil {
    
    

	public static SqlSessionFactory ssf;

    // 构建SqlSessionFactory对象
	static {
    
    
		SqlSessionFactoryBuilder ssfb = new SqlSessionFactoryBuilder();
		ssf = ssfb.build(MybatisUtil.class.getClassLoader().getResourceAsStream("SqlMapConfig.xml"));
	}
	// 获取sqlsession(默认数据库事务不是自动提交)
	public static SqlSession getSession() {
    
    
		return ssf.openSession();
	}
	// 获取sqlsession(手动设置事务是否自动提交)
	// isAutoCommit=true 自动提交 false自动提交
	public static SqlSession getSession(boolean isAutoCommit) {
    
    
		return ssf.openSession(isAutoCommit);
	}
	public static void main(String[] args) {
    
    
		System.out.println(MybatisUtil.getSession());
	}
}

Eclipse中用mybatis实现CRUD

sql:

SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;
-- ----------------------------
-- Table structure for t_emp
-- ----------------------------
DROP TABLE IF EXISTS `t_emp`;![在这里插入图片描述](https://img-blog.csdnimg.cn/20201012171207854.JPG?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzQxODU3OTU1,size_16,color_FFFFFF,t_70#pic_center)

CREATE TABLE `t_emp`  (
  `e_id` int(4) NOT NULL AUTO_INCREMENT,
  `e_name` varchar(10) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  `e_salary` double(7, 2) NULL DEFAULT NULL,
  `e_bonus` double(5, 2) NULL DEFAULT NULL,
  `e_hiredate` date NULL DEFAULT NULL,
  `e_deptno` int(2) NULL DEFAULT NULL,
  PRIMARY KEY (`e_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1016 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Compact;
SET FOREIGN_KEY_CHECKS = 1;

结构:
在这里插入图片描述

EmpDao.java

package com.jektong.dao;
import java.util.List;
import org.apache.ibatis.session.SqlSession;
import com.jektong.entity.Emp;
import com.jektong.util.MybatisUtil;
/**
 * @author jektong
 * @Date 2020-10-12 11:22:45
 */
public class EmpDao {
    
    
	SqlSession ss = null;

    // 查询所有
	public List<Emp> findAll() {
    
    
		ss = MybatisUtil.getSession();
		List<Emp> emps = ss.selectList("com.jektong.dao.EmpDao.findAll");
		ss.close();
		return emps;
	}
    // 根据id查找
	public Emp findById(int id) {
    
    
		ss = MybatisUtil.getSession();
		Emp emp = ss.selectOne("com.jektong.dao.EmpDao.findById", id);
        ss.close();
		return emp;
	}
    // 添加
	public void save(Emp emp) {
    
    
		try {
    
    
			ss = MybatisUtil.getSession();
			ss.insert("com.jektong.dao.EmpDao.save", emp);
			ss.commit();
		} catch (Exception e) {
    
    
			ss.rollback();
		} finally {
    
    
			ss.close();
		}
	}
    // 修改
	public void updateEmp(Emp emp) {
    
    
		ss = MybatisUtil.getSession(true);
		ss.update("com.jektong.dao.EmpDao.updateEmp", emp);
		ss.close();
	}
    // 删除
	public void deleteById(int id) {
    
    
		ss = MybatisUtil.getSession(true);
		ss.delete("com.jektong.dao.EmpDao.deleteById", id);
		ss.close();
	}
}

EmpMapper.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="com.jektong.dao.EmpDao">
	<!-- 
		namespace: 所映射的类
		id: 一般与方法名一致
 		resultType: 返回类型
		parameterType: 参数类型
    -->
    <!-- 查询所有 -->
	<select id="findAll" resultType="com.jektong.entity.Emp">
		select * from t_emp
	</select>

	<!-- id查询单个对象 -->
	<select id="findById" resultType="com.jektong.entity.Emp"
		parameterType="java.lang.Integer">
		select * from t_emp where e_id = #{e_id};
	</select>

	<!-- 添加员工 -->
	<insert id="save" parameterType="com.jektong.entity.Emp">
		insert into t_emp
		values(#{e_id}, #{e_name}, #{e_salary}, #{e_bonus},
		#{e_hiredate},#{e_deptno} )
	</insert>

    <!-- 修改 -->
	<update id="updateEmp" parameterType="com.jektong.entity.Emp">
		update t_emp set
		e_name=#{e_name},
		e_salary=#{e_salary},
		e_bonus=#{e_bonus},
		e_hiredate=#{e_hiredate},
		e_deptno = #{e_deptno}
		where e_id=#{e_id}
	</update>
	
    <!--删除-->
	<delete id="deleteById" parameterType="java.lang.Integer">
		delete from t_emp where e_id = #{e_id}
	</delete>
</mapper>

在mybatis配置文件中关联映射:

<!-- 关联映射文件 -->
<mappers>
	<mapper resource="com/jektong/mapper/EmpMapper.xml"/>
</mappers>
</configuration>

测试:

package com.jektong.test;
import java.sql.Date;
import java.util.List;
import org.junit.Test;
import com.jektong.dao.EmpDao;
import com.jektong.entity.Emp;
/**
 * @author jektong
 * @Date 2020-10-12 14:05:25
 */
public class OneTest {
    
    

	@Test
	public void t1() {
    
    
		EmpDao empDao = new EmpDao();
		List<Emp> emps = empDao.findAll();
		for (Emp emp : emps) {
    
    
			System.out.println(emp.getE_name() + ":" + emp.getE_salary());
		}
	}
	@Test
	public void t2() {
    
    
		EmpDao empDao = new EmpDao();
		System.out.println(empDao.findById(1001).getE_name());
	}
	@Test
	public void t3() {
    
    
		EmpDao empDao = new EmpDao();
		Emp emp = new Emp();
		emp.setE_name("张三丰");
		emp.setE_hiredate(new Date(System.currentTimeMillis()));
		empDao.save(emp);
	}
	@Test
	public void t4() {
    
    
		EmpDao empDao = new EmpDao();
		Emp emp = new Emp();
		emp.setE_id(1015);
		emp.setE_name("张三丰2");
		empDao.updateEmp(emp);
	}
	@Test
	public void t5() {
    
    
		EmpDao empDao = new EmpDao();
		empDao.deleteById(1014);
	}
}

注意:解决字段名与实体属性名不一致问题

不一致问题,如果结果集的字段名实体类的属性名不一致,并且在结果映射时定义为resultType,则不会创建实体类对象,但是如果只是部分不一致,则会创建实体对象并且自动关联属性名和字段名一致的属性

解决方式

  1. 结果集的字段名实体类的属性名全部保持一致
  2. 取列别名
  3. 通过resulrMap来进行映射
<resultMap id="empMap" type="com.jektong.entity.Emp">
		<!-- 主键字段 -->
		<id property="e_id" column="e_id" jdbcType="INTEGER"/>
		<!-- 非主键字段 -->
		<result property="e_name" column="e_name" jdbcType="VARCHAR"/>
		<result property="e_salary" column="e_salary" jdbcType="DOUBLE"/>
		<result property="e_bonus" column="e_bonus" jdbcType="DOUBLE"/>
		<result property="e_hiredate" column="e_hiredate" jdbcType="DATE"/>
		<result property="e_deptno" column="e_deptno" jdbcType="INTEGER"/>
	</resultMap>
	<!-- 查询所有 -->
	<select id="findAll" resultType="com.jektong.entity.Emp" resultMap="empMap">
		select * from t_emp
	</select>

猜你喜欢

转载自blog.csdn.net/qq_41857955/article/details/109030292
今日推荐