Simple database addition, deletion, modification and query of MyBatis demo

1. Introduction to MyBatis (taken from official documents): MyBatis is an excellent persistence layer framework that supports customized SQL, stored procedures, and advanced mapping. MyBatis avoids almost all JDBC code and manual setting of parameters and obtaining result sets. MyBatis can use simple XML or annotations for configuration and native Maps, and map interfaces and Java POJOs (Plain Old Java Objects) to records in the database.
Composition: SqlSessionFactoryBuilder ——>Build SqlSessionFactory through xm configuration file ——>Get SqlSession

1.
The sqlSessionFactoryBuilder class can be instantiated, used and discarded. Once the SqlSessionFactory is created, it is no longer needed. Therefore, the best scope of the SqlSessionFactoryBuilder instance is the method scope (that is, local method variables). You can reuse SqlSessionFactoryBuilder to create multiple SqlSessionFactory instances, but it is better not to keep it always in order to ensure that all XML parsing resources are open to more important things.

2.
SqlSessionFactory Once the SqlSessionFactory is created, it should always exist during the running of the application. There is no reason to clear or rebuild it. The best practice for using SqlSessionFactory is not to recreate it multiple times during the running of the application. Rebuilding the SqlSessionFactory multiple times is regarded as a code "bad smell". Therefore, the best scope of SqlSessionFactory is the scope of application. There are many ways to do it, the easiest is to use singleton mode or static singleton mode.

3.
Each thread of SqlSession should have its own instance of SqlSession. The instance of SqlSession is not thread-safe, so it cannot be shared, so its best scope is the request or method scope. You must not put the reference of the SqlSession instance in the static field of a class, even the instance variables of a class. Never place the reference of the SqlSession instance in any type of management scope, such as the HttpSession in the Serlvet architecture. If you are currently using a web framework, consider placing SqlSession in a similar scope to the HTTP request object. In other words, every time you receive an HTTP request, you can open a SqlSession, return a response, and then close it. This close operation is very important, you should put this close operation in the finally block to ensure that you can perform the close every time.

2. Demo realization.

数据库:mysql
1.学生表:
CREATE TABLE student (
id int(11) NOT NULL AUTO_INCREMENT,
name varchar(10) DEFAULT NULL,
sex varchar(10) DEFAULT NULL,
PRIMARY KEY (id)
) ENGINE=InnoDB AUTO_INCREMENT=10 DEFAULT CHARSET=utf8 |

2. Project directory structure

3.pom.xml, add dependency package

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.mybatis</groupId>
    <artifactId>MybatisDemo</artifactId>
    <packaging>war</packaging>
    <version>0.0.1-SNAPSHOT</version>
    <name>MybatisDemo Maven Webapp</name>
    <url>http://maven.apache.org</url>
    <dependencies>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>3.8.1</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.4.1</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.38</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-jdbc</artifactId>
            <version>3.0.5.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis-spring</artifactId>
            <version>1.3.0</version>
        </dependency>
    </dependencies>
    <build>
        <finalName>MybatisDemo</finalName>
        <defaultGoal>compile</defaultGoal>
    </build>
</project>

4. The mybatis-config.xml
XML configuration file (configuration XML) contains the core settings for the MyBatis system, including the data source (DataSource) for obtaining database connection instances and the transaction manager (TransactionManager) that determines the scope and control of the transaction

<?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/mybatisDemo?characterEncoding=GBK"/>
                <property name="username" value="root"/>
                <property name="password" value="root"/>
            </dataSource>
        </environment>
    </environments> 

    <mappers>
        <mapper resource="com/entity/StudentMapper.xml"/>
    </mappers>

</configuration>
  1. StudentMapper.xml mapping table
    5.1 typeAliases
    type alias is to set a short name for the Java type. It is only related to the XML configuration, and its meaning is only to reduce the redundancy of the fully qualified name of the class

Such as:

<typeAlias alias="Student" type="com.example.student.Student"/>

5.2 resultMap and resultType cannot be used at the same time .

resultType: The type of result. You can use JavaBeans or POJOs as the mapping object.
resultMap: result set. It can solve the column name mismatch, define the result set you want to return from SQL, and map more complex domain objects.

