英文:
Database/Schema is not being switched when API is called
问题
I am trying to implement hibernate multitenancy in my SpringBootWebApplication.
PROBLEM - tenant is being set in filter but when query is called Datasource is not being switched.
bad SQL grammar []; nested exception is org.postgresql.util.PSQLException: ERROR: relation "xyz" does not exist.
Here are the details
-
spring-boot-starter-parent -- 2.5.12
-
MyBatis for BE queries.
-
Hibernate for multi-tenancy.
@Configuration
@EnableTransactionManagement
@EnableJpaRepositories(
basePackages = {"com.xyz.*"}
)
public class HibernateConfig {
@Autowired
private JpaProperties jpaProperties;
public HibernateConfig() {
}
@Bean
JpaVendorAdapter jpaVendorAdapter() {
return new HibernateJpaVendorAdapter();
}
@Bean(name = {"entityManagerFactory"})
public LocalContainerEntityManagerFactoryBean entityManagerFactory(DataSource dataSource, MultiTenantConnectionProvider multiTenantConnectionProviderImpl, CurrentTenantIdentifierResolver currentTenantIdentifierResolverImpl){
Map<String, Object> jpaPropertiesMap = new HashMap(this.jpaProperties.getProperties());
jpaPropertiesMap.put("hibernate.multiTenancy", MultiTenancyStrategy.SCHEMA);
jpaPropertiesMap.put("hibernate.multi_tenant_connection_provider", multiTenantConnectionProviderImpl);
jpaPropertiesMap.put("hibernate.tenant_identifier_resolver", currentTenantIdentifierResolverImpl);
jpaPropertiesMap.put("hibernate.format_sql", true);
jpaPropertiesMap.put("hibernate.show_sql", true);
LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
em.setDataSource(dataSource);
em.setJpaVendorAdapter(this.jpaVendorAdapter());
em.setJpaPropertyMap(jpaPropertiesMap);
em.setPackagesToScan(new String[]{"com.xyz.*"});
return em;
}
}
@Component
public class DataSourceBasedMultiTenantConnectionProviderImpl extends AbstractDataSourceBasedMultiTenantConnectionProviderImpl {
private static final long serialVersionUID = 1L;
private static final String DEFAULT_TENANT_ID = "master";
@Autowired
private DataSource defaultDS;
@Autowired
private ApplicationContext context;
private Map<String, DataSource> map = new HashMap();
boolean init = false;
public DataSourceBasedMultiTenantConnectionProviderImpl() {
}
@PostConstruct
public void load() {
this.map.put("master", this.defaultDS);
}
protected DataSource selectAnyDataSource() {
return (DataSource)this.map.get("master");
}
protected DataSource selectDataSource(String tenantIdentifier) {
if (!this.init) {
this.init = true;
TenantDataSource tenantDataSource = (TenantDataSource)this.context.getBean(TenantDataSource.class);
this.map.putAll(tenantDataSource.getAll());
}
return this.map.get(tenantIdentifier) != null ? (DataSource)this.map.get(tenantIdentifier) : (DataSource)this.map.get("master");
}
}
The above Datasource provider is not being called.
Thanks in advance for your Help!!!
英文:
I am trying to implement hibernate multitenancy in my SpringBootWebApplication.
PROBLEM - tenant is being set in filter but when query is called Datasource is not being switched.
bad SQL grammar []; nested exception is org.postgresql.util.PSQLException: ERROR: relation "xyz" does not exist.
Here are the details
-
spring-boot-starter-parent -- 2.5.12
-
MyBatis for BE queries.
-
Hibernate for multi-tenancy.
@Configuration
@EnableTransactionManagement
@EnableJpaRepositories(
basePackages = {"com.xyz.*"}
)
public class HibernateConfig {
@Autowired
private JpaProperties jpaProperties;
public HibernateConfig() {
}
@Bean
JpaVendorAdapter jpaVendorAdapter() {
return new HibernateJpaVendorAdapter();
}
@Bean(name = {"entityManagerFactory"})
public LocalContainerEntityManagerFactoryBean entityManagerFactory(DataSource dataSource, MultiTenantConnectionProvider multiTenantConnectionProviderImpl, CurrentTenantIdentifierResolver currentTenantIdentifierResolverImpl){
Map<String, Object> jpaPropertiesMap = new HashMap(this.jpaProperties.getProperties());
jpaPropertiesMap.put("hibernate.multiTenancy", MultiTenancyStrategy.SCHEMA);
jpaPropertiesMap.put("hibernate.multi_tenant_connection_provider", multiTenantConnectionProviderImpl);
jpaPropertiesMap.put("hibernate.tenant_identifier_resolver", currentTenantIdentifierResolverImpl);
jpaPropertiesMap.put("hibernate.format_sql", true);
jpaPropertiesMap.put("hibernate.show_sql", true);
LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
em.setDataSource(dataSource);
em.setJpaVendorAdapter(this.jpaVendorAdapter());
em.setJpaPropertyMap(jpaPropertiesMap);
em.setPackagesToScan(new String[]{"com.xyz.*"});
return em;
}
}
@Component
public class DataSourceBasedMultiTenantConnectionProviderImpl extends AbstractDataSourceBasedMultiTenantConnectionProviderImpl {
private static final long serialVersionUID = 1L;
private static final String DEFAULT_TENANT_ID = "master";
@Autowired
private DataSource defaultDS;
@Autowired
private ApplicationContext context;
private Map<String, DataSource> map = new HashMap();
boolean init = false;
public DataSourceBasedMultiTenantConnectionProviderImpl() {
}
@PostConstruct
public void load() {
this.map.put("master", this.defaultDS);
}
protected DataSource selectAnyDataSource() {
return (DataSource)this.map.get("master");
}
protected DataSource selectDataSource(String tenantIdentifier) {
if (!this.init) {
this.init = true;
TenantDataSource tenantDataSource = (TenantDataSource)this.context.getBean(TenantDataSource.class);
this.map.putAll(tenantDataSource.getAll());
}
return this.map.get(tenantIdentifier) != null ? (DataSource)this.map.get(tenantIdentifier) : (DataSource)this.map.get("master");
}
}
The above Datasource provider is not being called.
Thanks in advance for your Help!!!
答案1
得分: 0
我找到了问题。
我的项目正在使用MyBatis进行数据库查询。由于配置是通过Hibernate设置的,所以在触发查询时使用SpringDataJPA或Hibernate有助于切换数据库。
英文:
I have found the issue.
My project is using MyBatis for Database queries. Since the configuration is set via hibernate, so using SpringDataJPA or hibernate helped in switching the DB while triggering the query.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论