場景假設:現有電商業務,商品和庫存分別放在不同的庫
配置數據庫連接
app:
datasource:
first:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://127.0.0.1/product?useSSL=false
username: root
password: root
configuration:
maximum-pool-size: 10
second:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://127.0.0.1/stock?useSSL=false
username: root
password: root
configuration:
maximum-pool-size: 10
添加配置類
FirstConfig
@Configuration
@EnableJpaRepositories(
basePackages = {"com.karonda.springboot2datasourcesjpa.dao.first"},// 1. dao 層所在的包
entityManagerFactoryRef = "firstEntityManagerFactory",
transactionManagerRef = "firstTransactionManager")
@EnableTransactionManagement
public class FirstConfig {
@Bean
@Primary
public PlatformTransactionManager firstTransactionManager() {
return new JpaTransactionManager(firstEntityManagerFactory().getObject());
}
@Bean
@Primary
public LocalContainerEntityManagerFactoryBean firstEntityManagerFactory() {
HibernateJpaVendorAdapter jpaVendorAdapter = new HibernateJpaVendorAdapter();
LocalContainerEntityManagerFactoryBean factoryBean = new LocalContainerEntityManagerFactoryBean();
factoryBean.setDataSource(firstDataSource());
factoryBean.setJpaVendorAdapter(jpaVendorAdapter);
factoryBean.setJpaProperties(hibernateProperties());
factoryBean.setPackagesToScan("com.karonda.springboot2datasourcesjpa.entity.first");// 2. 實體類所在的包
return factoryBean;
}
@Bean
@Primary
@ConfigurationProperties("app.datasource.first")
public DataSourceProperties firstDataSourceProperties() {
return new DataSourceProperties();
}
@Bean
@Primary
@ConfigurationProperties("app.datasource.first.configuration")
public DataSource firstDataSource() {
return firstDataSourceProperties()
.initializeDataSourceBuilder()
.type(HikariDataSource.class) // 3. 可以顯示指定連接池,也可以不顯示指定;即此行代碼可以注釋掉
.build();
}
private Properties hibernateProperties() {
final Properties hibernateProperties = new Properties();
hibernateProperties.setProperty("hibernate.dialect", "org.hibernate.dialect.MySQL5Dialect");
// hibernateProperties.setProperty("hibernate.hbm2ddl.auto", "create");
return hibernateProperties;
}
}
SecondConfig
@Configuration
@EnableJpaRepositories(
basePackages = {"com.karonda.springboot2datasourcesjpa.dao.second"},
entityManagerFactoryRef = "secondEntityManagerFactory",
transactionManagerRef = "secondTransactionManager")
@EnableTransactionManagement
public class SecondConfig {
@Bean
public PlatformTransactionManager secondTransactionManager() {
return new JpaTransactionManager(secondEntityManagerFactory().getObject());
}
@Bean
public LocalContainerEntityManagerFactoryBean secondEntityManagerFactory() {
HibernateJpaVendorAdapter jpaVendorAdapter = new HibernateJpaVendorAdapter();
LocalContainerEntityManagerFactoryBean factoryBean = new LocalContainerEntityManagerFactoryBean();
factoryBean.setDataSource(secondDataSource());
factoryBean.setJpaVendorAdapter(jpaVendorAdapter);
factoryBean.setJpaProperties(hibernateProperties());
factoryBean.setPackagesToScan("com.karonda.springboot2datasourcesjpa.entity.second");
return factoryBean;
}
@Bean
@ConfigurationProperties("app.datasource.second")
public DataSourceProperties secondDataSourceProperties() {
return new DataSourceProperties();
}
@Bean
@ConfigurationProperties("app.datasource.second.configuration")
public DataSource secondDataSource() {
return secondDataSourceProperties()
.initializeDataSourceBuilder()
.type(HikariDataSource.class)
.build();
}
private Properties hibernateProperties() {
final Properties hibernateProperties = new Properties();
hibernateProperties.setProperty("hibernate.dialect", "org.hibernate.dialect.MySQL5Dialect");
// hibernateProperties.setProperty("hibernate.hbm2ddl.auto", "create");
return hibernateProperties;
}
}
dao
public interface ProductDao extends JpaRepository<Product, Integer> {
@Query(value = "select p from Product p where p.id = id")
Product findById(@Param("id") int id);
}
public interface StockDao extends JpaRepository<Stock, Integer> {
@Query(value = "select s from Stock s where s.productId = productId")
Stock findByProductId(@Param("productId") int productId);
}
使用示例
@Component
public class Task {
@Autowired
private ProductDao productDao;
@Autowired
private StockDao stockDao;
@Scheduled(cron = "0/5 * * * * ? ")
public void job(){
final int productId = 1;
Product product = productDao.findById(productId);
Stock stock = stockDao.findByProductId(productId);
System.out.println("產品名稱: " + product.getName() + ", 庫存: " + stock.getStockCount());
}
}
注意事項
- 使用多數據源,其中一個配置類需要添加 @Primary 注解 (有且僅有一個配置類需要添加)
- 在配置類中需要同時配置 dao 層和實體類所在的包
參考:
完整代碼:GitHub
本人 C# 轉 Java 的 newbie, 如有錯誤或不足歡迎指正,謝謝