<?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 namespace="com.example.dao.StudentDao">
<!--id="studentList",在命名空间中唯一的标识符,后面查询结果会使用这个id-->
    <resultMap type="com.example.student.Student" id="studentList">
    <!--column对应数据库中表字段-->
        <id property="id" column="id" javaType="java.lang.Integer"/>
        <result property="name" column="name" javaType="java.lang.String"/>
        <result property="sex" column="sex" javaType="java.lang.String"/>
    </resultMap>
    <!--select insert update delete中的id名对应dao接口的方法名字 -->
    <select id="queryOneStudent" parameterType="int" resultType="com.example.student.Student"><--! 这就是全名(包含包路径),如果设置了别名就可以只用别名 -->
        select * from student where id=#{id}
    </select>
    <insert id="addStudent">
        insert into student (name,sex) values(#{name},#{sex})
    </insert>
    <delete id="deleteOneStudent" parameterType="int">
        delete from student where id=#{id}
    </delete>
    <update id="updateOneStudent" >
        update student set name=#{student.name},student.sex=#{student.sex} where id=#{id}
    </update>
    <!--这个resultMap则是之前定义的id -->
    <select id="queryAllStudent"  resultMap="studentList">
        select * from student
    </select>
</mapper>

6. MybatisUtil class, the initialization of sessionFactory commissioned into util class to avoid duplication of code.

public class MybatisUtil {
    public static SqlSessionFactory initSqlSessionFactory() {
        String resource = "mybatis/mybatis-config.xml";
        InputStream inputStream = null;
        SqlSessionFactoryBuilder sessionFactoryBuilder = null;
        SqlSessionFactory sessionFactory = null;
        try {
            inputStream = Resources.getResourceAsStream(resource);
            sessionFactoryBuilder = new SqlSessionFactoryBuilder();
            sessionFactory = sessionFactoryBuilder.build(inputStream);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return sessionFactory;
    }

    public static SqlSession initSqlSession() {
        SqlSession session = initSqlSessionFactory().openSession();
        return session;
    }

    public static void closeOrCommitSession(SqlSession session,int flag) {
        if (flag == 0) {
            session.close();
        } else {
            session.commit();
            session.close();
        }
    }
}

7. StudentDao
Notice : If you don’t use @Param annotation, an exception will be reported:
Cause: org.apache.ibatis.binding.BindingException: Parameter'id' not found. Available parameters are [0, student, param1, param2]

public interface StudentDao {
    public Student queryOneStudent(int id);
    public void addStudent(Student student);
    public void deleteOneStudent(int id);
    public void updateOneStudent(@Param("id") int id, @Param("student") Student student);
    public List<Student> queryAllStudent();
}

8. StudentDaoImpl
Notice: Remember to close the session every time. In addition, the commit method must be used for insert, update, and delete operations. For code readability, a common util method is proposed here.

public class StudentDaoImpl implements StudentDao {
    
    
    private static final int ONLY_CLOSE_FLAG = 0;
    private static final int COMMIT_CLOSE_FLAG = 1;
    public Student queryOneStudent(int id) {
        SqlSession session = MybatisUtil.initSqlSession();
        StudentDao studentDao = session.getMapper(StudentDao.class);
        Student student = studentDao.queryOneStudent(id);
        System.out.println("queryOneStudent-->>" + id);
        MybatisUtil.closeOrCommitSession(session, ONLY_CLOSE_FLAG);
        return student;
    }

    public void addStudent(Student student) {
        SqlSession session = MybatisUtil.initSqlSession();
        StudentDao studentDao = session.getMapper(StudentDao.class);
        studentDao.addStudent(student);
        System.out.println("addStudent-->>" + student.getName());
        MybatisUtil.closeOrCommitSession(session, COMMIT_CLOSE_FLAG);
    }

    public void deleteOneStudent(int id) {
        SqlSession session = MybatisUtil.initSqlSession();
        StudentDao studentDao = session.getMapper(StudentDao.class);
        studentDao.deleteOneStudent(id);
        System.out.println("deleteOneStudent-->>" + id);
        MybatisUtil.closeOrCommitSession(session, COMMIT_CLOSE_FLAG);

    }

    public void updateOneStudent(int id, Student student) {
        SqlSession session = MybatisUtil.initSqlSession();
        StudentDao studentDao = session.getMapper(StudentDao.class);
        studentDao.updateOneStudent(id, student);
        System.out.println("updateOneStudent-->>" + id + student.getName());
        MybatisUtil.closeOrCommitSession(session, COMMIT_CLOSE_FLAG);
    }

    public List<Student> queryAllStudent() {
        SqlSession session = MybatisUtil.initSqlSession();
        StudentDao studentDao = session.getMapper(StudentDao.class);
        List<Student> studentList = studentDao.queryAllStudent();
        System.out.println("queryAllStudent-->>" );
        MybatisUtil.closeOrCommitSession(session, ONLY_CLOSE_FLAG);
        return studentList;
    }

}

7. Student entity class

public class Student {
    private int id;
    private String name;
    private String sex;

    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 getSex() {
        return sex;
    }

    public void setSex(String sex) {
        this.sex = sex;
    }

    @Override
    public String toString() {
        return "Student [id=" + id + ", name=" + name + ", sex=" + sex + "]";
    }

}

8. The Test class also proposes some methods to test the function.

public class Test {


    public static void main(String[] args) {
        StudentDao studentDao = new StudentDaoImpl();
        //StudentService studentService = new StudentServiceImpl();
        queryAllStudent(studentDao);
        //addStudent(studentDao);
        //deleteOneStudent(studentDao);
        //updateOneStudent(studentDao);
    }

    public static void queryOneStudent(StudentDao studentDao) {
        Student student = studentDao.queryOneStudent(3);
        System.out.println(student.toString());
    }

    public static void addStudent(StudentDao studentDao) {
        Student student = new Student();
        student.setName("huang2");
        student.setSex("female");
        studentDao.addStudent(student);
    }

    public static void deleteOneStudent(StudentDao studentDao) {
        studentDao.deleteOneStudent(4);
    }

    public static void updateOneStudent(StudentDao studentDao) {
        Student student = new Student();
        student.setName("wu1");
        student.setSex("male");
        studentDao.updateOneStudent(5, student);
    }

    public static void queryAllStudent(StudentDao studentDao) {
        List<Student> students = studentDao.queryAllStudent();
        for (Student student : students) {
            System.out.println(student.toString());
        }
    }
}

This is just an introductory demo. The configuration is still relatively primitive and inconvenient to use. There will be a demo combined with spring in the future, which is smarter, more convenient and more efficient.

Refer to mybatis official document: click here

Guess you like

Origin blog.csdn.net/u010857795/article/details/71499616