Mybatis connection pool and transaction control

1 Mybatis connection pool

In Mybatis's sqlmapconfig XML configuration file to configure the connection pool in Mybatis


Generally, POOLED data source is used
The data source configuration is in sqlmapconfig In the XML file, the specific configuration is as follows:

<!-- Configure data source (connection pool) information --> <dataSource type="POOLED"> <property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>

During initialization, MyBatis creates a data source of the corresponding type according to the type attribute of the,
Namely:
type = "POOLED": MyBatis will create a PooledDataSource instance
type = "UNPOOLED": MyBatis will create an UnpooledDataSource instance
type = "JNDI": MyBatis will find the DataSource instance from the JNDI service, and then return it for use

MyBatis creates a data source DataSource object through the factory pattern. MyBatis defines an abstract factory interface: org apache. ibatis. DataSource. Datasourcefactory, which returns the DataSource datasource through its getDataSource() method.
The source code of DataSourceFactory is as follows:

package org.apache.ibatis.datasource;
import java.util.Properties;
import javax.sql.DataSource;
/**
* @author Clinton Begin
*/
public interface DataSourceFactory {
 void setProperties(Properties props);
 DataSource getDataSource();
}

After MyBatis creates a DataSource instance, it will be placed in the Environment object in the Configuration object for later use.

When we need to create a SqlSession object and execute SQL statements, MyBatis will call the dataSource object to create Java sql. Connection object. That is, Java sql. The creation of the connection object is delayed until the SQL statement is executed.

@Test
public void testSql() throws Exception {
InputStream in = Resources.getResourceAsStream("SqlMapConfig.xml");
SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in);
SqlSession sqlSession = factory.openSession();
List<User> list = sqlSession.selectList("findUserById",41);
System.out.println(list.size());
}

Only when the fourth sentence sqlsession Selectlist ("findUserById") will trigger MyBatis to execute the following method at the bottom to create Java sql. The connection object, the time point when the real connection is opened, is only performed when we execute the SQL statement. It is further found that database connection is our most valuable resource. We only get and open the connection when we need it. When we run out, we will return the database connection to the connection pool immediately.

2 MyBatis transaction control

The transaction submission method in Mybatis essentially calls setAutoCommit() of JDBC to realize transaction control.
Code written before running:

@Test
public void testSaveUser() throws Exception {
User user = new User();
user.setUsername("mybatis user09");
//6. Perform the operation
int res = userDao.saveUser(user);
System.out.println(res);
System.out.println(user.getId());
}
@Before//Execute before test method execution
public void init()throws Exception {
//1. Read the configuration file
in = Resources.getResourceAsStream("SqlMapConfig.xml");
//2. Create builder object
SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder();
//3. Create SqlSession factory object
factory = builder.build(in);
//4. Create SqlSession object
session = factory.openSession();
//5. Create Dao's proxy object
userDao = session.getMapper(IUserDao.class);
}
@After//Execute after the test method execution is completed
public void destroy() throws Exception{
//7. Submission of services
session.commit();
//8. Release resources
session.close();
in.close();
}

Observe its output on the console:

Through analysis, we can find that during the previous CUD operation, we have to commit the transaction manually. The reason is that the value of etAutoCommit() method is set to false during execution, so we must pass sqlsession Commit () method to perform the commit operation.

Mybatis auto commit transaction settings
Sqlsession. Must be used during CUD The main reason why commit () commits a transaction is that all connections taken out from the connection pool will call connection Setautocommit (false) method, so we must use sqlsession The commit () method is equivalent to using the connection The commit () method implements transaction commit.
CUD operation without manual submission:

@Before//Execute before test method execution
public void init()throws Exception {
//1. Read the configuration file
in = Resources.getResourceAsStream("SqlMapConfig.xml");
//2. Create builder object
SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder();
//3. Create SqlSession factory object
factory = builder.build(in);
//4. Create SqlSession object
session = factory.openSession(true);
//5. Create Dao's proxy object
userDao = session.getMapper(IUserDao.class);
}
@After//Execute after the test method execution is completed
public void destroy() throws Exception{
//7. Release resources
session.close();
in.close();
}

Source code of the corresponding DefaultSqlSessionFactory class:

@Override
public SqlSession openSession(boolean autoCommit){
return openSessionFromDataSource(configuration.getDefaultExecutorType).null,autoCommit);
}

Operation results:

At this time, the transaction is set to automatic submission, and the record can also be saved during CUD operation. Although this is also a method, in terms of programming, it is more commonly used to set the automatic submission method to false, and then decide whether to submit according to the situation. Because we can decide whether to submit or not according to the business situation

Keywords: Java Apache Mybatis intellij-idea

Added by FloridaNutz on Mon, 27 Dec 2021 12:20:22 +0200