java - 使用 Spring 和 Hibernate 在 Multi-Tenancy 环境中访问数据的策略

标签 java hibernate jpa multi-tenant synchronized

我在一个 Multi-Tenancy 环境中工作,在该环境中,可以使用 Web 应用程序(休息)前端从大约 10 个不同的数据源(和实体管理器)访问数据。

要使用的 entitymanager 取决于 rest api 中的 URL 参数,例如。 api/订单/1/1000003.

我需要使用 entitymanager "1"来获取数据。目前,在创建 hibernate session 并通过 hibernate 条件创建查询之前,我在调用 setDistrict(1) 的存储库层中使用了一个方法。

一切正常,但我担心该方法需要同步以避免从错误的实体管理器获取数据。 当我同步存储库方法时,我担心性能会很差..

实现这种 Multi-Tenancy 访问的好策略是什么,以便性能良好并且在重负载下也能返回正确的数据?

感谢您的建议。

最佳答案

Hibernate 的 SessionFactory 允许使用 tenancy behavior :

  • SCHEMA Correlates to the separate schema approach. It is an error to attempt to open a session without a tenant identifier using this strategy. Additionally, a org.hibernate.service.jdbc.connections.spi.MultiTenantConnectionProvider must be specified.

  • DATABASE Correlates to the separate database approach. It is an error to attempt to open a session without a tenant identifier using this strategy. Additionally, a org.hibernate.service.jdbc.connections.spi.MultiTenantConnectionProvider must be specified.

  • DISCRIMINATOR Correlates to the partitioned (discriminator) approach. It is an error to attempt to open a session without a tenant identifier using this strategy. This strategy is not yet implemented in Hibernate as of 4.0 and 4.1. Its support is planned for 5.0.

在您的情况下,我认为您需要SCHEMADATABASE 并且必须实现MultiTenantConnectionProvider ( source )。

/**
 * Simplisitc implementation for illustration purposes supporting 2 hard coded providers (pools) and leveraging
 * the support class {@link org.hibernate.service.jdbc.connections.spi.AbstractMultiTenantConnectionProvider}
 */
public class MultiTenantConnectionProviderImpl extends AbstractMultiTenantConnectionProvider {
    private final ConnectionProvider acmeProvider = ConnectionProviderUtils.buildConnectionProvider( "acme" );
    private final ConnectionProvider jbossProvider = ConnectionProviderUtils.buildConnectionProvider( "jboss" );

    @Override
    protected ConnectionProvider getAnyConnectionProvider() {
        return acmeProvider;
    }

    @Override
    protected ConnectionProvider selectConnectionProvider(String tenantIdentifier) {
        if ( "acme".equals( tenantIdentifier ) ) {
            return acmeProvider;
        }
        else if ( "jboss".equals( tenantIdentifier ) ) {
            return jbossProvider;
        }
        throw new HibernateException( "Unknown tenant identifier" );
    }
}

有关详细信息,请参阅链接的文档。

关于java - 使用 Spring 和 Hibernate 在 Multi-Tenancy 环境中访问数据的策略,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38075217/

相关文章:

java - org.springframework.beans.factory.NoSuchBeanDefinitionException : No bean named 'customerService' is defined

java - HIbernate Maven项目:没有名为EntityManager的持久性提供程序

java - merge() 后无法删除分离的实体

javascript - 通过 DOJO JS 升级

java - 用户使用 JPA 生成的查询

java - 按下后退按钮 session 不会破坏

java - 清空对已删除实体的所有引用

java - Hibernate hql inner join eager fetch on one to many,获取冗余父对象

java - 父项目的打包类型必须是POM

java - 用于阻止请求的 Akka actor 池