[JAVA] Verwendung derselben Mapper-Klasse in mehreren Datenquellen mit Spring Boot + MyBatis

Einführung

In dem Fall habe ich erlebt Da wir ein System mit unterschiedlichen Datenquellen und derselben Tabellendefinition erstellt haben, Wir werden das Know-how zu diesem Zeitpunkt teilen.

Datenquellendefinition

Der Treiber verwendet "Oracle", aber bitte ändern Sie es entsprechend Ihrer Umgebung.

application.yml


spring:
  datasource:
    #Datenquelle A.
    alpha:
      jdbc-url: jdbc:oracle:thin:@localhost:1521/XEPDB1
      username: sample_a
      password: sample_a
      driverClassName: oracle.jdbc.OracleDriver
    #Datenquelle B.
    beta:
      jdbc-url: jdbc:oracle:thin:@localhost:1521/XEPDB1
      username: sample_b
      password: sample_b
      driverClassName: oracle.jdbc.OracleDriver

MyBatis-Einstellungen

DataSourceConfig.java


package com.example;

@Configuration
@MapperScan(basePackages = { "com.example.mapper" }, sqlSessionTemplateRef = "sqlSessionTemplate") // ①
public class DataSourceConfig {

    @Bean(name = "alphaDataSource")
    @ConfigurationProperties(prefix = "spring.datasource.alpha")
    public DataSource alphaDataSource() {
        return DataSourceBuilder.create().build();
    }

    @Bean(name = "betaDataSource")
    @ConfigurationProperties(prefix = "spring.datasource.beta")
    public DataSource betaDataSource() {
        return DataSourceBuilder.create().build();
    }

    @Bean("dynamicDataSource")
    public DynamicRoutingDataSourceResolver dynamicDataSource(@Qualifier("alphaDataSource") DataSource alphaDataSource, @Qualifier("betaDataSource") DataSource betaDataSource) {
        Map<Object, Object> targetDataSources = new HashMap<Object, Object>();
        targetDataSources.put(DataSourceType.ALPHA, alphaDataSource);
        targetDataSources.put(DataSourceType.BETA, betaDataSource);

        //Dynamischer Wechsel der Datenquelle
        DynamicRoutingDataSourceResolver resolver = new DynamicRoutingDataSourceResolver();
        resolver.setTargetDataSources(targetDataSources);
        resolver.setDefaultTargetDataSource(alphaDataSource);

        return resolver;
    }

    @Bean
    public SqlSessionFactory sqlSessionFactory(@Qualifier("dynamicDataSource") DynamicRoutingDataSourceResolver resolver) throws Exception {
        SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();

        // ②
        factoryBean.setDataSource(resolver);
        factoryBean.setMapperLocations("Mapper-XML-Pfad");
        factoryBean.getObject().getConfiguration().setMapUnderscoreToCamelCase(true);

        return factoryBean.getObject();
    }

    // ...Kürzung
}

①: Legen Sie einen Alias für die häufig verwendete Mapper-Klasse fest (2): AutoConfigure ist für Multi-Datenquellen deaktiviert. Stellen Sie es daher manuell ein.

Datenquellenumschaltung

Definieren Sie einen Partitionswert, um die Referenzdatenquelle zu bestimmen.

public enum DataSourceType {
    ALPHA, BETA
}

Der Teilungswert wird für jeden Thread gehalten.

DataSourceContextHolder.java


public class DataSourceContextHolder {

    private static ThreadLocal<DataSourceType> contextHolder = new ThreadLocal<DataSourceType>();

    public static void setDataSourceType(DataSourceType dataSourceType) {
        contextHolder.set(dataSourceType);
    }

    public static DataSourceType getDataSourceType() {
        return contextHolder.get();
    }

    public static void clear() {
        contextHolder.remove();
    }
}

Erfassen Sie den Klassifizierungswert zur Bestimmung der Referenzdatenquelle. Aus der in DataSourceConfig.dynamicDataSource festgelegten Datenquelle mit diesem Indikatorwert Bestimmen Sie die Datenquelle, auf die tatsächlich verwiesen werden soll.

DynamicRoutingDataSourceResolver.java


public class DynamicRoutingDataSourceResolver extends AbstractRoutingDataSource {

    @Override
    protected Object determineCurrentLookupKey() {
        return DataSourceContextHolder.getDataSourceType();
    }
}

wie benutzt man

Lassen Sie uns den DataSourceType über den DataSourceContextHolder festlegen. Wenn Sie es als Querschnittsprozess definieren möchten, verwenden Sie AOP usw., um die Datenquelle zu wechseln.

DataSourceContextHolder.setDataSourceType(DataSourceType.ALPHA);

