Mybatis(二)— 使用Mapper动态代理方式进行开发

来源:互联网 发布:清理后台的软件 编辑:程序博客网 时间:2024/05/20 23:07

mybait有两种开发方式,一种是传统的dao开发方式,一种是Mapper动态代理方式。
这里简单地介绍下这两种方式。
需要用到的数据库表结构如下:
这里写图片描述

1.Dao开发方式

映射文件Student.xml

<?xml version="1.0" encoding="UTF-8" ?><!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd"><!-- namespace:命名空间,做sql隔离 ,访问sql语句时,sql的id前面要带着命名空间--><mapper namespace="student">    <!--     id:sql语句唯一标识,不能重复。    parameterType:属性指明查询时使用的参数类型    resultType:属性指明查询返回的结果集类型。resultType="com.mq.pojo.Student"表示返回值是Student类型    #{}占位符:起到占位作用,如果传入的是基本类型(string,long,double,int,boolean,float等),那么#{}中的变量名称可以随意写,一般和属性名相同。    java.lang.Integer也可以直接写成int     -->    <select id="findStuById" parameterType="java.lang.Integer" resultType="com.mq.pojo.Student">        select * from students where id=#{id}    </select>    <!--     如果返回结果为集合,可以调用selectList方法,这个方法返回的结果就是一个集合,所以映射文件中应该配置成集合泛型的类型    ${}拼接符:字符串原样拼接,如果传入的参数是基本类型(string,long,double,int,boolean,float等),那么${}中的变量名称必须是value    注意:拼接符有sql注入的风险,所以慎重使用     -->    <select id="findStuByName" parameterType="java.lang.String" resultType="com.mq.pojo.Student">        select * from students where name like '%${value}%'    </select>    <!--     #{}:如果传入的是pojo类型,那么#{}中的变量名称必须是pojo中对应的属性,    如果要返回数据库自增主键:可以使用select LAST_INSERT_ID()-->    <insert id="insertStu" parameterType="com.mq.pojo.Student" >        <!-- 执行 select LAST_INSERT_ID()数据库函数,返回自增的主键        keyProperty:将返回的主键放入传入参数的Id中保存.        order:当前函数相对于insert语句的执行顺序,在insert前执行是before,在insert后执行是AFTER        resultType:id的类型,也就是keyproperties中属性的类型        -->        <selectKey keyProperty="id" order="AFTER" resultType="java.lang.Integer">            select LAST_INSERT_ID()        </selectKey>        insert into students (name,sex,age,tel) values(#{name},#{sex},#{age},#{tel})    </insert>    <delete id="delStuById" parameterType="int">        delete from students where id=#{id}    </delete>    <!--传入的是一个pojo类型,就是一个新的对象  -->    <update id="updateStuById" parameterType="com.mq.pojo.Student">        update students set name=#{name} where id=#{id}    </update></mapper>

配置文件sqlconfig.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="com.mysql.jdbc.Driver" />                <property name="url" value="jdbc:mysql://localhost:3306/study"/>                <property name="username" value="root" />                <property name="password" value="root" />            </dataSource>        </environment>    </environments>     <mappers>        <!-- 注册Student.xml文件,这两个文件在同一个目录下,都在src目录下-->         <mapper resource="Student.xml"/>     </mappers></configuration>

dao接口和实现类

