mybatis 原始dao开发方式(含使用mybatis的完整流程)

【看懂这篇博客需要对mybatis框架的基础知识有所了解】

写在前头:

【本博客使用的Java IDE开发环境并不是myeclipse或者eclipse而是IDEA,在这篇博客所要讲解的知识上两者没有太多的不同,不会因为没有接触过IDEA开发环境而对此篇博客一头雾水,请大家放心阅读。】

【本篇博客使用mybatis框架并不是通过手动导入jar包的方式,而是通过maven完成的jar包的导入】

目录

使用mybatis开发dao的方式和步骤:

对以上整个步骤进行穿通:

原始dao开发方式的弊端:


 


使用mybatis开发dao的方式和步骤:

1.使用IDEA创建一个maven工程(大家完全可以通过手动导入jar包的方式使用mybatis)

(这里创建maven工程大家可以理解成目的就是为了方便导入jar包,它和平时创建的工程没有什么区别,如果不了解maven的可以百度或者B站去学习一下。)然后将mybatis框架以及数据库驱动所需要的jar包的依赖全部都写在pom.xml中,这次用到的有如下这么多:

       <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.11</version>
            <scope>test</scope>
        </dependency>
        <!--mybatis核心包-->
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.4.4</version>
        </dependency>
        <!-- 日志文件管理包 -->
        <dependency>
            <groupId>log4j</groupId>
            <artifactId>log4j</artifactId>
            <version>1.2.17</version>
        </dependency>
        <!--生成po、mapper.java、mapper.xml核心jar-->
        <dependency>
            <groupId>org.mybatis.generator</groupId>
            <artifactId>mybatis-generator-core</artifactId>
            <version>1.3.6</version>
        </dependency>

 2.在src目录下创建一个名为SqlMapConfig.xml的xml文件

 如果在"new"的时候没有发现xml文件,就自己创建一个  具体方法如下:

 点击 + 按钮,即第一步完成后,会出现以下页面:

输入xml之后,就可以进行上图的第二步和第三步了。

3.配置SqlMapConfig.xml文件中的内容

直接对下面的代码进行复制粘贴过去即可(不要紧张,文件头处的代码程序员也写不出来,也不需要程序员写,现在就先用复制粘贴完成这个操作就好,这个并不是学习mybatis的重点所在):

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

 接下来就是在<configuration>中配置mybatis的运行环境等信息,这些是重要的(至少要做到可以看懂,有JDBC基础的话看参数就直接可以猜得出每个标签用来做什么  这段代码也直接复制粘贴过去就好):

<configuration>
    <!--
    environments指整个的运行环境
    -->
    <environments default="development">
        <environment id="development">
            <!--使用jdbc事务管理  事物的控制由mybatis完成-->
            <transactionManager type="JDBC"></transactionManager>
            <!--数据库连接池 由mybatis管理-->
            <dataSource type="POOLED">
                <property name="driver" value="com.mysql.jdbc.Driver"/>
                <property name="url" value="jdbc:mysql://127.0.0.1:3306/mybatisdemo"/>
                <property name="username" value="root"/>
                <property name="password" value="admin"/>
            </dataSource>
        </environment>
    </environments>
    <!--加载映射文件-->
</configuration>

 4.创建表所对应的类的映射文件

以下是所用数据库和数据库中的表结构

 user表(即用户表)的映射文件就给它取名为UserMapper.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">
<!--
在此映射文件中用于配置很多的sql语句
-->

