Comprehensive Overview and Source Code Analysis of the MyBatis Persistence Framework

This article provides a detailed introduction to MyBatis, covering its relationship with JDBC, core components, execution flow, configuration, design patterns, caching strategies, plugin mechanisms, logging options, dynamic SQL features, and includes complete Java and XML code examples to illustrate practical usage.

Full-Stack Internet Architecture
Full-Stack Internet Architecture
Full-Stack Internet Architecture
Comprehensive Overview and Source Code Analysis of the MyBatis Persistence Framework

Introduction

The author, known as 老田, summarizes a series of previous MyBatis source‑code analyses and presents a complete overview of the framework, emphasizing that MyBatis is built on top of JDBC and therefore a solid understanding of JDBC is required before diving into MyBatis internals.

JDBC Basics

Typical JDBC usage is demonstrated with a simple public class JdbcDemo { ... } example that shows loading the driver, obtaining a connection, creating a Statement, executing a query, and iterating over the ResultSet to print the name and age fields.

public class JdbcDemo {
    public static final String URL = "jdbc:mysql://localhost:3306/mblog";
    public static final String USER = "root";
    public static final String PASSWORD = "123456";

    public static void main(String[] args) throws Exception {
        Class.forName("com.mysql.jdbc.Driver");
        Connection conn = DriverManager.getConnection(URL, USER, PASSWORD);
        Statement stmt = conn.createStatement();
        ResultSet rs = stmt.executeQuery("SELECT id, name, age FROM m_user where id =1");
        while(rs.next()){
            System.out.println("name: "+rs.getString("name")+" 年龄:"+rs.getInt("age"));
        }
    }
}

Problems with Traditional JDBC

Hard‑coded connection strings and SQL statements.

Frequent opening and closing of connections, hurting performance.

Duplicated boiler‑plate code.

These drawbacks motivate the existence of persistence frameworks.

Persistence Framework Landscape

Two major families are highlighted:

ORM series : Hibernate, EclipseLink, TopLink.

Utility series : MyBatis, dbUtils, JdbcTemplate.

The article notes that JPA is a specification, not an implementation, and that Spring‑Data‑JPA (based on Hibernate) abstracts SQL completely, while MyBatis keeps SQL visible and highly controllable.

MyBatis Core Features

Simple and lightweight – only two JARs are needed.

Flexible – SQL is written in XML or annotations, allowing full control.

Decouples SQL from Java code via DAO interfaces.

Supports dynamic SQL, result mapping, and advanced tags.

Basic MyBatis Setup

Required dependencies (Maven coordinates) are shown:

<dependency>
  <groupId>org.mybatis</groupId>
  <artifactId>mybatis</artifactId>
  <version>x.x.x</version>
</dependency>
<dependency>
  <groupId>mysql</groupId>
  <artifactId>mysql-connector-java</artifactId>
  <version>8.0.16</version>
</dependency>

A sample table t_user and its Java entity class are provided:

CREATE TABLE `t_user` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(255) DEFAULT NULL,
  `age` int(11) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
INSERT INTO `t_user` VALUES ('1','tian','19','1');
public class User {
    private Integer id;
    private String name;
    private Integer age;
    // getters & setters
}

The mapper XML ( UserMapper.xml) and mapper interface ( UserMapper.java) are shown, followed by the global MyBatis configuration ( mybatis-config.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">
<mapper namespace="com.tian.mapper.UserMapper">
  <select id="selectUserById" resultType="com.tian.domain.User">
    select * from t_user where id = #{id}
  </select>
</mapper>
public interface UserMapper {
    User selectUserById(Integer id);
}
<?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.cj.jdbc.Driver"/>
        <property name="url" value="jdbc:mysql://localhost:3306/mblog?useUnicode=true&characterEncoding=utf8&autoReconnect=true&useSSL=false&serverTimezone=UTC"/>
        <property name="username" value="root"/>
        <property name="password" value="123456"/>
      </dataSource>
    </environment>
  </environments>
  <mappers>
    <mapper resource="mappers/UserMapper.xml"/>
  </mappers>
</configuration>

A test class demonstrates how to build a SqlSessionFactory, obtain a SqlSession, get the mapper proxy, execute the query, and finally close resources.

public class MybatisApplication {
    public static void main(String[] args) {
        String resource = "mybatis-config.xml";
        InputStream inputStream = null;
        SqlSession sqlSession = null;
        try {
            inputStream = Resources.getResourceAsStream(resource);
            SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
            sqlSession = sqlSessionFactory.openSession();
            UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
            User user = userMapper.selectUserById(1);
            System.out.println(user);
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try { inputStream.close(); } catch (IOException e) { e.printStackTrace(); }
            sqlSession.close();
        }
    }
}

The output is User{id=1, name='tian', age=19}, confirming successful mapping.

MyBatis Core Components

Configuration : Holds global settings, mapper registrations, type aliases, and type handlers.

MappedStatement : Represents a single SQL statement defined in XML or annotations.

SqlSession : User‑level API (Facade) for executing CRUD operations; internally delegates to Executor.

Executor : Executes the actual JDBC calls.

StatementHandler : Wraps JDBC Statement creation and parameter setting.

ParameterHandler : Converts Java values to JDBC setXXX() calls.

ResultSetHandler : Converts ResultSet rows into Java objects.

TypeHandler : Bridges Java types and JDBC types for both setting parameters and retrieving results.

Design Patterns in MyBatis

The framework extensively uses patterns such as Factory, Builder, Proxy, Singleton, Adapter, Decorator, and Chain of Responsibility, providing concrete examples for each.

Caching Mechanism

MyBatis offers a first‑level cache (session scoped, always on) and an optional second‑level cache (namespace scoped) that can be backed by implementations like Ehcache, OSCache, or Redis. The second‑level cache is realized via a decorator around the Executor (e.g., CachingExecutor).

Plugin Architecture

Four core components ( Executor, ParameterHandler, ResultSetHandler, StatementHandler) can be intercepted. Custom interceptors allow features such as pagination (e.g., PageHelper) or slow‑SQL logging.

Logging Integration

MyBatis detects and uses one of seven logging frameworks in the order: SLF4J → JCL → Log4j2 → Log4j → JUL → No Logging, with Stdout as a fallback.

Dynamic SQL

MyBatis supports rich dynamic SQL tags ( <where>, <if>, <choose>, <foreach>, etc.). Placeholders #{} become prepared‑statement parameters, while ${} performs literal string substitution.

Conclusion

The article wraps up by emphasizing that studying MyBatis source code not only deepens understanding of persistence mechanisms but also teaches design patterns, caching strategies, plugin development, and practical debugging techniques, which are valuable for real‑world backend development and interview preparation.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

BackendDesign PatternsJavaSQLPersistenceMyBatisORM
Full-Stack Internet Architecture
Written by

Full-Stack Internet Architecture

Introducing full-stack Internet architecture technologies centered on Java

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.