Mybatis从浅入深(IDEA版通俗易懂)

抱怨是一件最没意义的事情。如果实在难以忍受周围的环境,那就暗自努力练好本领,然后跳出那个圈子。你好,我是梦阳辰,快来和我一起学习吧!

 

引入

1.三层架构

界面层:和用户打交道的,接收用户的请求参数,显示处理结果的。(jsp , htnml , servlet)

业务逻辑层:接收了界面层传递的数据,计算逻辑,调用数据库,获取数据

数据访问层:就是访问数据库,执行对数据的查询,修改,删除等等的。
三层对应的包
界面层:controller包( servlet)

业务逻辑层:service包(xxxservice类)

数据访问层:dao包(xxxDao类)

三层中类的交互
用户使用界面层–>业务逻辑层—>数据访问层(持久层)–>数据库(mysql)

三层对应的处理框架
界面层—servlet—springmvc(框架)

业务逻辑层—service类–spring(框架)

数据访问层—dao类–mybatis (框架)

模版:
1、规定了好一些条款,内容-2.加入自己的东西
框架是一个模块

1.框架中定义好了一些功能。这些功能是可用的

2.可以加入项目中自己的功能,这些功能可以利用框架中写好的功能。
框架是一个软件,半成品的软件,定义好了一些基础功能,需要加入你的功能就是完整的。基础功能是可重复使用的,可升级的

框架特点:
1.框架一般不是全能的,不能做所有事情。

2.框架是针对某一个领域有效。特长在某一个方面,比如mybatis做数据库操作强,但是他不能做其它的。

3.框架是一个软件。

01.概述

使用JDBC的缺陷

1.代码比较多,开发效率低

2.需要关注 Connection ,Statement,ResultSet对象创建和销毁

3.对 ResultSet查询的结果,需要自己封装为List

4.重复的代码比较多些

5.业务代码和数据库的操作混在一起
框架是一个软件,半成品的软件,定义好了一些基础功能,需要加入你的功能就是完整的。基础功能是可重复使用的,可升级的
框架特点:

1.框架一般不是全能的,不能做所有事情

2.框架是针对某一个领域有效。特长在某一个方面,比如mybatis做数据库操作强,但是他不能做其它的。

3.框架是一个软件

什么是 MyBatis?
MyBatis是一款优秀的持久层框架。

它支持自定义 SQL、存储过程以及高级映射。MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。

mybatis框架
一个框架,早期叫做ibatis,代码在github.

mybatis是MyBatis sQL Mapper Framework for Java (sql映射框架)

1)sql mapper :sql映射
可以把数据库表中的一行数据映射为一个java对象。
一行数据可以看做是一个java对象。操作这个对象,就相当于操作表中的数据

2)Data Access 0bjects (DAOs) 数据访问,对数据库执行增删改查。

mybatis提供了哪些功能:
1.提供了创建connection能力tate不用你执行sqile"t人的约力

2.提供了执行sql语句的能力,不用你执行sql

3.提供了循环sql,把sql的结果转为java对象,list集合的能力

4 .提供了关闭资源的能力,不用你关闭conneqtion,statement,Resultset

开发人员做的是:提供sql语句

MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)为数据库中的记录。

MyBatis 本是apache的一个开源项目iBatis, 2010年这个项目由apache software foundation 迁移到了google code,并且改名为MyBatis 。

2013年11月迁移到Github。

总结:
mybatis是一个sql映射框架,提供的数据库的操作能力。增强的JDBC.
使用mybatis让开发人员集中精神写sql就可以了,不必关心connection ,statement,ResultSet的创建,销毁,sql的执行.

<!-- https://mvnrepository.com/artifact/org.mybatis/mybatis -->
<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis</artifactId>
    <version>3.5.6</version>
</dependency>

持久化

数据持久化
持久化就是将程序的数据在持久状态和瞬时状态转化的过程。

内存:断电即失。
数据库(jdbc),io文件持久化。

生活:冷藏。

为什么需要持久化?
有一些对象,不能让他丢失。
内存很贵。

持久层

Dao层,Serice层,Controller层…
完成持久化工作的代码块。

