【MyBatis框架】Mybatis开发dao方法第二部分

简介:
下面来继续讨论mybatis开发Dao的方法

我们前面使用原始的Dao开发方法,发现了许多弊端,我们下面使用mapper代理来写Dao方法。

1.mapper代理方法(程序员只需要mapper接口(相当 于dao接口))

开发人员需要先编写Mapper接口(相当 于dao接口),需要遵循一些开发规范,mybatis可以自动生成mapper接口实现类代理对象。
package cn.edu.hpu.mybatis.mapper;

import cn.edu.hpu.mybatis.PO.User;

//用户管理的Dao接口
public interface UserMapper {
	
	//根据Id查询用户信息
	public User findUserById(int id) throws Exception;
	
	//添加用户信息
	public void insertUser(User user) throws Exception;
	
	//删除用户信息
	public void deleteUser(int id) throws Exception;
	
	//修改用户信息
	public void updateUser(User user) throws Exception;


	//根据姓名查找用户
	public List<User> findUserByUserName(String username) throws Exception;
}

开发人员还要编写mapper.xml映射文件

我们在src同文件夹下的config文件夹下创建mapper包,在包下创建UserMapper.xml文件,内容同之前写过的User.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命名空间,作用就是对sql进行分类化管理,理解sql隔离
注意:使用mapper代理方法开发,namespace有特殊重要的作用,就是对应的mapper接口地址 -->
<mapper namespace="cn.edu.hpu.mybatis.mapper.UserMapper">
	<!-- 在映射文件中配置很多sql语句 -->
	
	<!-- 需求:通过id查询用户表的记录 -->
	<!-- 通过select执行数据库查询,
	     id:标示映射文件中的sql,成为Statement的id 
	     将sql语句封装到mappedStatement对象中,所以将id称为statement的id,
	     
	     parameterType:指定输入参数的类型,
	     
	     #{}标示一个占位符,
	     
	     #{id}其中id表示接收输入参数的名称,如果输入参数是简单类型,那么#{}中的值可以任意(如value)。
	     
	     resultType:指定sql输出结果的映射的java对象类型,
	     select指定resultType表示将单条记录映射成java对象-->	
	<select id="findUserById" parameterType="int" resultType="cn.edu.hpu.mybatis.PO.User">
	  SELECT * FROM USER WHERE id=#{id}
	</select>
	
	<!-- ${}:表示拼接sql串,将接收到的参数内容不加任何修饰拼接在sql中。
		 使用${}拼接sql,引起sql注入。
		 ${}中只能使用value-->
	<select id="findUserByUserName" parameterType="java.lang.String" 
			resultType="cn.edu.hpu.mybatis.PO.User">
	   select * from user where username like '%${value}%' 
	</select>
	
	<!-- 添加用户
	parameterType:指定输入参数类型是pojo(包括用户信息) 
	#{}中指定POJO的属性名,接收到POJO对象的属性值,mybatis通过OGNL获取对象的属性
	-->
	<insert id="insertUser" parameterType="cn.edu.hpu.mybatis.PO.User">
		<!-- 将插入数据的主键返回,返回到user对象中。
		SELECT_INSERT_ID():得到刚insert进去的主键值,只适用于自增主键 
		KeyProperty:将查询到主键值设置到parameterType指定对象的哪个属性。
		order:SELECT LAST_INSERT_ID()执行顺序,相对于insert语句来说它的执行顺序
		-->
		<selectKey keyProperty="id" order="AFTER" resultType="java.lang.Integer">
			SELECT LAST_INSERT_ID()
		</selectKey>
		
		<!-- 使用MySql的UUID来生成主键
		执行过程:
		首先通过uuid()得到主键,将主键设置到user对象的id属性中
		其次在insert执行时,从user对象中取出id属性值 
		<selectKey keyProperty="id" order="BEFORE" resultType="java.lang.String">
			SELECT uuid()
		</selectKey>
		insert into user(id,birthday,sex,address) value(#{id},#{birthday,jdbcType=DATE},#{sex},#{address})-->
		
		insert into user(username,birthday,sex,address) value(#{username},#{birthday,jdbcType=DATE},#{sex},#{address})
	</insert>
	
	<!-- 删除用户 -->
	<delete id="deleteUser" parameterType="java.lang.Integer">
		delete from user where id=#{id}
	</delete>
	
	<!-- 更新用户 
	分析:
	需要传入用户的id,需要传入用户的更新信息.
	parameterType指定user对象,包括id和更新信息(注意:id必须存在)
	#{id}:从输入user对象中获取id属性值-->
	<update id="updateUser" parameterType="cn.edu.hpu.mybatis.PO.User">
		update user set username=#{username},birthday=#{birthday,jdbcType=DATE},sex=#{sex},address=#{address} 
		where id=#{id}
	</update>
</mapper>

别忘记在SqlMapConfig.xml中加载映射文件
<!-- 加载映射文件 -->
<mappers>
	<mapper resource="mapper/UserMapper.xml"/>
</mappers>

开发规范:
A、在mapper.xml中namespace等于mapper接口地址
!-- namespace命名空间,作用就是对sql进行分类化管理,理解sql隔离
注意:使用mapper代理方法开发,namespace有特殊重要的作用,就是对应的mapper接口地址 -->
<mapper namespace="cn.edu.hpu.mybatis.mapper.UserMapper">
......
</mapper>

B、mapper.java接口中的方法名和mapper.xml中statement的id一致
public findUserById()
对应
<select id="findUserByUsername" ...

C、mapper.java接口中的方法输入参数类型和mapper.xml中statement的parameterType指定的类型一致。
public findUserById(int id)
对应
<select id="findUserById" parameterType="int" 

D、mapper.java接口中的方法返回值类型和mapper.xml中statement的resultType指定的类型一致。
public User findUserById(int id)
对应
<select id="findUserById" parameterType="int" resultType="cn.edu.hpu.mybatis.PO.User">

遵循这些开发规范,mybatis可以自动生成mapper接口实现类代理对象。

总结:
以上开发规范主要是对下边的代码进行统一生成:
User user=sqlSession.selectOne("test.findUserById",id);
sqlSession.insert("test.insertUser",user);

mapper.java与mapper.xml互联互助

接下来我们直接根据接口来测试:
package cn.edu.hpu.mybatis.test;

import java.io.InputStream;

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.Before;
import org.junit.Test;


import cn.edu.hpu.mybatis.PO.User;
import cn.edu.hpu.mybatis.mapper.UserMapper;


public class UserMapperTest {


	private SqlSessionFactory sqlSessionFactory;
	
	//注解Before是在执行本类所有测试方法之前先调用这个方法
	@Before
	public void setup() throws Exception{
		//创建SqlSessionFactory
		String resource="SqlMapConfig.xml";
		
		//将配置文件加载成流
		InputStream inputStream = Resources.getResourceAsStream(resource);
		//创建会话工厂,传入mybatis配置文件的信息
		sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
	}
	
	@Test
	public void testFindUserById() throws Exception{
		
		SqlSession sqlSession=sqlSessionFactory.openSession();
		
		//创建UserMapper代理对象
		UserMapper userMapper=sqlSession.getMapper(UserMapper.class);
		
		//调用userMapper的方法
		User user=userMapper.findUserById(1);
		
		System.out.println(user.getUsername());
	}
}

测试testFindUserById()方法,结果:张三

输出日志信息:
DEBUG [main] - Logging initialized using 'class org.apache.ibatis.logging.slf4j.Slf4jImpl' adapter.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - Opening JDBC Connection
DEBUG [main] - Created connection 14069849.
DEBUG [main] - Setting autocommit to false on JDBC Connection [com.mysql.jdbc.Connection@d6b059]
DEBUG [main] - ==>  Preparing: SELECT * FROM USER WHERE id=? 
DEBUG [main] - ==> Parameters: 1(Integer)
DEBUG [main] - <==      Total: 1

这里我们使用mapper代理的方法,不需要方法的实现体就完成了查找方法,是不是很轻松?

其他增删改写的方法与上面差不多,但是,当我们实现利用姓名模糊查询的时候,返回的是List集合的数据,我们要注意:
2.一些问题总结
2.1代理对象内部调用selectOne或selectList

如果mapper方法返回单个pojo对象(非集合对象),代理对象内部通过selectOne查询数据库。

如果mapper方法返回集合对象,代理对象内部通过selectList查询数据库。

这些是MyBatis内部自动执行的,是不是很方便?我们可以测试一下是不是这样:
测试方法:
@Test
	public void testFindUserByUserName() throws Exception{
		
		SqlSession sqlSession=sqlSessionFactory.openSession();
		
		//创建UserMapper代理对象
		UserMapper userMapper=sqlSession.getMapper(UserMapper.class);
		
		//调用userMapper的方法
		List<User> users=userMapper.findUserByName("张三");
		
		for (int i = 0; i < users.size(); i++) {
			User user=(User)users.get(i);
			System.out.println(user.getId()+":"+user.getUsername());
		}
	}
测试结果:
1:张三
4:张三丰

输出日志:
DEBUG [main] - Logging initialized using 'class org.apache.ibatis.logging.slf4j.Slf4jImpl' adapter.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
DEBUG [main] - Opening JDBC Connection
DEBUG [main] - Created connection 1668655.
DEBUG [main] - Setting autocommit to false on JDBC Connection [com.mysql.jdbc.Connection@19762f]
DEBUG [main] - ==>  Preparing: select * from user where username like '%张三%' 
DEBUG [main] - ==> Parameters: 
DEBUG [main] - <==      Total: 2

测试成功,说明MyBatis内部确实是这么做的

我们发现,mapper接口中的参数好像只有一个,Mybatis内部好像也只能自动处理一个参数的mapper方法,那么mapper接口方法参数只能有一个是否影响系统开发?

问:mapper接口方法参数只能有一个,系统是否不利于扩展维护。

答:
系统 框架中,dao层的代码是被业务层公用的。
即使mapper接口只有一个参数,可以使用包装类型的pojo满足不同的业务方法的需求。

注意:持久层方法的参数可以包装类型、map。。。,service方法中建议不要使用包装类型(不利于业务层的可扩展)。


转载请注明出处:http://blog.csdn.net/acmman/article/details/46488843

相关文章
|
12天前
|
SQL Java 数据库连接
持久层框架MyBatisPlus
持久层框架MyBatisPlus
31 1
持久层框架MyBatisPlus
|
1月前
|
SQL Java 数据库连接
mybatis使用四:dao接口参数与mapper 接口中SQL的对应和对应方式的总结,MyBatis的parameterType传入参数类型
这篇文章是关于MyBatis中DAO接口参数与Mapper接口中SQL的对应关系,以及如何使用parameterType传入参数类型的详细总结。
30 10
|
1月前
|
前端开发 Java 数据库连接
表白墙/留言墙 —— 中级SpringBoot项目,MyBatis技术栈MySQL数据库开发,练手项目前后端开发(带完整源码) 全方位全步骤手把手教学
本文是一份全面的表白墙/留言墙项目教程,使用SpringBoot + MyBatis技术栈和MySQL数据库开发,涵盖了项目前后端开发、数据库配置、代码实现和运行的详细步骤。
43 0
表白墙/留言墙 —— 中级SpringBoot项目,MyBatis技术栈MySQL数据库开发,练手项目前后端开发(带完整源码) 全方位全步骤手把手教学
|
26天前
|
缓存 Cloud Native 安全
探索阿里巴巴新型ORM框架:超越MybatisPlus?
【10月更文挑战第9天】在Java开发领域,Mybatis及其增强工具MybatisPlus长期占据着ORM(对象关系映射)技术的主导地位。然而,随着技术的发展,阿里巴巴集团推出了一种新型ORM框架,旨在提供更高效、更简洁的开发体验。本文将对这一新型ORM框架进行探索,分析其特性,并与MybatisPlus进行比较。
28 0
|
2月前
|
Java 数据库连接 数据格式
【Java笔记+踩坑】Spring基础2——IOC,DI注解开发、整合Mybatis,Junit
IOC/DI配置管理DruidDataSource和properties、核心容器的创建、获取bean的方式、spring注解开发、注解开发管理第三方bean、Spring整合Mybatis和Junit
【Java笔记+踩坑】Spring基础2——IOC,DI注解开发、整合Mybatis,Junit
|
3月前
|
SQL Java 数据库连接
Spring Boot联手MyBatis,打造开发利器:从入门到精通,实战教程带你飞越编程高峰!
【8月更文挑战第29天】Spring Boot与MyBatis分别是Java快速开发和持久层框架的优秀代表。本文通过整合Spring Boot与MyBatis,展示了如何在项目中添加相关依赖、配置数据源及MyBatis,并通过实战示例介绍了实体类、Mapper接口及Controller的创建过程。通过本文,你将学会如何利用这两款工具提高开发效率,实现数据的增删查改等复杂操作,为实际项目开发提供有力支持。
174 0
|
3月前
|
SQL Java 数据库连接
【Java 第十三篇章】MyBatis 框架介绍
MyBatis 原名 iBATIS,2001 年由 Clinton Begin 创建,以其简易灵活著称。2010 年更名以重塑品牌形象。MyBatis 通过 SQL 映射文件将 SQL 语句与 Java 代码分离,支持编写原生 SQL 并与方法映射。具备对象关系映射功能,简化数据库记录处理。支持动态 SQL 构建,灵活应对不同查询条件。内置缓存机制,提升查询效率。相比全功能 ORM,MyBatis 提供更高 SQL 控制度和更好的维护性,并易于与 Spring 等框架集成,广泛应用于 Java 数据访问层。
38 0
|
1月前
|
Java 数据库连接 Maven
mybatis使用一:springboot整合mybatis、mybatis generator,使用逆向工程生成java代码。
这篇文章介绍了如何在Spring Boot项目中整合MyBatis和MyBatis Generator,使用逆向工程来自动生成Java代码,包括实体类、Mapper文件和Example文件,以提高开发效率。
107 2
mybatis使用一:springboot整合mybatis、mybatis generator,使用逆向工程生成java代码。
|
1月前
|
SQL JSON Java
mybatis使用三:springboot整合mybatis,使用PageHelper 进行分页操作,并整合swagger2。使用正规的开发模式:定义统一的数据返回格式和请求模块
这篇文章介绍了如何在Spring Boot项目中整合MyBatis和PageHelper进行分页操作,并且集成Swagger2来生成API文档,同时定义了统一的数据返回格式和请求模块。
54 1
mybatis使用三:springboot整合mybatis,使用PageHelper 进行分页操作,并整合swagger2。使用正规的开发模式:定义统一的数据返回格式和请求模块
|
1月前
|
前端开发 Java Apache
Springboot整合shiro,带你学会shiro,入门级别教程,由浅入深,完整代码案例,各位项目想加这个模块的人也可以看这个,又或者不会mybatis-plus的也可以看这个
本文详细讲解了如何整合Apache Shiro与Spring Boot项目,包括数据库准备、项目配置、实体类、Mapper、Service、Controller的创建和配置,以及Shiro的配置和使用。
295 1
Springboot整合shiro,带你学会shiro,入门级别教程,由浅入深,完整代码案例,各位项目想加这个模块的人也可以看这个,又或者不会mybatis-plus的也可以看这个