Recommended Posts

Verwendung derselben Mapper-Klasse in mehreren Datenquellen mit Spring Boot + MyBatis
Verwendung von MyBatis2 (iBatis) mit Spring Boot 1.4 (Spring 4)
Verwendung des eingebauten h2db mit Federstiefel
Verwendung von CommandLineRunner im Spring Batch von Spring Boot
Aufrufen und Verwenden der API in Java (Spring Boot)
Verwendung des Java-Aufzählungstyps (Enum) in Mapper XML von MyBatis
Zuordnung zu einer Klasse mit einem Wertobjekt in How to My Batis
Wie man Lombok im Frühling benutzt
Hinweise zur Verwendung von Spring Data JDBC
Verwendung der Wrapper-Klasse
Verwendung der MyBatis Mapper-Annotation
Verwendung von ModelMapper (Spring Boot)
Verwendung von MinIO mit derselben Funktion wie S3 Verwenden Sie Docker-Compose
So rufen Sie mehrere Namen gleichzeitig in derselben Kategorie auf
[Java] Verwendung der File-Klasse
[Verarbeitung × Java] Verwendung der Klasse
[Java] Verwendung der Calendar-Klasse
So wenden Sie Thymeleaf-Änderungen sofort mit #Spring Boot + maven auf den Browser an
So lesen Sie Request Body mit Spring Boot + Spring Security mehrmals
Bis zur Datenerfassung mit Spring Boot + MyBatis + PostgreSQL
Verwendung von Spring Boot-Sitzungsattributen (@SessionAttributes)
So fügen Sie in Spring Boot einen Klassenpfad hinzu
So binden Sie mit einer Eigenschaftendatei in Spring Boot
[JAVA] [Spring] [MyBatis] Verwenden Sie IN () mit SQL Builder
So definieren Sie mehrere orm.xml in Spring4, JPA2.1
[Spring Boot] So verweisen Sie auf die Eigenschaftendatei
[Schienen] So registrieren Sie mehrere Datensätze in der Zwischentabelle mit einer Zuordnung von vielen zu vielen
Speichern von Objekten in PostgreSQL als JSON mit MyBatis (Mapper XML)
So führen Sie UT mit Excel als Testdaten mit Spring Boot + JUnit5 + DBUnit durch
So legen Sie Umgebungsvariablen in der Eigenschaftendatei der Spring-Boot-Anwendung fest
So ändern Sie die Aktion mit mehreren Senden-Schaltflächen
Verwendung der Z3-Bibliothek in Scala mit Eclipse
So erstellen Sie ein Spring Boot-Projekt in IntelliJ
Organisierte schrittweise Interaktion mit dem JDK
Verwendung der JDD-Bibliothek in Scala mit Eclipse
Booten nach Umgebung mit Spring Boot of Maven
Verwendung des In-Memory-Job-Repositorys mit Spring Batch
Verwendung von git mit der Leistung von jgit in einer Umgebung ohne git-Befehle
Zusammenfassung der Verwendung des im IE festgelegten Proxy-Sets bei der Verbindung mit Java
Verwendung der Getter / Setter-Methode (in Objektorientierung)
So ändern Sie den Einstellungswert von application.properties beim Booten im Frühjahrsstart
Verwenden Sie collection_select, um die in Active_Hash gespeicherten Daten abzurufen
Verwendung von JSON-Daten in der WebSocket-Kommunikation (Java, JavaScript)
So übergeben Sie ein Objekt in MyBatis an Mapper, ohne ein Argument durchzugehen
So schreiben Sie in die Modellklasse, wenn Sie mit PlayFramework Binärdaten in der Datenbank speichern möchten
So erstellen Sie ein Platzhalterteil zur Verwendung in der IN-Klausel
Verwendung der Java-Klasse
Großschreibung nur des angegebenen Bereichs mit Teilzeichenfolge. (Verwendung von Teilzeichenfolgen)
Fluss bis zur Ausgabe von Tabellendaten, die mit Spring Boot angezeigt werden sollen
So fügen Sie dieselben Indizes in ein verschachteltes Array ein
Verwenden Sie thymeleaf3 mit parent, ohne Spring-Boot-Starter-Parent in Spring Boot anzugeben
Verwenden Sie Spring JDBC mit Spring Boot
wsimport-Fehlerbehandlung (Eine Klasse / Schnittstelle mit dem gleichen Namen "xxx" wird bereits verwendet)
Lassen Sie uns herausfinden, wie Sie mit Request Body mit der REST-API von Spring Boot empfangen können
Verwenden Sie im Spring Boot @ControllerAdvice, @ExceptionHandler, HandlerExceptionResolver, um Ausnahmen abzufangen