Mybatis

2020年9月10日19:29:16

一、什么是Mybatis

1.1、什么是mybatis

  • Mybatis是一款优秀的持久层框架
  • 他支持定制化SQL、储存过程以及高级映射。
  • MyBatis避免了几乎所有的JDBC代码和手动设置参数以及获取结果集。
  • Mybatis可以使用简单的XML或注解来配置和映射原生类型、接口和java的POJO(Plain Old java Objects,普通老式java对象)为数据库中的记录。
  • Mybatis本是apache的一个开源项目iBtis,2010年这个项目由Apache software foundation前移到了google code,并且改名为MaBatis。
  • 2013年11月迁移到GItHub。

1.2、持久化

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

  • 持久状态;比如数据库(JDBC),IO文件持久化。

  • 瞬时状态:比如内存,断电即失。

  • 生活中冷藏也是一种持久化。

为什么需要持久化?

  • 避免断电丢失
  • 内存太贵

1.3、持久层

Dao层、Service层、Controller层

  • 王朝的那个持久化工作的代码块
  • 层界线明显

1.4、为什么需要MyBatis?

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

  • 增加开发效率

  • 传统JDBC代码太复杂了,简化代码,(框架)自动化管理。

  • 易上手,易使用。(技术没有高低之分)

    • sql与代码分离,提高了维护性。
    • 使程序设计清晰、易维护、易测试。
    • 将业务逻辑与数据访问逻辑分离。
    • 灵活
    • 提供xml标签,支持编写动态SQL。

    重要的是:使用的人多!

二、第一次使用MyBatis程序

思路:搭建环境–>导入MyBatis–>编写代码–>测试!

2.1、搭建环境

