Mybatisで使用するデータソースを切り替える方法
MyBatisで使用するデータソースを切り替える方法
MyBatisで複数のデータソースを使用する場合、環境や処理内容に応じて適切なデータソースに切り替える必要があります。
以下では、データソースの切り替え方法について説明します。
データソースの設定
まず、DataSourceを複数設定します。
例えば、testDataSource1とtestDataSource2の2つのデータソースを用意する場合の設定は次のようになります。
application.propertiesやapplication.ymlにデータソースの設定を追加します。
application.properties(プロパティファイルでの設定例)
# testDataSource1の設定 spring.datasource.testDataSource1.url=jdbc:mysql://localhost:3306/testdb1 spring.datasource.testDataSource1.username=root spring.datasource.testDataSource1.password=password1 # testDataSource2の設定 spring.datasource.testDataSource2.url=jdbc:mysql://localhost:3306/testdb2 spring.datasource.testDataSource2.username=root spring.datasource.testDataSource2.password=password2
application.yml(YAMLファイルでの設定例)
spring: datasource: testDataSource1: url: jdbc:mysql://localhost:3306/testdb1 username: root password: password1 testDataSource2: url: jdbc:mysql://localhost:3306/testdb2 username: root password: password2
データソースの切り替え
データソースを切り替えるには、DataSourceを管理するコンポーネントを作成し、動的にデータソースを切り替えるロジックを実装します。
以下にその一例を示します。
DataSourceConfig.java
import org.apache.ibatis.session.SqlSessionFactory; import org.apache.ibatis.session.SqlSessionFactoryBuilder; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.jdbc.datasource.DataSourceTransactionManager; import org.springframework.jdbc.datasource.lookup.AbstractRoutingDataSource; import org.springframework.jdbc.datasource.lookup.DataSourceLookupFailureException; import javax.sql.DataSource; import java.util.HashMap; import java.util.Map; @Configuration public class DataSourceConfig { @Bean public DataSource dataSource() { AbstractRoutingDataSource routingDataSource = new AbstractRoutingDataSource() { @Override protected Object determineCurrentLookupKey() { return DataSourceContextHolder.getDataSourceType(); } }; Map<Object, Object> dataSourceMap = new HashMap<>(); dataSourceMap.put("testDataSource1", testDataSource1()); dataSourceMap.put("testDataSource2", testDataSource2()); routingDataSource.setTargetDataSources(dataSourceMap); return routingDataSource; } @Bean public DataSource testDataSource1() { // testDataSource1の設定 } @Bean public DataSource testDataSource2() { // testDataSource2の設定 } @Bean public DataSourceTransactionManager transactionManager(DataSource dataSource) { return new DataSourceTransactionManager(dataSource); } @Bean public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception { SqlSessionFactoryBean sessionFactory = new SqlSessionFactoryBean(); sessionFactory.setDataSource(dataSource); return sessionFactory.getObject(); } }
DataSourceContextHolder.java
public class DataSourceContextHolder { private static final ThreadLocal<String> contextHolder = new ThreadLocal<>(); public static void setDataSourceType(String dataSourceType) { contextHolder.set(dataSourceType); } public static String getDataSourceType() { return contextHolder.get(); } public static void clearDataSourceType() { contextHolder.remove(); } }
データソースの切り替えの使用
サービスやリポジトリでデータソースを切り替える際には、DataSourceContextHolderを使用して適切なデータソースを設定します。
UserService.java
@Service public class UserService { @Autowired private UserMapper userMapper; public void performOperation(String dataSourceType) { DataSourceContextHolder.setDataSourceType(dataSourceType); // ビジネスロジックやデータ操作を行う userMapper.getUsers(); DataSourceContextHolder.clearDataSourceType(); } }
このように、DataSourceContextHolderを用いて、データソースを動的に切り替えることができます。
切り替えが必要な操作が完了したら、必ずDataSourceContextHolder.clearDataSourceType()を呼び出し、スレッドローカルのデータソースタイプをクリアすることが重要です。