<!--namespace命名空间  它的内容随便写  (不要问我为什么写com.deml.User 因为我喜欢!)-->
<mapper namespace="com.demo.User">

    <!--select:查询标签   id用于唯一标识此sql语句  (随便取名字)
     sql语句的大小写无所谓
     #{}表示一个占位符
     使用占位符之后要用 parameterType 指定输入参数的类型  应该与数据库中设置的类型相同
     resultType表示sql输出结果所映射的Java对象类型(也就是这张表所对应的类)
    -->

    <select id="findById" parameterType="int" resultType="com.demo.User">
        SELECT * FROM User WHERE userid=#{id}
    </select>

    <!--${}:表示拼接字符串  将接收到的参数的内容不加任何修饰拼接在sql中
    由此可知 ${}有sql注入的风险  在此例如:输入的是:" or 1=1 "
    ${value}:接受输入参数的内容,如果传入类型是简单类型,则只能使用value
    -->

    <select id="findUserByName" resultType="com.demo.User">
        select * from user where username like "%${value}%"
    </select>

    <!--添加用户-->
    <insert id="insertUser1" parameterType="com.demo.User">
        insert into user value (#{userName},#{password},#{userId})
    </insert>

    <!--添加用户并将插入数据的主键值返回 返回给表相对应的对象(只适用于主键值设置成了自增时的情况)
    因为如果在数据库中主键设置成了自增,那么就会按照这个去给主键赋值。在对象中给主键符的值是没有用的
    keyProperty:将查询的主键值设置到parameterType指定的对象的哪个属性
    order:    相对于insert语句的select LAST_INSERT_ID()的执行顺序
    resultType:指定select LAST_INSERT_ID()的结果类型
    -->

    <insert id="insertUser2" parameterType="com.demo.User">
        <selectKey keyProperty="userId" order="AFTER" resultType="java.lang.Integer">
            select LAST_INSERT_ID()
        </selectKey>
        insert into user value (#{userName},#{password},#{userId})
    </insert>

    <!--
    查询返回非自增的主键值
    执行过程:通过uuid()得到主键,
    然后将主键值设置到user对象的userId属性中,
    之后,在insert执行时,从user对象中取出userId属性值
    -->

    <insert id="insertUser3" parameterType="com.demo.User">
        <selectKey keyProperty="userId" order="BEFORE" resultType="java.lang.Integer">
            select uuid()
        </selectKey>
        insert into user value (#{userName},#{password},#{userId})
    </insert>

    <!--根据userId删除用户-->
    <delete id="deleteById" parameterType="java.lang.Integer">
      delete from user where userid=#{userid}
    </delete>
    <!--更新用户
    -->

    <update id="updateById" parameterType="com.demo.User">
        update user set username=#{userName} where userid=#{userId}
    </update>
</mapper>

5.创建接口

每一张表对应一个接口(其实创建接口可以把和创建表所对应的dao层的类统称为一个操作)。因为创建接口的目的就是为了给接下来创建类提供一个模板,让类去实现它,以便于后期维护起来方便。这里的接口创建如下:

/**
 * Create by ZwZ
 * DateTime:2018/10/2 11:49
 * Description :
 */
public interface User {
    void insertUser(User user) throws Exception;//添加用户信息
    void deleteUser(int userId) throws Exception;//删除用户信息
    void updateUser(int userId) throws  Exception;//根据id修改用户信息
    com.demo.User findUserById(int userId) throws Exception;//根据id查询用户信息
}

如何深入理解创建接口和dao层的意义:

   

6.创建dao层接口的实现类

创建了接口之后,就要创建接口的实现类:

package dao.impi;
//                       .::::.
//                     .::::::::.
//                    :::::::::::
//                 ..:::::::::::'
//              '::::::::::::'
//                .::::::::::
//           '::::::::::::::..
//                ..::::::::::::.
//              ``::::::::::::::::
//               ::::``:::::::::'        .:::.
//              ::::'   ':::::'       .::::::::.
//            .::::'      ::::     .:::::::'::::.
//           .:::'       :::::  .:::::::::' ':::::.
//          .::'        :::::.:::::::::'      ':::::.
//         .::'         ::::::::::::::'         ``::::.
//     ...:::           ::::::::::::'              ``::.
//    ```` ':.          ':::::::::'                  ::::..
//                       '.:::::'                    ':'````..

import dao.jiekou.User;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;

/**
 * Create by ZwZ
 * DateTime:2018/10/2 11:56
 * Description : 
 */
public class UserImpl implements User {
    private SqlSessionFactory sqlSessionFactory;
    //通过构造方法注入SqlSessionFactory对象
    public UserImpl(SqlSessionFactory sqlSessionFactory) {
        this.sqlSessionFactory = sqlSessionFactory;
    }

    @Override
    public void insertUser(User user) throws Exception {
        SqlSession sqlSession = sqlSessionFactory.openSession();
        sqlSession.insert("com.demo.User.insertUser2",user);
        sqlSession.commit();
        sqlSession.close();

    }

    @Override
    public void deleteUser(int userId) throws Exception {

    }

    @Override
    public void updateUser(int userId) throws Exception {

    }

    @Override
    public com.demo.User findUserById(int userId) throws Exception {
        SqlSession sqlSession = sqlSessionFactory.openSession();
        com.demo.User user = sqlSession.selectOne("com.demo.User.findById",userId);
        sqlSession.commit();
        sqlSession.close();
        return user;
    }
}

 7.在总的配置文件中映射上表所对应的类的映射文件

其目的就是告诉mybatis : 我这里有一个映射文件,到时候加载的时候加载上。

方法:在SqlMapConfig.xml的<configuration>标签中的末尾加上以下代码

 <!--加载映射文件-->
    <mappers>
        <mapper resource="mapper/UserMapper.xml"/>
    </mappers>

8.测试运行

package com.Test;
//                       .::::.
//                     .::::::::.
//                    :::::::::::
//                 ..:::::::::::'
//              '::::::::::::'
//                .::::::::::
//           '::::::::::::::..
//                ..::::::::::::.
//              ``::::::::::::::::
//               ::::``:::::::::'        .:::.
//              ::::'   ':::::'       .::::::::.
//            .::::'      ::::     .:::::::'::::.
//           .:::'       :::::  .:::::::::' ':::::.
//          .::'        :::::.:::::::::'      ':::::.
//         .::'         ::::::::::::::'         ``::::.
//     ...:::           ::::::::::::'              ``::.
//    ```` ':.          ':::::::::'                  ::::..
//                       '.:::::'                    ':'````..

import com.demo.User;
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;

/**
 * Create by ZwZ
 * DateTime:2018/10/1 21:25
 * Description :通过用户id查询用户
 */
public class Test1 {
    public static void main(String[] args) throws IOException {
        //mybatis的总配置文件
        String resource = "SqlMapConfig.xml";
        //得到配置文件流
        InputStream inputStream =  Resources.getResourceAsStream(resource);
        //创建会话工厂,传入mybatis的配置文件信息
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        /*通过工厂得到SqlSession*/
        SqlSession sqlSession = sqlSessionFactory.openSession();
        /*通过SqlSession操作数据库
        * 第一个参数:映射文件中statement的id 等于 namespace+"."+statement的id
        * 第二个参数:指定和映射文件中所匹配的parameterType类型的参数
        * selectOne()表示查询出一条记录
        */
        User user = sqlSession.selectOne( "com.demo.User.findById",1);
        System.out.println(user.getUserName());
        //释放资源
        sqlSession.close();
    }
}

对以上整个步骤进行穿通:

原始dao开发方式的弊端:

  1. dao接口实现类方法中存在大量重复代码,从设计上来看,应该抽取
  2. 调用sqlSession方法时,将satement的id硬编码了,即类似于"com.demo.User.findById"这种,都写死了。
  3. sqlSession的方法中,第二个参数要求传入的参数是Object类型,如果传错了参数,编译不会报错执行的时候才会报错,降低了开发效率,不利于开发。

猜你喜欢

转载自blog.csdn.net/My_name_is_ZwZ/article/details/82926601