使用场景
Atomikos 适合单服务多数据源的场景
配置
- 数据库配置
import lombok.Data;
@Data
public class DatabasesConfig {
private String url;
private String username;
private String password;
/**
* min-pool-size 初始化最小连接数
**/
private int minPoolSize;
/**
* max-pool-size 连接池最大连接数
**/
private int maxPoolSize;
/**
* max-lifetime 设置连接在池中被自动销毁之前保留的最大秒数。
**/
private int maxLifetime;
/**
* borrow-connection-timeout 获取连接失败重新获等待最大时间,在这个时间内如果有可用连接,将返回
**/
private int borrowConnectionTimeout;
/**
* login-timeout java数据库连接池,最大可等待获取datasouce的时间
**/
private int loginTimeout;
/**
* maintenance-interval 连接回收时间
**/
private int maintenanceInterval;
/**
* max-idle-time 最大闲置时间,超过最小连接池连接的连接将将关闭
**/
private int maxIdleTime;
/**
* type-aliases-package指定class别名包名
*/
private String typeAliasesPackage;
/**
* location-pattern指定mapper.xml的路径
*/
private String locationPattern;
}
- 数据源规范接口
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionTemplate;
import javax.sql.DataSource;
/**
* 数据源规范接口
*/
public interface DataSourceConfig {
/**
* 数据源配置
*
* @return
*/
public abstract DatabasesConfig databasesConfig();
/**
* 数据源
*
* @param databasesConfig
* @return
* @throws Exception
*/
public abstract DataSource dataSource(DatabasesConfig databasesConfig) throws Exception;
/**
* SqlSessionFactory
*
* @param dataSource
* @param databasesConfig
* @return
* @throws Exception
*/
public abstract SqlSessionFactory sqlSessionFactory(DataSource dataSource, DatabasesConfig databasesConfig) throws Exception;
/**
* SqlSessionTemplate
*
* @param sqlSessionFactory
* @return
* @throws Exception
*/
public SqlSessionTemplate sqlSessionTemplate(SqlSessionFactory sqlSessionFactory) throws Exception;
}
- 数据源工具类
import com.atomikos.jdbc.AtomikosDataSourceBean;
import com.mysql.cj.jdbc.MysqlXADataSource;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import javax.sql.DataSource;
import java.sql.SQLException;
public class DataSourceConfigUtil {
public static DataSource getDataSource(DatabasesConfig databasesConfig, String resourceName) throws SQLException {
MysqlXADataSource mysqlXaDataSource = new MysqlXADataSource();
mysqlXaDataSource.setUrl(databasesConfig.getUrl());
mysqlXaDataSource.setPinGlobalTxToPhysicalConnection(true);
mysqlXaDataSource.setPassword(databasesConfig.getPassword());
mysqlXaDataSource.setUser(databasesConfig.getUsername());
mysqlXaDataSource.setPinGlobalTxToPhysicalConnection(true);
AtomikosDataSourceBean xaDataSource = new AtomikosDataSourceBean();
xaDataSource.setXaDataSource(mysqlXaDataSource);
xaDataSource.setUniqueResourceName(resourceName);
xaDataSource.setMinPoolSize(databasesConfig.getMinPoolSize()); // 初始化连接池最小连接数
xaDataSource.setMaxPoolSize(databasesConfig.getMaxPoolSize()); // 连接池最大连接数
xaDataSource.setMaxLifetime(databasesConfig.getMaxLifetime()); // 设置连接在池中被自动销毁之前保留的最大秒数。
xaDataSource.setBorrowConnectionTimeout(databasesConfig.getBorrowConnectionTimeout()); // 设置池在连接为空时将阻止其等待连接可用的最长时间
xaDataSource.setLoginTimeout(databasesConfig.getLoginTimeout());
xaDataSource.setMaintenanceInterval(databasesConfig.getMaintenanceInterval()); // 连接回收时间
xaDataSource.setMaxIdleTime(databasesConfig.getMaxIdleTime());
xaDataSource.setTestQuery("select 1");
return xaDataSource;
}
public static SqlSessionFactory getSqlSessionFactory(DataSource dataSource, DatabasesConfig databasesConfig) throws Exception {
SqlSessionFactoryBean bean = new SqlSessionFactoryBean();
bean.setDataSource(dataSource);
bean.setTypeAliasesPackage(databasesConfig.getTypeAliasesPackage());
bean.setMapperLocations(new PathMatchingResourcePatternResolver().getResources(databasesConfig.getLocationPattern()));
return bean.getObject();
}
}
使用
- 新数据源
import cn.lettin.datasource.jta.config.DataSourceConfig;
import cn.lettin.datasource.jta.config.DataSourceConfigUtil;
import cn.lettin.datasource.jta.config.DatabasesConfig;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionTemplate;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.sql.DataSource;
@Configuration
@MapperScan(basePackages = "cn.lettin.account.mapper.newer", sqlSessionTemplateRef = "newerSqlSessionTemplate")
public class NewerDataSourceConfig implements DataSourceConfig {
@Override
@Bean(name = "newerDatabasesConfig")
@ConfigurationProperties(prefix = "mysql.datasource.newer")
public DatabasesConfig databasesConfig() {
return new DatabasesConfig();
}
@Override
@Bean(name = "newerDataSource")
public DataSource dataSource(@Qualifier("newerDatabasesConfig") DatabasesConfig databasesConfig) throws Exception {
return DataSourceConfigUtil.getDataSource(databasesConfig, "newerDataSource");
}
@Override
@Bean(name = "newerSqlSessionFactory")
public SqlSessionFactory sqlSessionFactory(@Qualifier("newerDataSource") DataSource dataSource, @Qualifier("newerDatabasesConfig") DatabasesConfig databasesConfig) throws Exception {
return DataSourceConfigUtil.getSqlSessionFactory(dataSource, databasesConfig);
}
@Override
@Bean(name = "newerSqlSessionTemplate")
public SqlSessionTemplate sqlSessionTemplate(@Qualifier("newerSqlSessionFactory") SqlSessionFactory sqlSessionFactory) throws Exception {
return new SqlSessionTemplate(sqlSessionFactory);
}
}
- 老数据源
import cn.lettin.datasource.jta.config.DataSourceConfig;
import cn.lettin.datasource.jta.config.DataSourceConfigUtil;
import cn.lettin.datasource.jta.config.DatabasesConfig;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionTemplate;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.sql.DataSource;
@Configuration
@MapperScan(basePackages = "cn.lettin.account.mapper.older", sqlSessionTemplateRef = "olderSqlSessionTemplate")
public class OlderDataSourceConfig implements DataSourceConfig {
@Override
@Bean(name = "olderDatabasesConfig")
@ConfigurationProperties(prefix = "mysql.datasource.older")
public DatabasesConfig databasesConfig() {
return new DatabasesConfig();
}
@Override
@Bean(name = "olderDataSource")
public DataSource dataSource(@Qualifier("olderDatabasesConfig") DatabasesConfig databasesConfig) throws Exception {
return DataSourceConfigUtil.getDataSource(databasesConfig, "olderDataSource");
}
@Override
@Bean(name = "olderSqlSessionFactory")
public SqlSessionFactory sqlSessionFactory(@Qualifier("olderDataSource") DataSource dataSource, @Qualifier("olderDatabasesConfig") DatabasesConfig databasesConfig) throws Exception {
return DataSourceConfigUtil.getSqlSessionFactory(dataSource, databasesConfig);
}
@Override
@Bean(name = "olderSqlSessionTemplate")
public SqlSessionTemplate sqlSessionTemplate(@Qualifier("olderSqlSessionFactory") SqlSessionFactory sqlSessionFactory) throws Exception {
return new SqlSessionTemplate(sqlSessionFactory);
}
}
事务上限和超时时间配置
#JTA配置
#事务数量不上限制
spring.jta.atomikos.properties.max-actives=-1
#事务超时时间
spring.jta.atomikos.properties.max-timeout=900000