什么是 nestjs typeorm 中的 getRepositoryToken 以及何时使用它?

Posted

技术标签:

【中文标题】什么是 nestjs typeorm 中的 getRepositoryToken 以及何时使用它?【英文标题】:what is getRepositoryToken in nestjs typeorm and when to use it? 【发布时间】:2021-04-10 17:14:36 【问题描述】:

文档here如下:

在对应用程序进行单元测试时,我们通常希望避免 建立数据库连接,保持我们的测试套件独立和 他们的执行过程尽可能快。但是我们的课可能 依赖于从连接实例中提取的存储库。 我们如何处理?解决方案是创建模拟存储库。在 为了实现这一点,我们设置了自定义提供程序。每个注册 存储库自动由存储库表示 令牌,其中 EntityName 是您的实体类的名称。

@nestjs/typeorm 包公开了 getRepositoryToken() 函数 它根据给定实体返回准备好的令牌。

这到底是什么意思?自动完成文档只是给出签名,没有任何解释。

【问题讨论】:

【参考方案1】:

getRepositoryToken() 是一个帮助方法,它允许您获取与@InjectRepository() 返回的相同的注入令牌。这在测试时很有用,这样您就可以定义一个具有匹配 DI 解析令牌的自定义提供程序,因此您可以提供 Repository 方法的模拟,而无需实际与数据库对话。例如,如果你有

@Injectable()
export class FooService 
  constructor(@InjectRepository(Foo) private readonly fooRepo: Repository<Foo>) 


在您的测试中,您可以添加提供者


  provide: getRepositoryToken(Foo),
  useValue: 
    find: jest.fn(),
    insert: jest.fn(),
  ,

现在您已经为 Repository 提供了一个模拟可注入提供程序。

必须这样做的最大原因是因为 typescript 不反映泛型类,它只反映Repository,并且如果 Nest 试图找出你要注入的存储库,只使用那个名称 ( Repository) 它很可能会出错并注入错误的类。使用@InjectRepsitory() 可以设置正确的注入令牌。

【讨论】:

那么让我看看我是否正确理解了您的答案。这在模拟和测试调用注入存储库的服务或事物时专门使用?所以在某些情况下我看到了不使用 getRepository 的地方,但我认为在那些情况下它只是直接测试存储库而不是调用存储库方法的服务? 听起来不错。您还可以使用getRepositoryToken() 将存储库正确注入useFactory 方法以异步注册模块 爱你的免打扰应用顺便说一句。 :) 我仍然对最终结果的差异感到好奇。在实践中,即使在测试上述场景时,我发现它仍然可以在没有 getRespositoryToken 方法的情况下工作,而且我没有看到任何问题。 我可能不得不看看你是如何测试的。 This repo 有很多不同的测试,包括对 typeorm、mongoose 和 sequelize 的测试。在单元测试期间它们都没有连接到数据库,因此在它们期间不需要数据库连接。

以上是关于什么是 nestjs typeorm 中的 getRepositoryToken 以及何时使用它?的主要内容,如果未能解决你的问题,请参考以下文章

播种时NestJS中的TypeOrm:RepositoryNotFoundError

NestJS + TypeORM 中的 JoinTable 问题

Nestjs 与自定义存储库中的 Typeorm 事务

NestJS & TypeORM:发布请求中的 DTO 格式

迁移文件中的 NestJS TypeORM 语法错误

使用 Typeorm 连接到 Nestjs 中的 mssql,但 Nest 无法解析 EmployeeRepository 的依赖关系