【MyBatis框架】MyBatis入门程序第二部分

我们通过写一个简单的MyBatis小项目来在实战中学习MyBatis,接着上一篇继续

我们开始实现需求中的添加和删除用户功能

(1)向数据库中添加用户数据

使用User.xml,加入添加用户的sql语句。

[html] view
plain
 copy

  1. <!-- 添加用户
  2. parameterType:指定输入参数类型是pojo(包括用户信息)
  3. #{}中指定POJO的属性名,接收到POJO对象的属性值,mybatis通过OGNL获取对象的属性
  4. -->
  5. <insert id="insertUser" parameterType="cn.edu.hpu.mybatis.PO.User">
  6. insert into user(username,birthday,sex,address) value(#{username}.#{birthday,jdbcType=DATE}.#{sex},#{address})
  7. </insert>

*注:在字段中有Date和DateTime类型,在插入数据时只要将实体的属性设置成Timestamp就会对应mysql的DateTime类型,Date会对应mysql的Date类型:

#{modified_date,jdbcType=TIMESTAMP}、#{date,jdbcType=DATE}。

测试方法:

[java] view
plain
 copy

  1. //添加用户
  2. @Test
  3. public void insertUserTest(){
  4. //mybatis配置文件
  5. String resource="SqlMapConfig.xml";
  6. //将配置文件加载成流
  7. InputStream inputStream;
  8. try {
  9. inputStream = Resources.getResourceAsStream(resource);
  10. //创建会话工厂,传入mybatis配置文件的信息
  11. SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
  12. //通过工厂得到sqlSession
  13. sqlSession=sqlSessionFactory.openSession();
  14. //插入用户对象
  15. User user=new User();
  16. user.setUsername("李云华");
  17. user.setBirthday(new Date());
  18. user.setSex("男");
  19. user.setAddress("云南大理");
  20. //通过SqlSession操作数据库
  21. //第一个参数:映射文件中的statement的Id,等于=namespace+"."+statement的Id
  22. //第二个参数:指定和映射文件所匹配的parameterType类型的参数
  23. //sqlSession.selectOne最终结果与你映射文件中所匹配的resultType类型
  24. sqlSession.insert("test.insertUser",user);
  25. //提交事务
  26. sqlSession.commit();
  27. } catch (IOException e) {
  28. e.printStackTrace();
  29. }finally{
  30. //释放资源
  31. sqlSession.close();
  32. }
  33. }

测试结果:

在数据库中插入了

李云华(String), 2015-06-07(Date), 男(String), 云南大理(String)

输出的日志信息:

[plain] view
plain
 copy

  1. DEBUG [main] - Logging initialized using ‘class org.apache.ibatis.logging.slf4j.Slf4jImpl‘ adapter.
  2. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  3. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  4. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  5. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  6. DEBUG [main] - Opening JDBC Connection
  7. DEBUG [main] - Created connection 30685694.
  8. DEBUG [main] - Setting autocommit to false on JDBC Connection [[email protected]]
  9. DEBUG [main] - ==>  Preparing: insert into user(username,birthday,sex,address) value(?,?,?,?)
  10. DEBUG [main] - ==> Parameters: 李云华(String), 2015-06-07(Date), 男(String), 云南大理(String)
  11. DEBUG [main] - <==    Updates: 1
  12. DEBUG [main] - Committing JDBC Connection [[email protected]]
  13. DEBUG [main] - Resetting autocommit to true on JDBC Connection [[email protected]]
  14. DEBUG [main] - Closing JDBC Connection [[email protected]]
  15. DEBUG [main] - Returned connection 30685694 to pool.

(2)主键返回

a.自增主键的返回

mysql的自增主键,执行insert之前自动生成一个自增主键

通过mysql函数获取到刚插入记录的自增主键

LAST_INSERT_ID

(当插入一个数据后,立即用这个函数就会返回刚加的主键:SELECT LAST_INSERT_ID())

在刚刚的User.xml中这么写:

  1. <!-- 添加用户
  2. parameterType:指定输入参数类型是pojo(包括用户信息)
  3. #{}中指定POJO的属性名,接收到POJO对象的属性值,mybatis通过OGNL获取对象的属性
  4. -->
  5. <insert id="insertUser" parameterType="cn.edu.hpu.mybatis.PO.User">
  6. <!-- 将插入数据的主键返回,返回到user对象中。
  7. SELECT_INSERT_ID():得到刚insert进去的主键值,只适用于自增主键
  8. KeyProperty:将查询到主键值设置到parameterType指定对象的哪个属性。
  9. order:SELECT LAST_INSERT_ID()执行顺序,相对于insert语句来说它的执行顺序
  10. -->
  11. <selectKey keyProperty="id" order="AFTER" resultType="java.lang.Integer">
  12. SELECT LAST_INSERT_ID()
  13. </selectKey>
  14. insert into user(username,birthday,sex,address) value(#{username},#{birthday,jdbcType=DATE},#{sex},#{address})
  15. </insert>

我们在刚刚的方法后面输出user的ID

[java] view
plain
 copy

  1. //插入用户对象
  2. User user=new User();
  3. user.setUsername("李云华");
  4. user.setBirthday(new Date());
  5. user.setSex("男");
  6. user.setAddress("云南大理");
  7. //通过SqlSession操作数据库
  8. //第一个参数:映射文件中的statement的Id,等于=namespace+"."+statement的Id
  9. //第二个参数:指定和映射文件所匹配的parameterType类型的参数
  10. //sqlSession.selectOne最终结果与你映射文件中所匹配的resultType类型
  11. sqlSession.insert("test.insertUser",user);
  12. //提交事务
  13. sqlSession.commit();
  14. System.out.println(user.getId());

结果:6

为啥能得到,就是在配置文件里设置了当insert完成之后就把id取出来存到user对象中

b.非自增主键的返回

使用mysql的uuid()函数生成主键,需要修改表中id字段类型为string,长度设置成35位。

执行思路:

先通过uuid()查询到主键,将主键输入到sql语句中。

执行uuid()语句顺序相对于insert语句之前执行。

在刚刚的User.xml中这么写:

  1. <!-- 使用MySql的UUID来生成主键
  2. 执行过程:
  3. 首先通过uuid()得到主键,将主键设置到user对象的id属性中
  4. 其次在insert执行时,从user对象中取出id属性值 -->
  5. <selectKey keyProperty="id" order="BEFORE" resultType="java.lang.String">
  6. SELECT uuid()
  7. </selectKey>
  8. insert into user(id,birthday,sex,address) value(#{id},#{birthday,jdbcType=DATE},#{sex},#{address})
  9. 如果使用的数据库是oracle那么通过oracle的序列生成主键写法:
  10. <selectKey keyProperty="id" order="BEFORE" resultType="java.lang.String">
  11. SELECT 序列名.nextval()
  12. </selectKey>
  13. insert into user(id,username,birthday,sex,address) value(#{id},#{username},#{birthday,jdbcType=DATE},#{sex},#{address})

测试略

(3)删除和更新用户

映射文件User.xml中添加的语句:

[html] view
plain
 copy

  1. <!-- 删除用户 -->
  2. <delete id="deleteUser" parameterType="java.lang.Integer">
  3. delete from user where id=#{id}
  4. </delete>
  5. <!-- 更新用户
  6. 分析:
  7. 需要传入用户的id,需要传入用户的更新信息.
  8. parameterType指定user对象,包括id和更新信息(注意:id必须存在)
  9. #{id}:从输入user对象中获取id属性值-->
  10. <update id="updateUser" parameterType="cn.edu.hpu.mybatis.PO.User">
  11. update user set username=#{username},birthday=#{birthday,jdbcType=DATE},sex=#{sex},address=#{address}
  12. where id=#{id}
  13. </update>

测试代码:

删除测试代码:

  1. //删除用户
  2. @Test
  3. public void deleteUserTest(){
  4. //mybatis配置文件
  5. String resource="SqlMapConfig.xml";
  6. //将配置文件加载成流
  7. InputStream inputStream;
  8. try {
  9. inputStream = Resources.getResourceAsStream(resource);
  10. //创建会话工厂,传入mybatis配置文件的信息
  11. SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
  12. //通过工厂得到sqlSession
  13. sqlSession=sqlSessionFactory.openSession();
  14. //传入id删除用户
  15. sqlSession.delete("test.deleteUser",6);
  16. //提交事务
  17. sqlSession.commit();
  18. } catch (IOException e) {
  19. e.printStackTrace();
  20. }finally{
  21. //释放资源
  22. sqlSession.close();
  23. }
  24. }

测试结果:从数据库删除了id为6的数据

输出日志:

  1. DEBUG [main] - Logging initialized using ‘class org.apache.ibatis.logging.slf4j.Slf4jImpl‘ adapter.
  2. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  3. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  4. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  5. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  6. DEBUG [main] - Opening JDBC Connection
  7. DEBUG [main] - Created connection 30685694.
  8. DEBUG [main] - Setting autocommit to false on JDBC Connection [[email protected]]
  9. DEBUG [main] - ==>  Preparing: delete from user where id=?
  10. DEBUG [main] - ==> Parameters: 6(Integer)
  11. DEBUG [main] - <==    Updates: 1
  12. DEBUG [main] - Committing JDBC Connection [[email protected]]
  13. DEBUG [main] - Resetting autocommit to true on JDBC Connection [[email protected]]
  14. DEBUG [main] - Closing JDBC Connection [[email protected]]
  15. DEBUG [main] - Returned connection 30685694 to pool.

更新测试代码:

[java] view
plain
 copy

  1. //更新用户
  2. @Test
  3. public void updateUserTest(){
  4. //mybatis配置文件
  5. String resource="SqlMapConfig.xml";
  6. //将配置文件加载成流
  7. InputStream inputStream;
  8. try {
  9. inputStream = Resources.getResourceAsStream(resource);
  10. //创建会话工厂,传入mybatis配置文件的信息
  11. SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
  12. //通过工厂得到sqlSession
  13. sqlSession=sqlSessionFactory.openSession();
  14. //更新用户信息(更改id=5的用户数据)
  15. User user=new User();
  16. user.setId(5);
  17. user.setUsername("刘三姐");
  18. user.setBirthday(new Date());
  19. user.setSex("女");
  20. user.setAddress("云南大理");
  21. sqlSession.update("test.updateUser",user);
  22. //提交事务
  23. sqlSession.commit();
  24. } catch (IOException e) {
  25. e.printStackTrace();
  26. }finally{
  27. //释放资源
  28. sqlSession.close();
  29. }
  30. }

测试结果:

id=5的数据被更新

输出日志:

[plain] view
plain
 copy

  1. DEBUG [main] - Logging initialized using ‘class org.apache.ibatis.logging.slf4j.Slf4jImpl‘ adapter.
  2. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  3. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  4. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  5. DEBUG [main] - PooledDataSource forcefully closed/removed all connections.
  6. DEBUG [main] - Opening JDBC Connection
  7. DEBUG [main] - Created connection 30685694.
  8. DEBUG [main] - Setting autocommit to false on JDBC Connection [[email protected]]
  9. DEBUG [main] - ==>  Preparing: update user set username=?,birthday=?,sex=?,address=? where id=?
  10. DEBUG [main] - ==> Parameters: 刘三姐(String), 2015-06-07(Date), 女(String), 云南大理(String), 5(Integer)
  11. DEBUG [main] - <==    Updates: 1
  12. DEBUG [main] - Committing JDBC Connection [[email protected]]
  13. DEBUG [main] - Resetting autocommit to true on JDBC Connection [[email protected]]
  14. DEBUG [main] - Closing JDBC Connection [[email protected]]
  15. DEBUG [main] - Returned connection 30685694 to pool.

小结:

a.parameterType

在映射文件中通过parameterType指定输入 参数的类型。

b.resultType

在映射文件中通过resultType指定输出结果的类型。

c.#{}和${}

#{}表示一个占位符号,#{}接收输入参数,类型可以是简单类型,pojo、hashmap。

如果接收简单类型,#{}中可以写成value或其它名称。

#{}接收pojo对象值,通过OGNL读取对象中的属性值,通过属性.属性.属性...的方式获取对象属性值。

${}表示一个拼接符号,会引用sql注入,所以不建议使用${}。

${}接收输入参数,类型可以是简单类型,pojo、hashmap。

如果接收简单类型,${}中只能写成value。

${}接收pojo对象值,通过OGNL读取对象中的属性值,通过属性.属性.属性...的方式获取对象属性值。

d.selectOne和selectList

selectOne表示查询出一条记录进行映射。如果使用selectOne可以实现使用selectList也可以实现(list中只有一个对象)。

selectList表示查询出一个列表(多条记录)进行映射。如果使用selectList查询多条记录,不能使用selectOne。

如果使用selectOne报错:

org.apache.ibatis.exceptions.TooManyResultsException: Expected one result (or null) to be returned by selectOne(), but found: 4

最后来说说hibernate与mybatis,大家如果用过hibernate,刚学mybatis就会很疑惑,mybatis的执行效率并不比hibernate高多少,而且还要多写sql语句,为什么要用它呢?下面来看一下它们的区别,你就会明白mybatis的存在是有一定道理的

看看mybatis和hibernate本质区别和应用场景:

hibernate:是一个标准ORM框架(对象关系映射)。入门门槛较高的,不需要程序写sql,sql语句自动生成了。

对sql语句进行优化、修改比较困难的。

应用场景:

适用与需求变化不多的中小型项目,比如:后台管理系统,erp、orm、oa。。

mybatis:专注是sql本身,需要程序员自己编写sql语句,sql修改、优化比较方便。mybatis是一个不完全 的ORM框架,虽然程序员自己写sql,mybatis 也可以实现映射(输入映射、输出映射)。

应用场景:

适用与需求变化较多的项目,比如:互联网项目。

企业进行技术选型,以低成本 高回报作为技术选型的原则,根据项目组的技术力量进行选择。

时间: 2024-10-20 01:18:29

【MyBatis框架】MyBatis入门程序第二部分的相关文章

myBatis框架之入门(一)

什么是框架 框架就是一个架子,表演节目,舞台已经搭建好,表演什么节目,看自己的需求了. 框架是一个半成品,对于Java语言来说,框架就是封装了别人的代码.在框架的基础上我们在进一步开发,拿来主义. 框架解决什么问题 解决的是技术整合问题.软件开发环境和规模都很大,不可能任何一个项目的代码都从零开始,此时就需要一个非常优秀的框架把基础技术整合完毕,我们在他的基础上进一步开发.提高性能,易扩展,易维护,最终提高整个团队的开发效率. 什么时候使用框架 企业级大型项目开发,避免大炮打蚊子. 怎么使用框架

Mybatis(一)Mybatis简介与入门程序

Mybatis简介: MyBatis是一个优秀的持久层框架,它对jdbc的操作数据库的过程进行封装,使开发者只需要关注 SQL 本身,而不需要花费精力去处理例如注册驱动.创建connection.创建statement.手动设置参数.结果集检索等jdbc繁杂的过程代码. Mybatis通过xml或注解的方式将要执行的各种statement(statement.preparedStatemnt.CallableStatement)配置起来,并通过java对象和statement中的sql进行映射生

IDEA工具下Mybaties框架快速入门程序

本篇文章介绍在IDEA工具下mybatis快速入门程序分为以下五步 ? 1 添加依赖包 ? 2 编写pojo对象 ? 3 编写映射文件 ? 4 编写核心配置文件 ? 5 测试框架 详细如下 建立Module后 ? 1 添加依赖包   在pox.xml 添加   代码如下 <properties> <maven.coppiler.source>1.9</maven.coppiler.source> <maven.coppiler.target>1.9</

mybatis框架(入门方法,dao层原始开发方法,mapper代理开发)(sqlserver数据库)

1.入门方法 第一步:mybatis全局环境配置  configurs.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">

MyBatis框架——mybatis插入数据返回主键(mysql、oracle)

向数据库中插入数据时,大多数情况都会使用自增列或者UUID做为主键.主键的值都是插入之前无法知道的,但很多情况下我们在插入数据后需要使用刚刚插入数据的主键,比如向两张关联表A.B中插入数据(A的主键是B的外键),向A表中插入数据之后,向B表中插入数据时需要用到A的主键. 比如添加一个用户,同时返回插入用户后得到的用户id: /** * 添加用户信息 * @param user * @throws Exception */ public int insertUser(User user) thro

MyBatis 介绍、简单入门程序

JDBC 编程中的问题 1. 将 SQL 语句硬编码到 Java 代码.不利于系统维护. 设想怎样解决:将SQL单独抽取出来,在配置文件(xml方式.properties文件)进行配置. 2. 数据库连接不能反复利用,对数据库资源是一中浪费. 设想怎样解决:使用数据库连接池管理数据库连接. 3. 向 Statement 设置參数时,对于參数的位置通过硬编码指定,不利于系统维护. 设想怎样解决:是否可以自己主动将 Java 对象的值设置到 Statement. 4. 遍历结果集.resultSet

Mybatis框架01

概述 MyBadis是一个优秀的基于Java的持久层框架,内部封装了Jdbc,使开发者只需要关注SQL语句本身,而不需要花费精力去处理加载驱动.创建连接.创建statement等繁杂的过程. Mybatis通过xml或注解的方式将要执行的各种statement配置起来,并通过Java对象和statement中SQL的动态参数进行映射生成最终执行的SQL,最后由mybatis框架执行SQL并将结果映射为Java对象并返回. 采用ORM思想解决了实体和数据库映射的问题,对Jdbc进行了封装,屏蔽了J

Mybatis框架(一)初识Mybatis框架

一. 什么是框架框架(Framework)就是一个提供了可重用的公共结构的半成品,是应用程序的骨架.它就好比建筑物的骨架,结构统一固定,不需要考虑建筑物结构怎么设计,只需要考虑在这样的结构基础上,使用什么内容(建筑材料)来填充这个建筑物.对应到程序上也是一样的道理,程序结构固定,只需填充满足功能的相关代码即可.那么使用框架有什么优势呢?1. 保证了程序结构风格统一,便于学习和维护.2. 省去了结构设计,可以专心于业务逻辑的开发.3. 框架集中了前人的经验,使初学者能够写出结构优美,高质量的程序.

Mybatis框架(9)---Mybatis自定义插件生成雪花ID做为表主键项目

Mybatis自定义插件生成雪花ID做为主键项目 先附上项目项目GitHub地址 spring-boot-mybatis-interceptor 有关Mybatis雪花ID主键插件前面写了两篇博客作为该项目落地的铺垫. 1.Mybatis框架---Mybatis插件原理 2.java算法---静态内部类实现雪花算法 该插件项目可以直接运用于实际开发中,作为分布式数据库表主键ID使用. 一.项目概述 1.项目背景 在生成表主键ID时,我们可以考虑主键自增 或者 UUID,但它们都有很明显的缺点 主