Я не понимаю, как работает инъекционная зависимость. Есть ли кто-нибудь, кто может мне четко объяснить - PullRequest
0 голосов
/ 06 мая 2020

Я пытаюсь реализовать небольшое приложение Nest JS, в которое я хочу интегрировать планировщик задач. Одной из первых задач этого планировщика будет обновление данных в базе данных. Эта служба задач будет использовать UserService, как показано ниже:

import {
  Injectable,
  Inject,
  UnprocessableEntityException,
  HttpStatus,
} from '@nestjs/common';
import { Repository } from 'typeorm';
import * as bcrypt from 'bcryptjs';
import { User, UserStatus } from './user.entity';
import { LoggerService } from '../../../logger/logger.service';
import { HammerErrors } from 'src/error/hammer.errors';
import * as Config from '../../../config/global.env';

@Injectable()
export class UserService {
  private readonly _logger = new LoggerService(UserService.name);

  constructor(
    @Inject('USER_REPOSITORY')
    private _userRepository: Repository<User>,
  ) {}
  ....
  async reactiveBlockedUsers() {
    this._logger.setMethod(this.reactiveBlockedUsers.name);
    this._logger.log(`Update blocked users`);
    await this._userRepository
      .createQueryBuilder('hm_users')
      .update(User)
      .set({
        nextValidDate: null,
      })
      .where(
        `hm_users.nextValidDate IS NOT NULL hm_users.nextValidDate < utc_timestamp()`,
      )
      .execute();
    return null;
  }

}

Моя служба задач выглядит следующим образом:

import { LoggerService } from '../../../logger/logger.service';
import { UserService } from '../../providers/user/user.service';
import { Injectable } from '@nestjs/common';
import { Cron, CronExpression } from '@nestjs/schedule';

@Injectable()
export class TasksService {
  private _logger = new LoggerService(TasksService.name);

  constructor(private _userService: UserService) {}

  @Cron(CronExpression.EVERY_MINUTE)
  async reactiveUsers() {
    this._logger.setMethod(this.reactiveUsers.name);
    this._logger.log(`Reactive blocked users`);
    try {
      await this._userService.reactiveBlockedUsers();
    } catch (error) {
      this._logger.log(error);
    }
  }

  @Cron(CronExpression.EVERY_MINUTE)
  startBatchJobs() {
    this._logger.setMethod(this.startBatchJobs.name);
    this._logger.log(`Start batch job service`);
  }

  triggerNotifications() {}
}

Модуль задачи следующий:

import { Module } from '@nestjs/common';
import { TasksService } from './tasks.service';
import { UserService } from 'src/shared/providers/user/user.service';
import { Repository } from 'typeorm';

@Module({
  providers: [
    TasksService,
    UserService,
    {
      provide: 'USER_REPOSITORY',
      useClass: Repository,
    },
  ],
})
export class TasksModule {}

Когда процесс работает, у меня возникает следующая ловушка: [INFO] 06/05/2020 19: 57: 00.024 [TasksService.reactiveUsers] TypeError: невозможно прочитать свойство createQueryBuilder из undefined

Или: (узел: 13668) UnhandledPromiseRejectionWarning: TypeError: Невозможно прочитать свойство createQueryBuilder неопределенного значения в Repository.createQueryBuilder (D: \ dev \ hammer \ hammer-server \ node_modules \ typeorm \ repository \ Repository. js : 17: 29) в UserService.reactiveBlockedUsers (D: \ dev \ hammer \ hammer-server \ dist \ src \ shared \ sizes \ user \ user.service. js: 183: 14) в TasksService.reactiveUsers (D: \ dev \ hammer \ hammer-server \ dist \ src \ shared \ services \ tasks \ tasks.service. js: 25: 33) в CronJob.fireOnTick (D: \ dev \ hammer \ hammer-server \ node_modules \ cron \ lib \ cron. js: 562: 23) в Timeout.callbackWrapper [как _onTimeout] ( D: \ dev \ hammer \ hammer-server \ node_modules \ cron \ lib \ cron. js: 629: 10) в listOnTimeout (внутренние / таймеры. js: 549: 17) в processTimers (внутренние / таймеры. js: 492: 7) (узел: 13668) UnhandledPromiseRejectionWarning: необработанное отклонение обещания. Эта ошибка возникла либо из-за выброса внутри функции asyn c без блока catch, либо из-за отклонения обещания, которое не было обработано с помощью .catch (). Чтобы завершить процесс узла при отклонении необработанного обещания, используйте флаг CLI --unhandled-rejections=strict (см. https://nodejs.org/api/cli.html#cli_unhandled_rejections_mode). (идентификатор отклонения: 2) (узел: 13668) [DEP0018] DeprecationWarning: необработанные отклонения обещаний устарели. В будущем, отклонения обещаний, которые не были обработаны, завершат процесс Node.js с ненулевым кодом выхода.

когда я подавлю перехват попытки.

Для меня это проблема предоставления модуля Repositiry, который вводится в UserService, но я не понимаю, как это работает и как решить эту проблему.

Если у кого-то есть идея, мне будет интересно.

Спасибо за ваша помощь.

Ответы [ 2 ]

1 голос
/ 06 мая 2020

Repository является абстрактным классом в TypeORM и не может быть создан напрямую. Nest делает все возможное для решения этой проблемы, но в конечном итоге предоставит undefined и, таким образом, вызов createQueryBuilder создаст вам проблему. Если вы используете TypeORM, по какой причине вы не используете пакет @nestjs/typeorm? Он управляет созданием классов репозитория для вас и значительно упрощает работу. Вы сильно обеспокоены тем, что не используете пакет, вы всегда можете создать свой собственный класс репозитория UserRepository extends Repository с соответствующими метаданными и всем остальным, а затем использовать этот класс вместо Repository

0 голосов
/ 08 мая 2020

Спасибо за информацию, которую я не знал об этом существующем пакете. Постараюсь реализовать ваше предложение. Я новичок в этой технологии и день ото дня открываю для себя что-то новое. С начала марта я изучил HTML, CSS, Javascript, Typescript Nest Js и Angular и сейчас пытаюсь реализовать небольшой проект со всеми этими технологиями. Я думаю, что у меня много пробелов в моих знаниях, и я ценю ваш ответ, который дал мне эту информацию.

...