2.1.1、搭建数据
CREATE TABLE `user`  (
  `id` int(20) NOT NULL AUTO_INCREMENT,
  `name` varchar(30) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  `pws` varchar(30) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

INSERT INTO `user` VALUES (1, '悟空', '123');
INSERT INTO `user` VALUES (2, '八戒', '321');
INSERT INTO `user` VALUES (3, '沙僧', '000');

2.1.2、新建项目
  1. 新建一个maven项目
    • 获取mybatis
      <!-- https://mvnrepository.com/artifact/org.mybatis/mybatis -->
      <dependency>
          <groupId>org.mybatis</groupId>
          <artifactId>mybatis</artifactId>
          <version>3.5.2</version>
      </dependency>
    
  2. 删除sre文件
  3. 在mop.xml文件中导入maven依赖
<!--导入依赖-->
<dependencies>
    <!--sql驱动-->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>8.0.16</version>
        </dependency>

    <!--mybatis-->
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.5.2</version>
        </dependency>

    <!--junit-->
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
            <scope>test</scope>
        </dependency>
</dependencies>
<!--防止导包出问题-->
    <build>
        <resources>
            <resource>
                <directory>src/main/resources</directory>
                <includes>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </includes>
                <filtering>true</filtering>
            </resource>
            <resource>
                <directory>src/main/java</directory>
                <includes>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </includes>
                <filtering>true</filtering>
            </resource>
        </resources>
    </build>
</project>

2.2、创建.xml配置文件

  1. 创建module。
    1. 配置mybatis-config.xml文件

      易忘点:

      1. 驱动使在mysql包下的jdbc包里。
      2. useUnicode=true(安全连接)
      3. useUnicode=true(Unicode编码可以正常输出,作用:可以使用中文)
      4. characterEncoding=UTF-8(解决了读取数据库产生的数据乱码的问题,从数据库读数据和写数据时MySQL的默认编码非UTF8编码,需要设置字符集编码为utf8 )
<?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核心配置-->
<configuration>
    <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"/>
            <dataSource type="POOLED">
                <property name="driver" value="com.mysql.jdbc.Driver"/>
                <!-- 与&同意  Unicode编码可以正常显示中文   时区-->
                <property name="url" value="jdbc:mysql://localhost:3306/mybatis?useUnicode=true&amp;characterEncoding=UTF-8&amp;serverTimezone=Asia/Shanghai"/>
                <property name="username" value="root"/>
                <property name="password" value="123"/>
            </dataSource>
        </environment>
    </environments>
    <mappers>
        <mapper resource="com/lyx/mapper/StuMapper.xml"/>
    </mappers>
</configuration>
  1. 编写MyBatis工具类
package main.java.com.lyx.dao;

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 java.io.IOException;
import java.io.InputStream;

/**
 * 工具类
 * 获取sqlSessionFactory --> sqlSession
 */

public class MybatisUtils {
    //提升作用域
    private static SqlSessionFactory  sqlSessionFactory;
    static {
        try {
            //使用MyBatis第一步: 获取sqlSessionFactory对象
            String resource = "org/mybatis/example/mybatis-config.xml";
            InputStream inputStream = Resources.getResourceAsStream(resource);
            SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //有了sqlSessionFactory对象,获取到SqlSession的实例了。
    //SqlSession中包含了面向数据库执行Sql命令的所有方法。
    public static SqlSession getSqlSession(){
        return sqlSessionFactory.openSession();
    }
}

2.3、编写代码

  • 实体类
    package main.java.com.lyx.pojo;
    //实体类
    public class user {
        private int id;
        private String naem;
        private String pws;
    
        public user() {
        }
    
        public user(int id, String naem, String pws) {
            this.id = id;
            this.naem = naem;
            this.pws = pws;
        }
    
        public int getId() {
            return id;
        }
    
        public String getNaem() {
            return naem;
        }
    
        public String getPws() {
            return pws;
        }
    
        public void setId(int id) {
            this.id = id;
        }
    
        public void setNaem(String naem) {
            this.naem = naem;
        }
    
        public void setPws(String pws) {
            this.pws = pws;
        }
    
        @Override
        public String toString() {
            return "user{" +
                    "id=" + id +
                    ", naem='" + naem + '\'' +
                    ", pws='" + pws + '\'' +
                    '}';
        }
    }
    
  • dao层mapper接口
    public interface User_dao {
        //遍历集合
        List<Stu> getStu();
    
        //根据id查询单条数据
        List<Stu> getStuId(int id);
    
        //添加数据(数据库增删改需要提交事务才行!)
        int addStu(Stu stu);
    
        //修改Stu
        int updateStu(Stu stu);
    
        //删除一条数据
        int deleteStu(int id);
    
        //Map测试
        int addMap(Map<String,Object> map);
    }
    
  • 接口实现
    • (在mapper中)由原来的的UserDaoimp转变为一个mapper配置文件
    <?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:绑定一个对应的Dao/Mapper接口-->
    <mapper namespace="com.lyx.dao.User_dao">
        <!--select语句    传参:parameter:类型Type,集合用Map-->
        <select id="getUserList" resultType="com.lyx.pojo.User">
            select * from mybatis.user
        </select>
        				    <select id="getStu" resultType="com.lyx.pojo.Stu">
        select * from stu
        </select>
        <select id="getStuId" parameterType="int" resultType="com.lyx.pojo.Stu">
             select * from Stu where id=#{id}
        </select>
    
    <!--    对象中的属性可以直接取出来使用-->
        <insert id="addStu" parameterType="com.lyx.pojo.Stu" >
            insert into mybatis.Stu (id,name,age) values (#{id},#{name},#{age})
        </insert>
    
        <update id="updateStu" parameterType="com.lyx.pojo.Stu">
        update mybatis.stu set name=#{name},age=#{age} where id=#{id}
        </update>
        <delete id="deleteStu" parameterType="int">
            delete from mybatis.stu where id=#{id}
        </delete>
    <!--测试Map-->
        <insert id="addMap" parameterType="map" >
            insert into mybatis.stu (id,name,age) values (#{a},#{b},#{c})
        </insert>
    </mapper>
    
  • 注意点:增删改需要提交事务(sqlSession.commit();)

2.4、测试

注意点:

  • 测试类最好写在与被测试类的路径类似
package com.lyx;

import com.lyx.mapper.StuMapper;
import com.lyx.pojo.Stu;
import com.lyx.util.StuUtil;
import org.apache.ibatis.session.SqlSession;
import org.junit.Test;

import java.util.List;

public class StuTest {
    @Test
    public void  test(){
        //调用util中的getSession方法获取到sqlSession方法
        SqlSession sqlSession = StuUtil.getSqlSession();
        //调用sqlSession方法获取
        StuMapper mapper = sqlSession.getMapper(StuMapper.class);
        List<Stu> stu = mapper.getStu();
        System.out.println(stu);
    }
    @Test
    public void TestId(){
        SqlSession sqlSession = mybatisUtil.getSqlSession();
        StuMapper mapper = sqlSession.getMapper(StuMapper.class);
        List<Stu> stuId = mapper.getStuId(1);
        System.out.println(stuId);
        sqlSession.close();
    }
}

  • 总结:失败的原因只有一个那就是懒性

三、拓展

1、万能的Map

接口

 //Map测试
    int addMap(Map<String,Object> map);

接口xml文件

<!--测试Map-->
    <insert id="addMap" parameterType="map" >
        insert into mybatis.stu (id,name,age) values (#{a},#{b},#{c})
    </insert>

测试

@Test
    public void addMap(){
        SqlSession sqlSession = mybatisUtil.getSqlSession();
        StuMapper mapper = sqlSession.getMapper(StuMapper.class);
        Map<String, Object> map = new HashMap<String, Object>();
        map.put("a",5);
        map.put("b","Map测试!");
        map.put("c",333333);
        mapper.addMap(map);
        sqlSession.commit();
        sqlSession.close();
    }

##2、模糊查询

//接口代码
	//模糊查询
    List<Stu> getStuN(String name);

//接口.xml代码
 <select id="getStuN"  resultType="com.lyx.pojo.Stu">
        select * from mybatis.stu where name like "%"#{name}"%"
    </select>

//测试
    @Test
    public void getStuN(){
        SqlSession sqlSession = mybatisUtil.getSqlSession();
        StuMapper mapper = sqlSession.getMapper(StuMapper.class);
        List<Stu> stuN = mapper.getStuN("李");
        System.out.print(stuN);
        sqlSession.close();
    }

四、配置优化

4.1、属性

  1. 在resources中新建.properties文件
driver=com.mysql.cj.jdbc.Driver
url=jdbc:mysql://localhost:3306/mybatis?useUnicode=true&&characterEncoding=UTF-8&&serverTimezone=Asia/Shanghai
username=root
password=123
  1. 在mybatis-config。xml文件中导入
<!--  方式一  -->
<properties resource="db.properties"/>


<!--  方式二  -->
<properties resource="org/mybatis/example/config.properties">
    
  <property name="username" value="dev_user"/>
  <property name="password" value="F2Fa3!33TYyg"/>
</properties>
  • 注意点:

    ①.properties文件和.xml数据库连接的url部分中的&&的解读方式不一样,在.xml文件中&amp; ,在.properties文件应该被写成&&

​ ②在xml文件中所有的标签都有其对应的位置。

​ ③方式二优先执行外部映入文件中的内容。

4.2、别名

  • 类型别名可为 Java 类型设置一个缩写名字。 它仅用于 XML 配置,意在降低冗余的全限定类名书写。
  1. 实体类别名 (mybatis的mapper层是是不能起别名的)
  <!-- mybatis文件中配置   配置别名-->
    <typeAliases >
        <typeAlias type="lyx.pojo.Stu" alias="Stu"/>
    </typeAliases>

<!--接口.xml文件中使用-->
    <select id="getStu" resultType="Stu">
    select * from stu
    </select>
  1. 包别名:指定一个包名,MyBatis 会在包名下面搜索需要的
<!-- mybatis文件中配置 -->
<typeAliases>
	<package name="com.lyx.mapper"/>
</typeAliases>	
  • 注意点:

    • 在没有注解的情况下,会使用 Bean 的首字母小写的非限定类名来作为它的别名 。

    • 接口不可以使用第一种方法。(namespace属性:在MyBatis中,Mapper中的namespace用于绑定Dao接口的,即面向接口编程。

      它的好处在于当使用了namespace之后就可以不用写接口实现类,业务逻辑会直接通过这个绑定寻找到相对应的SQL语句进行对应的数据处理,不可以定义别名)

**两者区别:**第一种可以自定义别名,第二种不行(如果个别需要自定义可以使用注解起别名自定义别名),如果实体类多,建议使用第二种,反之第一种。

  1. 注解别名:在实体类中采用注解方式,起别名
import org.apache.ibatis.type.Alias;

@Alias("zjbm")
public class Stu {}
  • 注意:是导入org.apache.ibatis.type中的Alias

4.3、设置

4.4、映射器

  • 作用:告诉 MyBatis 去哪里找映射文件 (寻找sql)

方式一:使用相对于类路径的资源引用

  <mappers>
        <mapper resource="com/lyx/mapper/StuMapper.xml"/>
  </mappers>

方式二:使用映射器接口实现类的完全限定类名

<mamppers>
    <mapper class="com.lyx.mapper.StuMapper"/>
</mamppers>

方式三:将包内的映射器接口实现全部注册为映射器

<mappers>
	<package name="com.lyx.mapper"/>
</mappers>
  • 后两者注意:实体类与映射文件必须在统一包内并且命名一致。

五、日志

5.1、日志工厂

  • 如果一个数据库操作出现异常,日志是最好的排查错误的助手。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EdQVQ9zk-1604538561160)(E:\桌面\Markdown笔记\1604132888073.png)]

  • 有效值:SLF4J、LOG4J 、 LOG4J2 、 JDK_LOGGING 、 COMMONS_LOGGING 、 STDOUT_LOGGING 、 NO_LOGGING (不同的有效值,实现方式不同,输出不同)

  • loglmpl没有默认值

  • 在mybatis中具体使用哪种日志实现,在设置中指定。

    • STDOUT_LOGGING标准日志输出

      <!-- settings标签位置必须在properties与typeAliases标签中间-->
      <settings>
              <!--标准日志工厂-->
              <setting name="logImpl" value="STDOUT_LOGGING"/>
          </settings>
      

5.2、LOG4J的使用

5.21、什么是LOG4J?

  • 控制日志信息输送的目的地是控制台、文件、GUI组件,甚至是套接口服务器、NT的事件记录器、UNIX Syslog、守护进程等
  • 控制每一条日志的输出格式
  • 定义每一条日志信息的级别,我们能够更加细致地控制日志的生成过
  • 还可以通过一个配置文件来灵活地进行配置,而不需要修改应用的代码。

5.22、基本使用

  1. 导入log4j的包
    <!-- https://mvnrepository.com/artifact/log4j/log4j -->
    <dependency>
        <groupId>log4j</groupId>
        <artifactId>log4j</artifactId>
        <version>1.2.17</version>
    </dependency>
  1. 创建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/log4j.txt
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.dql=DEBUG
log4j.logger.java.sq1.statement=DEBUG
log4j.logger.java.sq1.ResultSet=DEBUG
log4j.logger.java.sq1.PreparedStatement=DEBUG
  1. 配置log4j日志实现
   <!--在mybatis核心文件中配置     -->
<settings>
       <setting name="logImpl" value="LOG4J"/>
</settings>

5.23、Log4j简单使用

  1. 在要使用Log4j的类中,导入包:import org.apache.log4j.Logger;

  2. 创建日志对象,参数为当前类名

    static Logger logger = Logger.getLogger(BookTypeMapperTest.class);
    
  3. 日志级别

    • 级别不同,输出的标签不同,方便筛选
 //提示
logger.info("info,进入了log4j");
//调试
logger.debug("debug,进入了log4j");
 //紧急
logger.error("error,进入了log4j");

​ 日志文件记录内容:

[INFO][20-11-04][com.lyx.test.BookMapperTest]info进入!
[DEBUG][20-11-04][com.lyx.test.BookMapperTest]debug进入
[ERROR][20-11-04][com.lyx.test.BookMapperTest]error进入!

六、分页查询

  • 分页的作用:减少数据处理量

6.2、使用Limit分页查询

  • 语法:
select * from Emp limit staIndex,pageSize;
  • Limit两个属性:
    • staIndex:起止位置
    • pageSize:查询数据的条数
    • 如果只传入一个属性,默认起始位置为0
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值