层界限十分明显。

为什么需要Mybatis?

帮助程序员将数据存入到数据库中。

方便

传统的JDBC代码太复杂了,简化。框架。自动化。

不用Mybatis也可以,更容易上手。技术没有高低之分。

特点:

简单易学:本身就很小且简单。没有任何第三方依赖,最简单安装只要两个jar文件+配置几个sql映射文件易于学习,易于使用,通过文档和源代码,可以比较完全的掌握它的设计思路和实现。

灵活:mybatis不会对应用程序或者数据库的现有设计强加任何影响。 sql写在xml里,便于统一管理和优化。通过sql语句可以满足操作数据库的所有需求。

解除sql与程序代码的耦合:通过提供DAO层,将业务逻辑和数据访问逻辑分离,使系统的设计更清晰,更易维护,更易单元测试。sql和代码的分离,提高了可维护性。

提供映射标签,支持对象与数据库的orm字段关系映射

提供对象关系映射标签,支持对象关系组建维护

提供xml标签,支持编写动态sql。

02.Mybatis快速入门

实现步骤:
1.新建表

SET FOREIGN_KEY_CHECKS=0;

-- ----------------------------
-- Table structure for `student`
-- ----------------------------
DROP TABLE IF EXISTS `student`;
CREATE TABLE `student` (
  `id` int(10) NOT NULL,
  `name` varchar(30) DEFAULT NULL,
  `tid` int(10) DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `fktid` (`tid`),
  CONSTRAINT `fktid` FOREIGN KEY (`tid`) REFERENCES `teacher` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of student
-- ----------------------------
INSERT INTO `student` VALUES ('1', '梦阳辰', '1');
INSERT INTO `student` VALUES ('2', '小红', '1');
INSERT INTO `student` VALUES ('3', '小张', '1');
INSERT INTO `student` VALUES ('4', '小李', '1');
INSERT INTO `student` VALUES ('5', '小王', '1');

-- ----------------------------
-- Table structure for `teacher`
-- ----------------------------
DROP TABLE IF EXISTS `teacher`;
CREATE TABLE `teacher` (
  `id` int(10) NOT NULL,
  `name` varchar(30) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of teacher
-- ----------------------------
INSERT INTO `teacher` VALUES ('1', '黄老师');

-- ----------------------------
-- Table structure for `user`
-- ----------------------------
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
  `id` int(20) NOT NULL AUTO_INCREMENT,
  `name` varchar(30) DEFAULT NULL COMMENT '用户名',
  `pwd` varchar(30) DEFAULT NULL COMMENT '密码',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of user
-- ----------------------------
INSERT INTO `user` VALUES ('1', '梦阳辰', '123456');
INSERT INTO `user` VALUES ('2', 'MengYangChen', '1234567');
INSERT INTO `user` VALUES ('3', 'meng', '123456');

2.加入maven的mybatis坐标, mysql驱动的坐标

3.创建实体类,student–保存表中的一行数据的

4.创建持久层的dao接口,定义操作数据库的方法

5.创建一个mybatis使用的配置文件
叫做sql映射文件:写sql语句的。一般一个表一个sql映射文件。这个文件是xml文件。

6.创建mybatis的主配置文件:
一个项目就一个主配置文件。
主配置文件提供了数据库的连接信息和sql映射文件的位置信息

7.创建使用mybatis类,
通过mybatis访问数据库
思路:
搭建环境–>导入Mybatis–>编写代码–>测试

1.搭建环境:
创建操作的数据库
数据库mybtis

IDEA新建maven项目

导入maven依赖

2.新建配置文件mybatis-config.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="${driver}"/>
        <property name="url" value="${url}"/>
        <property name="username" value="${username}"/>
        <property name="password" value="${password}"/>
      </dataSource>
    </environment>
  </environments>
  <mappers>
    <mapper resource="org/mybatis/example/BlogMapper.xml"/>
  </mappers>
</configuration>

在这里插入图片描述
在这里插入图片描述

新建Mybatis工具类

1.使用Mybatis获取sqlSessionFactory对象
从 XML 中构建 SqlSessionFactory

MyBatis 包含一个名叫 Resources 的工具类,它包含一些实用方法,使得从类路径或其它位置加载资源文件更加容易。

从 XML 文件中构建 SqlSessionFactory 的实例非常简单,建议使用类路径下的资源文件进行配置。

MyBatis 包含一个名叫 Resources 的工具类,它包含一些实用方法,使得从类路径或其它位置加载资源文件更加容易。

String resource = "mybatis-config.xml";

nputStream inputStream = Resources.getResourceAsStream(resource);

SqlSessionFactory sqlSessionFactory = new 
SqlSessionFactoryBuilder().build(inputStream);

2.从 SqlSessionFactory 中获取 SqlSession
既然有了 SqlSessionFactory,顾名思义,我们可以从中获得 SqlSession 的实例。SqlSession 提供了在数据库执行 SQL 命令所需的所有方法。你可以通过 SqlSession 实例来直接执行已映射的 SQL 语句。

//sqlSessionFactory  -->sqlSession
public class MybatisUtils {
    private static SqlSessionFactory sqlSessionFactory;
    static {
        try {
            //使用Mybatis获取sqlSessionFactory对象
            String resource = "mybatis-config.xml";
            InputStream inputStream = Resources.getResourceAsStream(resource);
            sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    /**
     * 从 SqlSessionFactory 中获取 SqlSession
     * @return SqlSession对象
     */
    public  static SqlSession getSqlSession(){
        /*SqlSession sqlSession = sqlSessionFactory.openSession();
        return sqlSession;*/

        return sqlSessionFactory.openSession();
    }
}

编写代码

1.实体类

//实体类(javaBean)
public class User {
    private int id;
    private String name;
    private String pwd;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getPwd() {
        return pwd;
    }

    public void setPwd(String pwd) {
        this.pwd = pwd;
    }
}

2.Dao/Mapper接口


public interface UserDao {
    List<User> selectUser();
}

3.接口实现类
由原来的UserDaolmp转变为一个Mapper配置文件。

以前的方式就是写一个类实现接口,再重写接口方法,在方法中获取数据库连接,执行sql语句。

在Mybatis中免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。

一个语句既可以通过 XML 定义,也可以通过注解定义。我们先看看 XML 定义语句的方式,事实上 MyBatis 提供的所有特性都可以利用基于 XML 的映射语言来实现,这使得 MyBatis 在过去的数年间得以流行。如果你用过旧版本的 MyBatis,你应该对这个概念比较熟悉。 但相比于之前的版本,新版本改进了许多 XML 的配置,后面我们会提到这些改进。这里给出一个基于 XML 映射语句的示例,它应该可以满足上个示例中 SqlSession 的调用。

<?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">

<!--绑定一个对应的Dao/Mapper接口-->
<!--以前是写一个类实现Dao接口,现在绑定即可-->
<mapper namespace="com.mengyangchen.dao.UserDao">

    <!--查询语句-->
    <!--id相对于以前的书写,表示重写的方法名(以前在方法中执行连接数据库等操作,现在不需要了,只需要执行sql-->
    <!--resultType返回结果-->
    <select id="selectUser" resultType="com.mengyangchen.pojo.User">
    select * from mybatis.user
    </select>

</mapper>

在这里插入图片描述
在这里插入图片描述

为了这个简单的例子,我们似乎写了不少配置,但其实并不多。在一个 XML 映射文件中,可以定义无数个映射语句,这样一来,XML 头部和文档类型声明部分就显得微不足道了。文档的其它部分很直白,容易理解。

测试

核心文件mybatis-config.xml需要注册mappers

 <!--每一个Mapper.XML都需要在Mybatis核心文件中注册-->
    <mappers>
        <mapper resource="com/MengYangChen/mapper/UserMapper.xml"/>
    </mappers>

测试中可能遇到的问题:
1.配置文件没有注册

2.绑定接口错误。

3.方法名不对。

4.返回类型不对。

5.Maven导出资源问题。

<!--在build中配置resources,来防止我们资源导出失败的问题-->
<build>
 <resources>
      <resource>
        <directory>src/main/resources</directory>
        <includes>
          <include>**/*.properties</include>
          <include>**/*.xml</include>
        </includes>
        <filtering>false</filtering>
      </resource>
      <resource>
        <directory>src/main/java</directory>
        <includes>
          <include>**/*.properties</include>
          <include>**/*.xml</include>
        </includes>
        <filtering>false</filtering>
      </resource>
    </resources>
</build>

写到这里终于把搞了我好久的问题解决了,错误:Error:(3.28)java:程序报org.apache.ibatis.io不存在…。

网上很多解决方案是使用idea自带的maven,说是idea2020.1版本的问题。

我的解决方案:
解决方法:试过mvn idea:moudle命令的方法,但还是没有用。最后没办法
只能将在github网址下的mybatis3.5.6的jar包导入到新建的文件夹lib中。
在这里插入图片描述
但还是报错:
在这里插入图片描述
解决办法,将mybatis-config.xml文件的配置信息true该为false
在这里插入图片描述
完美得到结果:
在这里插入图片描述

03.Mybatis实现增删改查

为了规范将接口名UserDao统一改为UserMapper。

注意增删改需要提交事务
代码:

/**
 * 接口操作user表
 */
public interface UserMapper {
    //查询student表的所有数据
    List<User> selectUser();

    //根据id查询用户
    User selectUserById(int id);

    //insert一个用户
    int insertUser(User user);

    //更新一个用户
    int updateUser(User user);

    //删除一个用户
    int deleteUser(int id);
}

<?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.mengyangchen.dao.UserMapper">
    <select id="selectUser" resultType="com.mengyangchen.pojo.User">
    select * from mybatis.user
  </select>

    <!--根据id查询用户-->
    <select id="selectUserById" parameterType="int" resultType="com.mengyangchen.pojo.User">
        select * from mybatis.user where id=#{id}
    </select>

    <!--插入数据-->
    <insert id="insertUser" parameterType="com.mengyangchen.pojo.User">
        insert into mybatis.user (id,name,pwd) values(#{id},#{name},#{pwd});
    </insert>

    <!--更新数据-->
    <update id="updateUser" parameterType="com.mengyangchen.pojo.User">
        update mybatis.user set name =#{name},pwd=#{pwd}  where id=#{id} ;
    </update>

    <!--删除一个用户-->
    <delete id="deleteUser" parameterType="int">
        delete from mybatis.user where id=#{id}
    </delete>
</mapper>

测试代码:

public class UserMapperTest {
    @Test
    public void test(){
        //1.获取SqlSession对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        //方式一:getMapper
        //2.执行sql,获取sql,面向接口编程,获取UserMapper接口(以前是实现接口的实现类,现在是配置文件)
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);
        List<User> userList = mapper.selectUser();


        /*String sqlId = "com.mengyangchen.dao.UserDao"+"."+"selectUser";
        List<User> userList = sqlSession.selectList(sqlId);*/
        for(User user:userList){
            System.out.println(user);
        }

        //3.关闭SqlSession
        sqlSession.close();
    }


    @Test
    public void selectUserById(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        User user = mapper.selectUserById(1);
        System.out.println(user);
        sqlSession.close();
    }

    @Test
    public void insertUser(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        int num = mapper.insertUser(new User(3,"MengYangChen","123456"));
        //提交事务
        if(num>0){
            System.out.println("插入成功!");
        }
        sqlSession.commit();
        sqlSession.close();
    }

    @Test
    public void updateUser(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        int num = mapper.updateUser(new User(3,"陈末","123456"));
        //提交事务
        if(num>0){
            System.out.println("更新成功!");
        }
        sqlSession.commit();
        sqlSession.close();
    }

    @Test
    public void deleteUser(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        int num = mapper.deleteUser(3);
        //提交事务
        if(num>0){
            System.out.println("删除成功!");
        }
        sqlSession.commit();
        sqlSession.close();
    }
}

使用Map

假设实体类,属性过多,我们可以考虑用Map.当然用实体类属性的set和get方法也是一样的。map可以放多个对象中的属性。

使用map,后面的值可以不和实体类属性相同,只需要和map的键相同即可。
例如:

int updateUser2(Map<String,Object>map);
<update id="updateUser2" parameterType="map">
update mybatis.user set pwd =#{passWord} where id =#{userId}
</update>
public void updateUser2(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        Map<String,Object>map = new HashMap<String,Object>();
        map.put("userId",2);
        map.put("passWord","1234567");
        int num = mapper.updateUser2(map);
        //提交事务
        if(num>0){
            System.out.println("更新成功!");
        }
        sqlSession.commit();
        sqlSession.close();
    }


Map传递参数,直接在sql中取出key即可。
对象传递参数,直接在sql中去对象的属性即可。

模糊查询

在sql拼接中使用通配符可以防止sql注入。

  //模糊查询
    List<User> selectUserLike(String value);
 <!--模糊查询-->
    <select id="selectUserLike" resultType="com.mengyangchen.pojo.User">
        select * from mybatis.user where name like "%"#{value}"%";
    </select>
/**
     * 模糊查询*/
    @Test
    public void selectUserLike(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        List<User> list  = new LinkedList<>();
        list = mapper.selectUserLike("梦");
        for (User list1:list) {
            System.out.println(list1);
        }
        sqlSession.close();
    }

也可以:

 <!--模糊查询-->
    <select id="selectUserLike" resultType="com.mengyangchen.pojo.User">
        select * from mybatis.user where name like #{value};
    </select>
/**
     * 模糊查询*/
    @Test
    public void selectUserLike(){
        //获取执行sql的对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);//获取接口
        List<User> list  = new LinkedList<>();
        list = mapper.selectUserLike("%梦%");
        for (User list1:list) {
            System.out.println(list1);
        }
        sqlSession.close();
    }

第二种方式可能存在sql注入。

04.XML配置解析

MyBatis 的配置文件包含了会深深影响 MyBatis 行为的设置和属性信息。
配置文档的顶层结构如下:

configuration(配置)
properties(属性)
settings(设置)
typeAliases(类型别名)
typeHandlers(类型处理器)
objectFactory(对象工厂)
plugins(插件)
environments(环境配置)
environment(环境变量)
transactionManager(事务管理器)
dataSource(数据源)
databaseIdProvider(数据库厂商标识)
mappers(映射器)

properties(属性)

编写一个配置文件

db.properties
driver=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/mybatis?
userSSL=false&useUnicode=true&characterEncoding=UTF-8
username=root
password=123456
核心配置文件中引入:
位置需在第一位
<?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>
<!--引入外部配置文件-->
    <properties resource="db.properties">
        <property name="username" value="root"/><!--一配置文件中为准-->
        <property name="password" value="123456"/>
    </properties>


    <environments default="development">
        <environment id="development">
            <!--事务管理-->
            <transactionManager type="JDBC"/>
            <dataSource type="POOLED">
                <property name="driver" value="${driver}"/><!--&amp是xml的转义字符(即为&)-->
                <property name="url" value="${url}"/>
                <property name="username" value="${username}"/>
                <property name="password" value="${password}"/>
            </dataSource>
        </environment>

    </environments>

    <!--每一个Mapper.XML都需要在Mybatis核心文件中注册-->
    <mappers>
        <mapper resource="com/mengyangchen/dao/UserMapper.xml"/>
    </mappers>

</configuration>

可以直接引入外部文件,并且可以在其中增加一些属性配置,如果两个文件中都对有同一属性的配置,优先使用外部配置文件中的配置。

设置(settings)

是 MyBatis 中极为重要的调整设置,它们会改变 MyBatis 的运行时行为。 下表描述了设置中各项设置的含义、默认值等。
https://mybatis.org/mybatis-3/zh/configuration.html#typeAliases

类型别名(typeAliases)

类型别名可为 Java 类型设置一个缩写名字。 它仅用于 XML 配置,意在降低冗余的全限定类名书写。例如:

<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>

当这样配置时,Blog 可以用在任何使用 domain.blog.Blog 的地方。
也可以指定一个包名,MyBatis 会在包名下面搜索需要的 Java Bean,比如:

<typeAliases>
  <package name="domain.blog"/>
</typeAliases>

每一个在包 domain.blog 中的 Java Bean,在没有注解的情况下,会使用 Bean 的首字母小写的非限定类名来作为它的别名。 比如 domain.blog.Author 的别名为 author;若有注解,则别名为其注解值。见下面的例子:

@Alias("author")
public class Author {
    ...
}

映射器(mappers)

我们需要告诉 MyBatis 到哪里去找到这些语句。 在自动查找资源方面,Java 并没有提供一个很好的解决方案,所以最好的办法是直接告诉 MyBatis 到哪里去找映射文件。 你可以使用相对于类路径的资源引用,或完全限定资源定位符(包括 file:/// 形式的 URL),或类名和包名等。例如:

<!-- 使用相对于类路径的资源引用 -->
<mappers>
  <mapper resource="org/mybatis/builder/AuthorMapper.xml"/>
  <mapper resource="org/mybatis/builder/BlogMapper.xml"/>
  <mapper resource="org/mybatis/builder/PostMapper.xml"/>
</mappers>
需要接口和它的Mapper配置文件同名,并在同一包下。
<!-- 使用映射器接口实现类的完全限定类名 -->
<mappers>
  <mapper class="org.mybatis.builder.AuthorMapper"/>
  <mapper class="org.mybatis.builder.BlogMapper"/>
  <mapper class="org.mybatis.builder.PostMapper"/>
</mappers>
需要接口和它的Mapper配置文件同名,并在同一包下。
<!-- 将包内的映射器接口实现全部注册为映射器 -->
<mappers>
  <package name="org.mybatis.builder"/>
</mappers>

05.生命周期和作用域

理解我们之前讨论过的不同作用域和生命周期类别是至关重要的,因为错误的使用会导致非常严重的并发问题。
在这里插入图片描述

SqlSessionFactoryBuilder
这个类可以被实例化、使用和丢弃,一旦创建了 SqlSessionFactory,就不再需要它了。 因此 SqlSessionFactoryBuilder 实例的最佳作用域是方法作用域(也就是局部方法变量)。 你可以重用 SqlSessionFactoryBuilder 来创建多个 SqlSessionFactory 实例,但最好还是不要一直保留着它,以保证所有的 XML 解析资源可以被释放给更重要的事情。

SqlSessionFactory
可以想象为数据库连接池

SqlSessionFactory 一旦被创建就应该在应用的运行期间一直存在,没有任何理由丢弃它或重新创建另一个实例。 使用 SqlSessionFactory 的最佳实践是在应用运行期间不要重复创建多次,多次重建 SqlSessionFactory 被视为一种代码“坏习惯”。因此 SqlSessionFactory 的最佳作用域是应用作用域。 有很多方法可以做到,最简单的就是使用单例模式或者静态单例模式。

SqlSession
每个线程都应该有它自己的 SqlSession 实例。SqlSession 的实例不是线程安全的,因此是不能被共享的,所以它的最佳的作用域是请求或方法作用域。 绝对不能将 SqlSession 实例的引用放在一个类的静态域,甚至一个类的实例变量也不行。 也绝不能将 SqlSession 实例的引用放在任何类型的托管作用域中,比如 Servlet 框架中的 HttpSession。 如果你现在正在使用一种 Web 框架,考虑将 SqlSession 放在一个和 HTTP 请求相似的作用域中。 换句话说,每次收到 HTTP 请求,就可以打开一个 SqlSession,返回一个响应后,就关闭它。 这个关闭操作很重要,为了确保每次都能执行关闭操作,你应该把这个关闭操作放到 finally 块中。 下面的示例就是一个确保 SqlSession 关闭的标准模式:

try (SqlSession session = sqlSessionFactory.openSession()) {
  // 你的应用逻辑代码
}

在这里插入图片描述

06.解决属性名和字段名不一致的问题

解决方法:
起别名,将sql语句的字段名取一个别名跟属性名相同。

方法二:

resultMap结果集映射
<!--结果集映射-->
<!--column数据库中的字段,property实体类中的属性-->
<resultMap id="userMap" type="User">
	<result column="pwd" property="password"/>
</resultMap>

<select id="selectUserById" resultMap="userMap">
	select * from mybatis.user where id=#{id}
</select>

ResultMap 的设计思想是,对简单的语句做到零配置,对于复杂一点的语句,只需要描述语句之间的关系就行了。

07.日志

日志工厂
如果一个数据库操作,出现了异常,我们需要排错。日志就是最好的助手。
曾经:sout,debug
现在:日志工厂
在这里插入图片描述
SLF4J |
LOG4J | (掌握)
LOG4J2 |
JDK_LOGGING | COMMONS_LOGGING |
STDOUT_LOGGING |(掌握)
NO_LOGGING
在Mybatis中具体使用哪一种日志实现,在设置中设定。
STDOUT_LOGGING标准日志输出,默认无配置.

 <settings>
        <setting name="logImpl" value="STDOUT_LOGGING"/>
    </settings>

加了日志工厂后:
在这里插入图片描述

LOG4J

什么是Log4j?

Log4j是Apache的一个开源项目,通过使用Log4j,我们可以控制日志信息输送的目的地是控制台、文件、GUI组件,甚至是套接口服务器、NT的事件记录器、UNIX Syslog守护进程等;

我们也可以控制每一条日志的输出格式;

通过定义每一条日志信息的级别,我们能够更加细致地控制日志的生成过程。

最令人感兴趣的就是,这些可以通过一个配置文件来灵活地进行配置,而不需要修改应用的代码。【百度百科】

快速入门
1.先导入log4j的包。

<!-- https://mvnrepository.com/artifact/log4j/log4j -->
<dependency>
    <groupId>log4j</groupId>
    <artifactId>log4j</artifactId>
    <version>1.2.17</version>
</dependency>

2.新建log4j.properties文件

#将等级为DEBUG的日志信息输出到console和file这两个目的地,console和file的定义在下面的代码
log4j.rootLogger=DEBUG,console,file

#控制台输出的相关设置
log4j.appender.console = org.apache.log4j.ConsoleAppender
log4j.appender.console.Target = System.out
log4j.appender.console.Threshold=DEBUG
log4j.appender.console.layout = org.apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=[%c]-%m%n

#文件输出的相关设置
log4j.appender.file = org.apache.log4j.RollingFileAppender
log4j.appender.file.File=./log/kuang.log
log4j.appender.file.MaxFileSize=10mb
log4j.appender.file.Threshold=DEBUG
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=[%p][%d{yy-MM-dd}][%c]%m%n

#日志输出级别
log4j.logger.org.mybatis=DEBUG
log4j.logger.java.sql=DEBUG
log4j.logger.java.sql.Statement=DEBUG
log4j.logger.java.sql.ResultSet=DEBUG
log4j.logger.java.sql.PreparedStatement=DEBUG

配置logrj为日志的实现

<settings>
        <setting name="logImpl" value="LOG4J"/>
    </settings>

在这里插入图片描述

简单使用:
1.在需要使用log4j的类中,导入org.apachee.log4j.Logger包。

2.创建日志对象:参数为当前类的class
static Logger logger = Logger.getLogger(UserDaoTest.class);

在这里插入图片描述
3.日志级别
info
debug
error

08.分页

limit分页

1语法: SELECT  from user limit startIndex,pagesize;
2.SELECT * from user limit 3;#[o,n]

使用Mybatis实现分页,核心为sql

<!--/分页-->
<select id="getuserByLimit" parameterType="map" resu7tMap="userMap">
select  from mybatis.user limit #{startindex} ,#{pagesize}
</select>

RowBounds实现分页(了解即可,不推荐使用)

MyBatis分页插件PageHelper

这是MyBatis的初步了解与使用,你也许还需要了解注解开发,缓存等。
这些内容将在下一篇文章中介绍。
我是MyBatis的第一篇。

在这里插入图片描述

posted @ 2021-01-05 10:41  轻松玩编程  阅读(345)  评论(0编辑  收藏  举报