NestJS请求范围内的多租户

时间:2019-06-13 14:52:47

标签: multi-tenant nestjs

希望使用NestJS 6的新请求注入范围功能实现多租户NestJS解决方案。

对于任何给定的服务,我都认为我可以做这样的事情:

@Injectable({scope: Scope.REQUEST})
export class ReportService implements OnModuleInit { ... }

然后,在构造函数中,根据请求确定租户,连接到适当的数据库,并为新连接实例化存储库。

我想知道这是否是最简单的方法吗?

代替更新每个服务,是否可以覆盖请求的连接提供者和范围

2 个答案:

答案 0 :(得分:0)

这就是我们最终要做的...

  1. 创建一个绑定到请求范围的简单全局TenancyModule

tenancy.module.ts

import { Global, Module, Scope } from '@nestjs/common';
import { REQUEST } from '@nestjs/core';
import { getConnection } from 'typeorm';

const connectionFactory = {
  provide: 'CONNECTION',
  scope: Scope.REQUEST,
  useFactory: (req) => {
    const tenant = someMethodToDetermineTenantFromHost(req.headers.host);
    return getConnection(tenant);
  },
  inject: [REQUEST],
};

@Global()
@Module({
  providers: [connectionFactory],
  exports: ['CONNECTION'],
})
export class TenancyModule {}
  1. 将特定于请求的'CONNECTION'注入到模块服务中,以从中检索存储库:

user.service.ts

...
@Injectable({scope: Scope.REQUEST})
export class UserService {
  private readonly userRepository: Repository<User>;

  constructor(@Inject('CONNECTION') connection) {
    this.userRepository = connection.getRepository(User);
  }

答案 1 :(得分:0)

我建议将@nurikabe的方法与请求范围的工厂提供程序和请求范围的服务一起使用。 Nestjs本身也有类似的工厂示例in the docs

但是为了完整起见,还有另一种方法:您也可以使用中间件并将连接连接到请求对象,如this answer中所述,该问题类似。但是,通过中间件将诸如连接之类的内容附加到请求上,可以绕开DI机制并通过使请求对象的行为像提供连接的服务容器一样来疏远请求对象–因此,应首选工厂方法。