0

I know that here almost the same question was, in theory, answered here: Spring Boot Configure and Use Two DataSources Nevertheless I don't think it was fully comprehensive. Anyway I still don't understand, what the minimum amount of code and the most elegant solution for Spring Boot 2 is (I'm using Spring Boot 2.1.2).

Here's my two data sources configuration class:

package pl.viola.OrderChecker.Configuration;

import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;

import javax.sql.DataSource;

@Configuration
    public class MultipleDataSourceConfiguration {

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

    @Bean
    @ConfigurationProperties(prefix = "spring.second-datasource")
    public DataSource secondaryDataSource() {
        return DataSourceBuilder.create().build();
    }
}

... and here's my application.configuration file contents:

# Postgres data source 1
spring.datasource.jdbc-url=jdbc:postgresql://******.**:****/*****
spring.datasource.username= ***
spring.datasource.password=***
#spring.jpa.properties.hibernate.dialect = org.hibernate.dialect.PostgreSQL9Dialect
spring.jpa.generate.ddl = none
spring.jpa.properties.hibernate.temp.use_jdbc_metadata_defaults=false
hibernate.hbm2ddl.auto = none



# Mysql data source 1

ssh.tunnel.url=******************
ssh.tunnel.username=*****
ssh.tunnel.password=***

spring.second-datasource.jdbc-url=jdbc:mysql://127.0.0.1:****/****.**
spring.second-datasource.username=***
spring.second-datasource.password=***

... and here's one of my repositories (for Mysql)

package pl.viola.OrderChecker.DAO.ViolaPlRepositories;

import org.springframework.data.repository.CrudRepository;
import pl.viola.OrderChecker.model.ViolaPl.Orders;

public interface OrdersRepository
     extends CrudRepository<Orders, Integer> {}

... and my Entity (for Mysql)

package pl.viola.OrderChecker.model.ViolaPl;

import lombok.Getter;
import lombok.Setter;

import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;
import java.math.BigDecimal;
import java.sql.Timestamp;

@Entity
@Getter
@Setter
@Table(name = "ps_orders")


public class Orders {

    @Id
    private int id_order;
    private String reference;
    private int id_shop_group;
    private int id_shop;
    private int id_carrier;
        private int id_lang;
(...)
    }

... and my project tree:

enter image description here

This is how I'm trying to use the second (Mysql) data source in my controller:

public @ResponseBody Iterable<Orders> getAllOrders() {

        try {
            sshTunnelStarter.init();
        } catch (Exception e) {
            e.printStackTrace();
        }

        return ordersRepository.findAll();
    }

Now, of course I don't have any problems with using the first data source (Postgres), as it's marked as primary, and whatever data source operations I'm performing, it's the primary data source that is used. And also, I read the https://www.baeldung.com/spring-data-jpa-multiple-databases tutorial and from what I found there it's still not clear to me what I'm missing. I mean sure, if you're not using Spring Boot 2, the two configuration classes are missing for defining the following interfaces for the entities: DataSource, EntityManagerFactory, TransactionManager. My question is, where's the boilerplate code in them (that according to the author isn't necessary with Spring Boot).

So once again and to the point: What's the minimum amount of code still necessary in my case for defining and using the two data sources? Thanks a bunch.

  • Sorry but your question **is** answered there. Granted, a lot of the answers on that question are crap. Code with no explanation etc. The second answer [links to the official documentation](https://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#howto-two-datasources) which does a better job of explaining. – Michael Mar 04 '19 at 10:39
  • Still, it's confusing for me, especially in juxtaposition with the accepted solution and the link to the tutorial it provides. Besides, I think if someone provided an answer specifically for my case and my question it would be more valuable for someone looking for information on the subject (and a bit more up to date). Nevertheless, it's your call... – arcadius_maximus Mar 04 '19 at 11:13
  • It seems like you're creating 2 data sources but doing nothing with the second one. The postgres one is marked as primary, so that's picked by all of the autoconfiguration. It seems like you haven't followed step 4 in the tutorial you linked to. You're kind of expecting Spring to magically know which data source you want to use. – Michael Mar 04 '19 at 11:24
  • Well... kind of, like the author says : "Much of the above-shown code isn’t necessary if we use a Spring Boot app. The opinionated Spring Boot autoconfiguration will take care of most of the grunt work and boilerplate code for us. (...) We now want to keep on using the same way to configure the second DataSource, but with a different property namespace (..) Because we want the Spring Boot autoconfiguration to pick up those different properties (and actually instantiate two different DataSources), we need to instantiate our DataSource beans manually in a configuration class. " – arcadius_maximus Mar 04 '19 at 11:32
  • I agree that I don't see how Spring could know which data source to use... but where's the "boilerplate code" in that configuration (step 4), the code that the author is writes about and supposedly substitutes in step 6? – arcadius_maximus Mar 04 '19 at 11:38
  • I don't think the Spring Boot section of that article is very good. It's **only** referring to the `DataSource`s. All of the other configuration is required. Specifically, the thing which is linking the entity classes to a data source in step 4 is the `setPackagesToScan` method invocation. – Michael Mar 04 '19 at 11:42
  • Thanks Michael. You were actually very helpful. I was affraid that I was actually missing some 'magic'. :-) – arcadius_maximus Mar 04 '19 at 12:08
  • No problem. Happy to help. – Michael Mar 04 '19 at 12:10

0 Answers0