Introduction
MyBatis is a popular persistence framework that provides a flexible way to map SQL statements to Java objects.In this article, I’ll explore how to implements MyBatis integration in aSpring-like framework,base on my miniSpring project’s implementation.
Core Components
The MyBatis integration consists of several key components:
src/com/yaruyng/batis/├── DefaultSqlSessionFactory.java├── DefaultSqlSession.java├── SqlSessionFactory.java├── SqlSession.java└── MapperNode.javasrc/com/yaruyng/batis/ ├── DefaultSqlSessionFactory.java ├── DefaultSqlSession.java ├── SqlSessionFactory.java ├── SqlSession.java └── MapperNode.javasrc/com/yaruyng/batis/ ├── DefaultSqlSessionFactory.java ├── DefaultSqlSession.java ├── SqlSessionFactory.java ├── SqlSession.java └── MapperNode.java
Enter fullscreen mode Exit fullscreen mode
SqlSessionFactory Implementation
The SqlSessionFactory is the entry point for creating SqlSession instance:
<span>public</span> <span>class</span> <span>DefaultSqlSessionFactory</span> <span>implements</span> <span>SqlSessionFactory</span> <span>{</span><span>@Autowired</span><span>JdbcTemplate</span> <span>jdbcTemplate</span><span>;</span><span>String</span> <span>mapperLocations</span><span>;</span><span>Map</span><span><</span><span>String</span><span>,</span> <span>MapperNode</span><span>></span> <span>mapperNodeMap</span> <span>=</span> <span>new</span> <span>HashMap</span><span><>();</span><span>public</span> <span>void</span> <span>init</span><span>()</span> <span>{</span><span>scanLocation</span><span>(</span><span>this</span><span>.</span><span>mapperLocations</span><span>);</span><span>// Initialize mapper nodes</span><span>}</span><span>@Override</span><span>public</span> <span>SqlSession</span> <span>openSession</span><span>()</span> <span>{</span><span>SqlSession</span> <span>newSqlSession</span> <span>=</span> <span>new</span> <span>DefaultSqlSession</span><span>();</span><span>newSqlSession</span><span>.</span><span>setJdbcTemplate</span><span>(</span><span>jdbcTemplate</span><span>);</span><span>newSqlSession</span><span>.</span><span>setSqlSessionFactory</span><span>(</span><span>this</span><span>);</span><span>return</span> <span>newSqlSession</span><span>;</span><span>}</span><span>}</span><span>public</span> <span>class</span> <span>DefaultSqlSessionFactory</span> <span>implements</span> <span>SqlSessionFactory</span> <span>{</span> <span>@Autowired</span> <span>JdbcTemplate</span> <span>jdbcTemplate</span><span>;</span> <span>String</span> <span>mapperLocations</span><span>;</span> <span>Map</span><span><</span><span>String</span><span>,</span> <span>MapperNode</span><span>></span> <span>mapperNodeMap</span> <span>=</span> <span>new</span> <span>HashMap</span><span><>();</span> <span>public</span> <span>void</span> <span>init</span><span>()</span> <span>{</span> <span>scanLocation</span><span>(</span><span>this</span><span>.</span><span>mapperLocations</span><span>);</span> <span>// Initialize mapper nodes</span> <span>}</span> <span>@Override</span> <span>public</span> <span>SqlSession</span> <span>openSession</span><span>()</span> <span>{</span> <span>SqlSession</span> <span>newSqlSession</span> <span>=</span> <span>new</span> <span>DefaultSqlSession</span><span>();</span> <span>newSqlSession</span><span>.</span><span>setJdbcTemplate</span><span>(</span><span>jdbcTemplate</span><span>);</span> <span>newSqlSession</span><span>.</span><span>setSqlSessionFactory</span><span>(</span><span>this</span><span>);</span> <span>return</span> <span>newSqlSession</span><span>;</span> <span>}</span> <span>}</span>public class DefaultSqlSessionFactory implements SqlSessionFactory { @Autowired JdbcTemplate jdbcTemplate; String mapperLocations; Map<String, MapperNode> mapperNodeMap = new HashMap<>(); public void init() { scanLocation(this.mapperLocations); // Initialize mapper nodes } @Override public SqlSession openSession() { SqlSession newSqlSession = new DefaultSqlSession(); newSqlSession.setJdbcTemplate(jdbcTemplate); newSqlSession.setSqlSessionFactory(this); return newSqlSession; } }
Enter fullscreen mode Exit fullscreen mode
key features:
- Integration with Spring’s IoC container
- Mapper XML file scanning
- Session management
Mapper XML Parsing
The framework parse MyBatis mapper XML files:
<span>private</span> <span>Map</span><span><</span><span>String</span><span>,</span> <span>MapperNode</span><span>></span> <span>buildMapperNodes</span><span>(</span><span>String</span> <span>filePath</span><span>)</span> <span>{</span><span>SAXReader</span> <span>saxReader</span> <span>=</span> <span>new</span> <span>SAXReader</span><span>();</span><span>URL</span> <span>xmlPath</span> <span>=</span> <span>this</span><span>.</span><span>getClass</span><span>().</span><span>getClassLoader</span><span>().</span><span>getResource</span><span>(</span><span>filePath</span><span>);</span><span>try</span> <span>{</span><span>Document</span> <span>document</span> <span>=</span> <span>saxReader</span><span>.</span><span>read</span><span>(</span><span>xmlPath</span><span>);</span><span>Element</span> <span>rootElement</span> <span>=</span> <span>document</span><span>.</span><span>getRootElement</span><span>();</span><span>String</span> <span>namespace</span> <span>=</span> <span>rootElement</span><span>.</span><span>attributeValue</span><span>(</span><span>"namespace"</span><span>);</span><span>Iterator</span><span><</span><span>Element</span><span>></span> <span>nodes</span> <span>=</span> <span>rootElement</span><span>.</span><span>elementIterator</span><span>();</span><span>while</span> <span>(</span><span>nodes</span><span>.</span><span>hasNext</span><span>())</span> <span>{</span><span>Element</span> <span>node</span> <span>=</span> <span>nodes</span><span>.</span><span>next</span><span>();</span><span>String</span> <span>id</span> <span>=</span> <span>node</span><span>.</span><span>attributeValue</span><span>(</span><span>"id"</span><span>);</span><span>String</span> <span>parameterType</span> <span>=</span> <span>node</span><span>.</span><span>attributeValue</span><span>(</span><span>"parameterType"</span><span>);</span><span>String</span> <span>resultType</span> <span>=</span> <span>node</span><span>.</span><span>attributeValue</span><span>(</span><span>"resultType"</span><span>);</span><span>String</span> <span>sql</span> <span>=</span> <span>node</span><span>.</span><span>getText</span><span>();</span><span>MapperNode</span> <span>selectnode</span> <span>=</span> <span>new</span> <span>MapperNode</span><span>();</span><span>selectnode</span><span>.</span><span>setNamespace</span><span>(</span><span>namespace</span><span>);</span><span>selectnode</span><span>.</span><span>setId</span><span>(</span><span>id</span><span>);</span><span>selectnode</span><span>.</span><span>setParameterType</span><span>(</span><span>parameterType</span><span>);</span><span>selectnode</span><span>.</span><span>setResultType</span><span>(</span><span>resultType</span><span>);</span><span>selectnode</span><span>.</span><span>setSql</span><span>(</span><span>sql</span><span>);</span><span>selectnode</span><span>.</span><span>setParameter</span><span>(</span><span>""</span><span>);</span><span>this</span><span>.</span><span>mapperNodeMap</span><span>.</span><span>put</span><span>(</span><span>namespace</span> <span>+</span> <span>"."</span> <span>+</span> <span>id</span><span>,</span> <span>selectnode</span><span>);</span><span>}</span><span>}</span> <span>catch</span> <span>(</span><span>Exception</span> <span>ex</span><span>)</span> <span>{</span><span>ex</span><span>.</span><span>printStackTrace</span><span>();</span><span>}</span><span>return</span> <span>this</span><span>.</span><span>mapperNodeMap</span><span>;</span><span>}</span><span>private</span> <span>Map</span><span><</span><span>String</span><span>,</span> <span>MapperNode</span><span>></span> <span>buildMapperNodes</span><span>(</span><span>String</span> <span>filePath</span><span>)</span> <span>{</span> <span>SAXReader</span> <span>saxReader</span> <span>=</span> <span>new</span> <span>SAXReader</span><span>();</span> <span>URL</span> <span>xmlPath</span> <span>=</span> <span>this</span><span>.</span><span>getClass</span><span>().</span><span>getClassLoader</span><span>().</span><span>getResource</span><span>(</span><span>filePath</span><span>);</span> <span>try</span> <span>{</span> <span>Document</span> <span>document</span> <span>=</span> <span>saxReader</span><span>.</span><span>read</span><span>(</span><span>xmlPath</span><span>);</span> <span>Element</span> <span>rootElement</span> <span>=</span> <span>document</span><span>.</span><span>getRootElement</span><span>();</span> <span>String</span> <span>namespace</span> <span>=</span> <span>rootElement</span><span>.</span><span>attributeValue</span><span>(</span><span>"namespace"</span><span>);</span> <span>Iterator</span><span><</span><span>Element</span><span>></span> <span>nodes</span> <span>=</span> <span>rootElement</span><span>.</span><span>elementIterator</span><span>();</span> <span>while</span> <span>(</span><span>nodes</span><span>.</span><span>hasNext</span><span>())</span> <span>{</span> <span>Element</span> <span>node</span> <span>=</span> <span>nodes</span><span>.</span><span>next</span><span>();</span> <span>String</span> <span>id</span> <span>=</span> <span>node</span><span>.</span><span>attributeValue</span><span>(</span><span>"id"</span><span>);</span> <span>String</span> <span>parameterType</span> <span>=</span> <span>node</span><span>.</span><span>attributeValue</span><span>(</span><span>"parameterType"</span><span>);</span> <span>String</span> <span>resultType</span> <span>=</span> <span>node</span><span>.</span><span>attributeValue</span><span>(</span><span>"resultType"</span><span>);</span> <span>String</span> <span>sql</span> <span>=</span> <span>node</span><span>.</span><span>getText</span><span>();</span> <span>MapperNode</span> <span>selectnode</span> <span>=</span> <span>new</span> <span>MapperNode</span><span>();</span> <span>selectnode</span><span>.</span><span>setNamespace</span><span>(</span><span>namespace</span><span>);</span> <span>selectnode</span><span>.</span><span>setId</span><span>(</span><span>id</span><span>);</span> <span>selectnode</span><span>.</span><span>setParameterType</span><span>(</span><span>parameterType</span><span>);</span> <span>selectnode</span><span>.</span><span>setResultType</span><span>(</span><span>resultType</span><span>);</span> <span>selectnode</span><span>.</span><span>setSql</span><span>(</span><span>sql</span><span>);</span> <span>selectnode</span><span>.</span><span>setParameter</span><span>(</span><span>""</span><span>);</span> <span>this</span><span>.</span><span>mapperNodeMap</span><span>.</span><span>put</span><span>(</span><span>namespace</span> <span>+</span> <span>"."</span> <span>+</span> <span>id</span><span>,</span> <span>selectnode</span><span>);</span> <span>}</span> <span>}</span> <span>catch</span> <span>(</span><span>Exception</span> <span>ex</span><span>)</span> <span>{</span> <span>ex</span><span>.</span><span>printStackTrace</span><span>();</span> <span>}</span> <span>return</span> <span>this</span><span>.</span><span>mapperNodeMap</span><span>;</span> <span>}</span>private Map<String, MapperNode> buildMapperNodes(String filePath) { SAXReader saxReader = new SAXReader(); URL xmlPath = this.getClass().getClassLoader().getResource(filePath); try { Document document = saxReader.read(xmlPath); Element rootElement = document.getRootElement(); String namespace = rootElement.attributeValue("namespace"); Iterator<Element> nodes = rootElement.elementIterator(); while (nodes.hasNext()) { Element node = nodes.next(); String id = node.attributeValue("id"); String parameterType = node.attributeValue("parameterType"); String resultType = node.attributeValue("resultType"); String sql = node.getText(); MapperNode selectnode = new MapperNode(); selectnode.setNamespace(namespace); selectnode.setId(id); selectnode.setParameterType(parameterType); selectnode.setResultType(resultType); selectnode.setSql(sql); selectnode.setParameter(""); this.mapperNodeMap.put(namespace + "." + id, selectnode); } } catch (Exception ex) { ex.printStackTrace(); } return this.mapperNodeMap; }
Enter fullscreen mode Exit fullscreen mode
This implementation:
- Uses DOM4J for XML parsing
- Extracts SQL statements and metadata
- Creates MapperNode objects
MapperNode Structure
The MapperNode class represents a single SQL statement:
<span>public</span> <span>class</span> <span>MapperNode</span> <span>{</span><span>String</span> <span>namespace</span><span>;</span><span>String</span> <span>id</span><span>;</span><span>String</span> <span>parameterType</span><span>;</span><span>String</span> <span>resultType</span><span>;</span><span>String</span> <span>sql</span><span>;</span><span>String</span> <span>parameter</span><span>;</span><span>// Getters and setters</span><span>}</span><span>public</span> <span>class</span> <span>MapperNode</span> <span>{</span> <span>String</span> <span>namespace</span><span>;</span> <span>String</span> <span>id</span><span>;</span> <span>String</span> <span>parameterType</span><span>;</span> <span>String</span> <span>resultType</span><span>;</span> <span>String</span> <span>sql</span><span>;</span> <span>String</span> <span>parameter</span><span>;</span> <span>// Getters and setters</span> <span>}</span>public class MapperNode { String namespace; String id; String parameterType; String resultType; String sql; String parameter; // Getters and setters }
Enter fullscreen mode Exit fullscreen mode
Features:
- Namespace and ID for unique identification
- Parameter and result type information
- SQL statement storage
- Parameter mapping support
SqlSession Implementation
The DefaultSqlSession handles SQL execution:
<span>public</span> <span>class</span> <span>DefaultSqlSession</span> <span>implements</span> <span>SqlSession</span> <span>{</span><span>JdbcTemplate</span> <span>jdbcTemplate</span><span>;</span><span>SqlSessionFactory</span> <span>sqlSessionFactory</span><span>;</span><span>@Override</span><span>public</span> <span>Object</span> <span>selectOne</span><span>(</span><span>String</span> <span>sqlid</span><span>,</span> <span>Object</span><span>[]</span> <span>args</span><span>,</span><span>PreparedStatementCallBack</span> <span>pstmtcallback</span><span>)</span> <span>{</span><span>String</span> <span>sql</span> <span>=</span> <span>this</span><span>.</span><span>sqlSessionFactory</span><span>.</span><span>getMapperNode</span><span>(</span><span>sqlid</span><span>).</span><span>getSql</span><span>();</span><span>return</span> <span>jdbcTemplate</span><span>.</span><span>query</span><span>(</span><span>sql</span><span>,</span> <span>args</span><span>,</span> <span>pstmtcallback</span><span>);</span><span>}</span><span>}</span><span>public</span> <span>class</span> <span>DefaultSqlSession</span> <span>implements</span> <span>SqlSession</span> <span>{</span> <span>JdbcTemplate</span> <span>jdbcTemplate</span><span>;</span> <span>SqlSessionFactory</span> <span>sqlSessionFactory</span><span>;</span> <span>@Override</span> <span>public</span> <span>Object</span> <span>selectOne</span><span>(</span><span>String</span> <span>sqlid</span><span>,</span> <span>Object</span><span>[]</span> <span>args</span><span>,</span> <span>PreparedStatementCallBack</span> <span>pstmtcallback</span><span>)</span> <span>{</span> <span>String</span> <span>sql</span> <span>=</span> <span>this</span><span>.</span><span>sqlSessionFactory</span><span>.</span><span>getMapperNode</span><span>(</span><span>sqlid</span><span>).</span><span>getSql</span><span>();</span> <span>return</span> <span>jdbcTemplate</span><span>.</span><span>query</span><span>(</span><span>sql</span><span>,</span> <span>args</span><span>,</span> <span>pstmtcallback</span><span>);</span> <span>}</span> <span>}</span>public class DefaultSqlSession implements SqlSession { JdbcTemplate jdbcTemplate; SqlSessionFactory sqlSessionFactory; @Override public Object selectOne(String sqlid, Object[] args, PreparedStatementCallBack pstmtcallback) { String sql = this.sqlSessionFactory.getMapperNode(sqlid).getSql(); return jdbcTemplate.query(sql, args, pstmtcallback); } }
Enter fullscreen mode Exit fullscreen mode
Key aspects:
- SQL statement retrieval
- Parameter binding
- Result mapping
- JDBC template integration
Integration with Spring Ioc:
The Mybatis integration leverages Spring’s IoC container:
<span>@Autowired</span><span>JdbcTemplate</span> <span>jdbcTemplate</span><span>;</span><span>@Autowired</span> <span>JdbcTemplate</span> <span>jdbcTemplate</span><span>;</span>@Autowired JdbcTemplate jdbcTemplate;
Enter fullscreen mode Exit fullscreen mode
Benefits:
- Automatic dependency injection
- Transaction management
- Connection pooling
- Resource management
XML Configuration
Example mapper XML configuration:
<span><?xml version="1.0" encoding="UTF-8" ?></span><span><!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"></span><span><mapper</span> <span>namespace=</span><span>"com.example.UserMapper"</span><span>></span><span><select</span> <span>id=</span><span>"findById"</span> <span>parameterType=</span><span>"java.lang.Integer"</span><span>resultType=</span><span>"com.example.User"</span><span>></span>SELECT * FROM users WHERE id = ?<span></select></span><span></mapper></span><span><?xml version="1.0" encoding="UTF-8" ?></span> <span><!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"></span> <span><mapper</span> <span>namespace=</span><span>"com.example.UserMapper"</span><span>></span> <span><select</span> <span>id=</span><span>"findById"</span> <span>parameterType=</span><span>"java.lang.Integer"</span> <span>resultType=</span><span>"com.example.User"</span><span>></span> SELECT * FROM users WHERE id = ? <span></select></span> <span></mapper></span><?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.example.UserMapper"> <select id="findById" parameterType="java.lang.Integer" resultType="com.example.User"> SELECT * FROM users WHERE id = ? </select> </mapper>
Enter fullscreen mode Exit fullscreen mode
Usage Example
Here’s how to use the Mybatis integration:
<span>@Repository</span><span>public</span> <span>class</span> <span>UserDao</span> <span>{</span><span>@Autowired</span><span>private</span> <span>SqlSessionFactory</span> <span>sqlSessionFactory</span><span>;</span><span>public</span> <span>User</span> <span>findById</span><span>(</span><span>Integer</span> <span>id</span><span>)</span> <span>{</span><span>SqlSession</span> <span>session</span> <span>=</span> <span>sqlSessionFactory</span><span>.</span><span>openSession</span><span>();</span><span>try</span> <span>{</span><span>return</span> <span>(</span><span>User</span><span>)</span> <span>session</span><span>.</span><span>selectOne</span><span>(</span><span>"com.example.UserMapper.findById"</span><span>,</span><span>new</span> <span>Object</span><span>[]{</span><span>id</span><span>},</span><span>new</span> <span>UserRowMapper</span><span>()</span><span>);</span><span>}</span> <span>finally</span> <span>{</span><span>session</span><span>.</span><span>close</span><span>();</span><span>}</span><span>}</span><span>}</span><span>@Repository</span> <span>public</span> <span>class</span> <span>UserDao</span> <span>{</span> <span>@Autowired</span> <span>private</span> <span>SqlSessionFactory</span> <span>sqlSessionFactory</span><span>;</span> <span>public</span> <span>User</span> <span>findById</span><span>(</span><span>Integer</span> <span>id</span><span>)</span> <span>{</span> <span>SqlSession</span> <span>session</span> <span>=</span> <span>sqlSessionFactory</span><span>.</span><span>openSession</span><span>();</span> <span>try</span> <span>{</span> <span>return</span> <span>(</span><span>User</span><span>)</span> <span>session</span><span>.</span><span>selectOne</span><span>(</span> <span>"com.example.UserMapper.findById"</span><span>,</span> <span>new</span> <span>Object</span><span>[]{</span><span>id</span><span>},</span> <span>new</span> <span>UserRowMapper</span><span>()</span> <span>);</span> <span>}</span> <span>finally</span> <span>{</span> <span>session</span><span>.</span><span>close</span><span>();</span> <span>}</span> <span>}</span> <span>}</span>@Repository public class UserDao { @Autowired private SqlSessionFactory sqlSessionFactory; public User findById(Integer id) { SqlSession session = sqlSessionFactory.openSession(); try { return (User) session.selectOne( "com.example.UserMapper.findById", new Object[]{id}, new UserRowMapper() ); } finally { session.close(); } } }
Enter fullscreen mode Exit fullscreen mode
Key Features
- Mapper XML Support
- XML-Based SQL configuration
- Dynamic SQL support
- Parameter mapping
- Session Management
- Connection handing
- Transaction boundaries
- Resource cleanup
- Result Mapping
- Object mapping
- Type conversion
- Collection handing
- Spring Integration
- IoC container support
- Transaction management
- Resource management
Implementation Details
- Mapper Scanning
<span>private</span> <span>void</span> <span>scanLocation</span><span>(</span><span>String</span> <span>location</span><span>)</span> <span>{</span><span>String</span> <span>sLocation</span> <span>=</span> <span>this</span><span>.</span><span>getClass</span><span>().</span><span>getClassLoader</span><span>()</span><span>.</span><span>getResource</span><span>(</span><span>""</span><span>).</span><span>getPath</span><span>()</span> <span>+</span> <span>location</span><span>;</span><span>File</span> <span>dir</span> <span>=</span> <span>new</span> <span>File</span><span>(</span><span>sLocation</span><span>);</span><span>for</span> <span>(</span><span>File</span> <span>file</span> <span>:</span> <span>dir</span><span>.</span><span>listFiles</span><span>())</span> <span>{</span><span>if</span> <span>(</span><span>file</span><span>.</span><span>isDirectory</span><span>())</span> <span>{</span><span>scanLocation</span><span>(</span><span>location</span> <span>+</span> <span>"/"</span> <span>+</span> <span>file</span><span>.</span><span>getName</span><span>());</span><span>}</span> <span>else</span> <span>{</span><span>buildMapperNodes</span><span>(</span><span>location</span> <span>+</span> <span>"/"</span> <span>+</span> <span>file</span><span>.</span><span>getName</span><span>());</span><span>}</span><span>}</span><span>}</span><span>private</span> <span>void</span> <span>scanLocation</span><span>(</span><span>String</span> <span>location</span><span>)</span> <span>{</span> <span>String</span> <span>sLocation</span> <span>=</span> <span>this</span><span>.</span><span>getClass</span><span>().</span><span>getClassLoader</span><span>()</span> <span>.</span><span>getResource</span><span>(</span><span>""</span><span>).</span><span>getPath</span><span>()</span> <span>+</span> <span>location</span><span>;</span> <span>File</span> <span>dir</span> <span>=</span> <span>new</span> <span>File</span><span>(</span><span>sLocation</span><span>);</span> <span>for</span> <span>(</span><span>File</span> <span>file</span> <span>:</span> <span>dir</span><span>.</span><span>listFiles</span><span>())</span> <span>{</span> <span>if</span> <span>(</span><span>file</span><span>.</span><span>isDirectory</span><span>())</span> <span>{</span> <span>scanLocation</span><span>(</span><span>location</span> <span>+</span> <span>"/"</span> <span>+</span> <span>file</span><span>.</span><span>getName</span><span>());</span> <span>}</span> <span>else</span> <span>{</span> <span>buildMapperNodes</span><span>(</span><span>location</span> <span>+</span> <span>"/"</span> <span>+</span> <span>file</span><span>.</span><span>getName</span><span>());</span> <span>}</span> <span>}</span> <span>}</span>private void scanLocation(String location) { String sLocation = this.getClass().getClassLoader() .getResource("").getPath() + location; File dir = new File(sLocation); for (File file : dir.listFiles()) { if (file.isDirectory()) { scanLocation(location + "/" + file.getName()); } else { buildMapperNodes(location + "/" + file.getName()); } } }
Enter fullscreen mode Exit fullscreen mode
- SQL Execution
<span>public</span> <span>Object</span> <span>selectOne</span><span>(</span><span>String</span> <span>sqlid</span><span>,</span> <span>Object</span><span>[]</span> <span>args</span><span>,</span><span>PreparedStatementCallBack</span> <span>pstmtcallback</span><span>)</span> <span>{</span><span>String</span> <span>sql</span> <span>=</span> <span>this</span><span>.</span><span>sqlSessionFactory</span><span>.</span><span>getMapperNode</span><span>(</span><span>sqlid</span><span>).</span><span>getSql</span><span>();</span><span>return</span> <span>jdbcTemplate</span><span>.</span><span>query</span><span>(</span><span>sql</span><span>,</span> <span>args</span><span>,</span> <span>pstmtcallback</span><span>);</span><span>}</span><span>public</span> <span>Object</span> <span>selectOne</span><span>(</span><span>String</span> <span>sqlid</span><span>,</span> <span>Object</span><span>[]</span> <span>args</span><span>,</span> <span>PreparedStatementCallBack</span> <span>pstmtcallback</span><span>)</span> <span>{</span> <span>String</span> <span>sql</span> <span>=</span> <span>this</span><span>.</span><span>sqlSessionFactory</span><span>.</span><span>getMapperNode</span><span>(</span><span>sqlid</span><span>).</span><span>getSql</span><span>();</span> <span>return</span> <span>jdbcTemplate</span><span>.</span><span>query</span><span>(</span><span>sql</span><span>,</span> <span>args</span><span>,</span> <span>pstmtcallback</span><span>);</span> <span>}</span>public Object selectOne(String sqlid, Object[] args, PreparedStatementCallBack pstmtcallback) { String sql = this.sqlSessionFactory.getMapperNode(sqlid).getSql(); return jdbcTemplate.query(sql, args, pstmtcallback); }
Enter fullscreen mode Exit fullscreen mode
Best Practice
- Resource Management
- Proper session cleanup
- Connection pooling
- Transaction boundaries
- Error Handling
- SQL exception handling
- Resource cleanup in finally blocks
- Proper error propagation
- Performance Optimization
- Statement caching
- Connection pooling
- Batch processing support
Common Challenges and Solutions
- Connection Management
- Use connection pooling
- Implement proper cleanup
- Handle transaction boundaries
- SQL Mapping
- Proper parameter binding
- Result type conversion
- Collection handling
- Transaction Management
- Spring transaction integration
- Proper isolation levels
- Rollback handling
Conclusion
Implementing MyBatis integration in a Spring-like framework provides:
- Clean separation of concerns
- Flexible SQL mapping
- Transaction management
- Resource optimization Key takeaways:
- Understanding MyBatis core concepts
- Spring integration patterns
- Resource management
- Performance considerations
This implementation demonstrates how to create a robust ORM framework integration while maintaining simplicity and flexibility.
原文链接:Spring Architecture Series-5.Implementing Mybatis Integration
暂无评论内容