Spring Boot应用中集成与使用多数据源
1. 前言
通过定义和使用多个数据源,能在Spring Boot应用中实现更复杂的数据管理场景,比如读写分离、数据冗余等。
2. 准备工作
- 环境准备:确保已经准备好Spring Boot的开发环境。
- 数据库准备:在本地或云服务上创建两个数据库,如下文所示。
3. 创建Spring Boot项目
- 使用Spring Initializr创建项目:https://start.spring.io/。
- 在
pom.xml
中添加必要的依赖,包括JPA、Spring Boot Parent、数据库驱动等。
4. 配置多数据源
在application.yml
或application.properties
中配置:
yaml
# application.yml
spring:
datasource:
primary:
url: jdbc:mysql://localhost:3306/db1
username: user
password: password
driver-class-name: com.mysql.jdbc.Driver
hikari:
connection-timeout: 30000
maximum-pool-size: 20
secondary:
url: jdbc:mysql://localhost:3306/db2
username: user
password: password
driver-class-name: com.mysql.jdbc.Driver
hikari:
connection-timeout: 30000
maximum-pool-size: 20
5. 创建实体类及Repository
Entity Class - User (For Primary Database):
java
package com.example.multidatasource.entity;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity
@Table(name = "users")
public class User {
@Id
private Long id;
private String name;
private String email;
// getter, setter, constructors
}
Entity Class - Product (For Secondary Database):
java
package com.example.multidatasource.entity;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity
@Table(name = "products")
public class Product {
@Id
private Long id;
private String name;
private int price;
// getter, setter, constructors
}
Repository (Primary):
java
package com.example.multidatasource.repository;
import com.example.multidatasource.entity.User;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;
@Repository
public interface UserRepository extends JpaRepository<User, Long> {
}
Repository (Secondary):
java
package com.example.multidatasource.repository;
import com.example.multidatasource.entity.Product;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;
@Repository
public interface ProductRepository extends JpaRepository<Product, Long> {
}
6. 服务层配置与使用多数据源
java
package com.example.multidatasource.service;
import com.example.multidatasource.entity.Product;
import com.example.multidatasource.repository.ProductRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@Service
public class ProductService {
private final ProductRepository productRepository;
@Autowired
public ProductService(ProductRepository productRepository) {
this.productRepository = productRepository;
}
public Product createProduct(String name, int price) {
Product product = new Product();
product.setName(name);
product.setPrice(price);
return productRepository.save(product);
}
}
服务层同样应当遵循具体数据源的配置,确保通过合适的数据源进行持久化操作。
7. 事务与多数据源管理
针对跨数据源的事务操作,需要在@Service中配置@Transactional
注解:
java
@Service
public class MultiDataSourceTransactionService {
private final UserRepository userRepository;
private final ProductRepository productRepository;
@Autowired
public MultiDataSourceTransactionService(UserRepository userRepository, ProductRepository productRepository) {
this.userRepository = userRepository;
this.productRepository = productRepository;
}
// So that it's only using the primary dataSource
@Transactional(propagation = Propagation.REQUIRED)
public void performCreateUserAndProduct() {
userRepository.save(new User("John Doe", "john@example.com"));
productRepository.save(new Product("Widget", 1000));
}
}
通过这种方式,可以确保同一个请求中的所有操作,要么全部成功,要么全部回滚。
8. 配置及测试
确保所有的Bean和配置类被正确注解,测试应用是否能够启动,数据源是否能够正确读写数据。