public interface StudentDao {    public Student findStuById(int id);    public void findStuByName(String name);    public void insertStu();}
public class StudentDaoImpl implements StudentDao {    private SqlSession session;    public StudentDaoImpl(SqlSession session) {        super();        this.session = session;    }    @Override    public Student findStuById(int id) {        Student student = session.selectOne("student.findStuById", id);        System.out.println(student);        session.close();        return student;    }    @Override    public void findStuByName(String name) {        List<Student> list = session.selectList("student.findStuByName", name);        System.out.println(list);        session.close();    }    @Override    public void insertStu() {Student student=new Student();    student.setAge(22);    student.setSex("女");    student.setTel("44544665");    student.setName("小乔");    session.insert("student.insertStu", student);    //提交事务(mybatis会自动开启事务,但是它不知道何时提交,所以需要手动提交事务)    session.commit();    System.out.println("id值" + student.getId());    }}

测试类

public class StudentDaoTest {private SqlSession session;    //作用:在测试方法前执行这个方法    @Before    public void FirstDo() throws Exception{        //加载配置文件        String resource = "sqlconfig.xml";        //通过流将核心配置文件读取进来        InputStream inputStream = Resources.getResourceAsStream(resource);        //通过核心配置文件输入流来创建会话工厂        SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(inputStream);        session=factory.openSession();    }    //通过id查询数据库中的记录。并封装成对象    @Test    public void findStuById(){        StudentDao student=new StudentDaoImpl(session);        student.findStuById(2);    }    //模糊搜索    @Test    public void findStuByName(){        StudentDao student=new StudentDaoImpl(session);        student.findStuByName("飞");    }    //插入数据    @Test    public void insertStu(){        StudentDao student=new StudentDaoImpl(session);        student.insertStu();    }}

2.Mapper动态代理方式

Mapper接口开发方法只需要程序员编写Mapper接口(相当于Dao接口),由Mybatis框架根据接口定义创建接口的动态代理对象,代理对象的方法体同上边Dao接口实现类方法。
使用Mapper动态代理方式,只需要编写接口,不用去实现这个接口,mybatis会帮我们动态生成代理对象
我们编写的接口必须要和映射文件存在一定的关联,mybatis才能根据接口中的方法找到对应的sql语句

Mapper接口开发需要遵循以下规范:

1、Mapper.xml文件中的namespace与mapper接口的类路径相同。
2、 Mapper接口方法名和Mapper.xml中定义的每个statement的id相同
3、Mapper接口方法的输入参数类型和mapper.xml中定义的每个sql 的parameterType的类型相同
4、Mapper接口方法的输出参数类型和mapper.xml中定义的每个sql的resultType的类型相同

创建mapper接口

public interface StudentMapper {    public Student findStuById(int id);    public List<Student> findStuByName(String name);    public void insertStu(Student student);}

注意,接口的方法名,参数必须符合要求的规范

mapper映射文件StudentMapper.xml

<?xml version="1.0" encoding="UTF-8" ?><!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd"><!-- mapper接口代理实现编写规则:    1. 映射文件中namespace要等于接口的全路径名称    2. 映射文件中sql语句id要等于接口的方法名称    3. 映射文件中传入参数类型要等于接口方法的传入参数类型    4. 映射文件中返回结果集类型要等于接口方法的返回值类型 --><mapper namespace="com.mq.mapper.StudentMapper">    <select id="findStuById" parameterType="java.lang.Integer" resultType="com.mq.pojo.Student">        select * from students where id=#{id}    </select>    <select id="findStuByName" parameterType="java.lang.String" resultType="com.mq.pojo.Student">        select * from students where name like '%${value}%'    </select>    <!--     #{}:如果传入的是pojo类型,那么#{}中的变量名称必须是pojo中对应的属性,    如果要返回数据库自增主键:可以使用select LAST_INSERT_ID()-->    <insert id="insertStu" parameterType="com.mq.pojo.Student" >        <selectKey keyProperty="id" order="AFTER" resultType="java.lang.Integer">            select LAST_INSERT_ID()        </selectKey>        insert into students (name,sex,age,tel) values(#{name},#{sex},#{age},#{tel})    </insert>    <delete id="delStuById" parameterType="int">        delete from students where id=#{id}    </delete>    <!--传入的是一个pojo类型,就是一个新的对象  -->    <update id="updateStuById" parameterType="com.mq.pojo.Student">        update students set name=#{name} where id=#{id}    </update></mapper>

在sqlconfig.xml注册mapper映射文件

<?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="com.mysql.jdbc.Driver" />                <property name="url" value="jdbc:mysql://localhost:3306/study"/>                <property name="username" value="root" />                <property name="password" value="root" />            </dataSource>        </environment>    </environments>     <mappers>        <!-- 注册Student.xml文件,这两个文件在同一个目录下,都在src目录下-->         <mapper resource="Student.xml"/>         <!--StudentMapper.xml在com/mq/mapper的包下  -->         <mapper resource="com/mq/mapper/StudentMapper.xml"/>     </mappers></configuration>

测试类

public class StudentMapperTest {    private SqlSession session;    //作用:在测试方法前执行这个方法    @Before    public void FirstDo() throws Exception{        //加载配置文件        String resource = "sqlconfig.xml";        //通过流将核心配置文件读取进来        InputStream inputStream = Resources.getResourceAsStream(resource);        //通过核心配置文件输入流来创建会话工厂        SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(inputStream);        session=factory.openSession();    }    @Test    public void testFindStuById(){//获取mapper接口的代理对象        StudentMapper stuMapper = session.getMapper(StudentMapper.class);        //调用代理对象方法        Student student = stuMapper.findStuById(3);        System.out.println(student);        //关闭session        session.close();    }    @Test    public void testFindStuByName(){        StudentMapper stuMapper = session.getMapper(StudentMapper.class);        List<Student> list = stuMapper.findStuByName("john");        System.out.println(list);        session.close();    }    //插入数据    @Test    public void insertStu(){        StudentMapper stuMapper = session.getMapper(StudentMapper.class);        Student student=new Student();        student.setAge(34);        student.setName("曹操");        student.setSex("男");        student.setTel("4854684866");        stuMapper.insertStu(student);        session.commit();        session.close();    }}

我们只定义了接口,不用定义实现类。将接口中的方法和映射文件通过一定的规则对应起来。

阅读全文
0 0
原创粉丝点击