我有一个数据库与3个模式(运维,测试,培训)。所有这些模式都具有完全相同的表结构。现在,假设我有一个端点/cars,它接受模式/环境的查询参数。当用户向这个端点发出GET请求时,我需要Spring Boot后端能够基于客户机请求中指定的查询参数动态访问OPS、测试或训练模式。
其思想类似于这样:将环境作为请求参数传递给端点,然后在代码中以某种方式使用它来设置存储库将使用的模式/数据源。
@Autowired
private CarsRepository carsRepository;
@GetMapping("/cars")
public List<Car> getCars(@RequestParam String env) {
setSchema(env);
return carsRepository.findAll();
}
private setSchema(String env) {
// Do something here to set the schema that the CarsRepository
// will use when it runs the .findAll() method.
}
因此,如果客户端向/cars端点发出GET请求,并且环境请求参数设置为" OPS“,那么响应将是OPS模式中所有汽车的列表。如果客户端发出了相同的请求,但是env request param设置为" TEST ",那么响应将是测试方案中的所有汽车。
下面是我的数据源配置的一个示例。这个是针对运维方案的。其他模式也是以同样的方式完成的,但bean上面没有@Primary注释。
@Configuration
@EnableTransactionManagement
@EnableJpaRepositories(
entityManagerFactoryRef = "opsEntityManagerFactory",
transactionManagerRef = "opsTransactionManager",
basePackages = { "com.example.repo" }
)
public class OpsDbConfig {
@Autowired
private Environment env;
@Primary
@Bean(name = "opsDataSource")
@ConfigurationProperties(prefix = "db-ops.datasource")
public DataSource dataSource() {
return DataSourceBuilder
.create()
.url(env.getProperty("db-ops.datasource.url"))
.driverClassName(env.getProperty("db-ops.database.driverClassName"))
.username(env.getProperty("db-ops.database.username"))
.password(env.getProperty("db-ops.database.password"))
.build();
}
@Primary
@Bean(name = "opsEntityManagerFactory")
public LocalContainerEntityManagerFactoryBean opsEntityManagerFactory(
EntityManagerFactoryBuilder builder,
@Qualifier("opsDataSource") DataSource dataSource
) {
return builder
.dataSource(dataSource)
.packages("com.example.domain")
.persistenceUnit("ops")
.build();
}
@Primary
@Bean(name = "opsTransactionManager")
public PlatformTransactionManager opsTransactionManager(
@Qualifier("opsEntityManagerFactory") EntityManagerFactory opsEntityManagerFactory
) {
return new JpaTransactionManager(opsEntityManagerFactory);
}
}
发布于 2019-01-29 16:22:53
就我个人而言,我认为将环境作为请求参数传递并根据传递的值切换存储库是不正确的。
相反,您可以部署指向不同数据源的多个服务实例,并让网关守护设备(路由器)路由到相应的服务。
通过这种方式,客户端将暴露给一个网关服务,该服务根据网关守卫的输入依次路由到相应的服务。
发布于 2019-01-30 23:34:46
您通常不希望测试/ACPT实例在完全相同的机器上运行,因为通常很难控制这些环境上的负载会导致PROD环境变慢的程度。
你也不想要你设想的设置,因为它几乎不可能发展应用程序和/或它的数据库结构。(您不会同时在DEV中切换数据库模式,对吗?不同时切换是明智的,但它打破了“所有三个数据库具有完全相同的模式”的预设。
https://stackoverflow.com/questions/54404848
复制相似问题