首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >TSyringe和TypeORM在其他依赖项之前导入数据库依赖项

TSyringe和TypeORM在其他依赖项之前导入数据库依赖项
EN

Stack Overflow用户
提问于 2021-10-29 15:14:05
回答 1查看 618关注 0票数 0

我面临一个问题,其中我有很多存储库(它们是实现一个接口的TS类,它们是typeorm存储库类),我使用TSyringe来处理API中的所有依赖项

下面是一个存储库的示例

代码语言:javascript
复制
import { getRepository, Repository } from 'typeorm';
import SafeUsd from '@modules/currencies/infra/typeorm/entities/SafeUsd';
import ICreateSafeUsdDTO from '@modules/currencies/dtos/ICreateSafeUsdDTO';
import ISafeUsdRepository from '@modules/currencies/repositories/ISafeUsdRepository';
import { classToClass } from 'class-transformer';
import IUpdateSafeUsdDTO from '@modules/currencies/dtos/IUpdateSafeUsdDTO';

export default class SafeUsdRepository implements ISafeUsdRepository {
  private ormRepository: Repository<SafeUsd>;

  constructor() {
    this.ormRepository = getRepository(SafeUsd);
  }

  async create(data: ICreateSafeUsdDTO): Promise<SafeUsd> {
    const safeUsd = this.ormRepository.create(data);

    await this.ormRepository.save(safeUsd);

    return classToClass(safeUsd);
  }

  async update({
    safeUsd,
    value,
    acceptable_variance,
    margin,
  }: IUpdateSafeUsdDTO): Promise<SafeUsd> {
    if (margin !== undefined) {
      safeUsd.margin = margin;
    }

    if (value !== undefined) {
      safeUsd.value = value;
    }

    if (acceptable_variance !== undefined) {
      safeUsd.acceptable_variance = acceptable_variance;
    }

    await this.ormRepository.save(safeUsd);

    return classToClass(safeUsd);
  }

  async findOne(): Promise<SafeUsd | undefined> {
    const safeUsd = await this.ormRepository.findOne();

    return classToClass(safeUsd);
  }
}

之后,我在"shared/container/repositories/index.ts"中的一个文件中注册了我的所有存储库。

代码语言:javascript
复制
import { container } from 'tsyringe';

import ICurrenciesRepository from '@modules/currencies/repositories/ICurrenciesRepository';
import CurrenciesRepository from '@modules/currencies/infra/typeorm/repositories/CurrenciesRepository';

import ICurrenciesUrlRepository from '@modules/currencies/repositories/ICurrenciesUrlRepository';
import CurrenciesUrlRepository from '@modules/currencies/infra/typeorm/repositories/CurrenciesUrlRepository';
import ISafeUsdRepository from '@modules/currencies/repositories/ISafeUsdRepository';
import SafeUsdRepository from '@modules/currencies/infra/typeorm/repositories/SafeUsdRepository';

container.registerSingleton<ICurrenciesRepository>(
  'CurrenciesRepository',
  CurrenciesRepository,
);

container.registerSingleton<ICurrenciesUrlRepository>(
  'CurrenciesUrlRepository',
  CurrenciesUrlRepository,
);

container.registerSingleton<ISafeUsdRepository>(
  'SafeUsdRepository',
  SafeUsdRepository,
);

在我的应用程序中,我也有一些提供者(基本上是第三伙伴app的实现,例如AWS、GoogleFirebase等等)。

我想要做的是将我的一些存储库注入到我的提供程序中,然后注册由TSyringe容器解析的它们的实例。

当我尝试做我刚才写到的事情时,问题就开始了。在向TSyring容器注册存储库和提供程序时,我会这样做:

代码语言:javascript
复制
import './repositories';
import './providers';

这两个文件都是执行TSyringe container.registerSingleton、.resolve或.registerInstance方法的大量TS文件。

我总是会犯这样的错误:

代码语言:javascript
复制
Error: Cannot inject the dependency at position #2 of "BitfinexBrokerProvider" constructor.
Reason:No repository for "Currency" was found. Looks like this entity is not registered in current "default" connection?

这个错误意味着我的存储库还没有启动,所以当TSyringe试图向我的提供者注入它们时,它们甚至还没有建立与数据库的连接,所以我得到了这个错误。如果我不将这些存储库注入到我的提供者中,那么一切都能正常工作。

对如何解决这个问题有什么想法吗?我想做的是:

  1. 首先解析并注册所有存储库单例,以便它们与DB连接。
  2. 只有在此之后,注册所有提供者。

对如何做到这一点有什么想法吗?我希望我已经说清楚了我的问题,问我,如果你们有任何疑问,我会编辑这篇文章,试图变得更清楚。

提前谢谢。

更新:我尝试在"setTimeout(() => {},3000)“中添加”setTimeout(()=>{},3000)“中的”setTimeout(()=>{},3000)“中的”setTimeout(()=>{},3000)“中的所有”setTimeout(()=>{},3000)“中的”setTimeout(()=>{},3000)“。正如我在我的问题中所说的,我只是需要稍等一会儿,以便在我的存储库中建立数据库连接,然后再注入到提供程序上。

,你可以看到我做了什么,

代码语言:javascript
复制
import { container } from 'tsyringe';

import BitfinexBrokerProvider from './implementations/BitfinexBrokerProvider';
import BrokerHandlerProvider from './implementations/BrokerHandlerProvider';
import FlowBTCBrokerProvider from './implementations/FlowBTCBrokerProvider';
import BitfinexChannelHandler from './implementations/websocket/bitfinex/ChannelHandler';

import IBrokerHandlerProvider from './models/IBrokerHandlerProvider';
import IBrokerProvider from './models/IBrokerProvider';
import IChannelHandler from './models/IChannelHandler';

setTimeout(() => {
  container.registerSingleton<IBrokerProvider>(
    'FlowBTCBrokerProvider',
    FlowBTCBrokerProvider,
  );

  container.registerSingleton<IChannelHandler>(
    'BitfinexChannelHandler',
    BitfinexChannelHandler,
  );

  const bitfinexBrokerProvider = container.resolve(BitfinexBrokerProvider);

  container.registerInstance<IBrokerProvider>(
    'BitfinexBrokerProvider',
    bitfinexBrokerProvider,
  );

  const brokerHandlerProvider = container.resolve(BrokerHandlerProvider);

  container.registerInstance<IBrokerHandlerProvider>(
    'BrokerProvider',
    brokerHandlerProvider,
  );
}, 3000);

虽然它奏效了,但我发现这个解决方案很不舒服,也不优雅。有没有更好的方法来实现更好的解决方案?

EN

回答 1

Stack Overflow用户

发布于 2021-12-16 16:48:13

您可以在TSyringe中使用“延迟”助手函数。更多细节这里

示例:

代码语言:javascript
复制
@injectable()
export class Foo {
  constructor(@inject(delay(() => Bar)) public bar: Bar) {}
}

@injectable()
export class Bar {
  constructor(@inject(delay(() => Foo)) public foo: Foo) {}
}

// construction of foo is possible
const foo = container.resolve(Foo);

// property bar will hold a proxy that looks and acts as a real Bar instance.
foo.bar instanceof Bar; // true
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/69771196

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档