Typeorm getRepository mockImplementation 返回模拟的 findOne 方法

时间:2021-05-24 17:05:54

标签: typescript nestjs typeorm

我正在使用带有 typeOrm 的 nestjs
这是我要测试的方法。

PropertyBuilder.ts

import { getRepository } from 'typeorm'
...

export class PropertyBuilder extends BasicEntityBuilder<PropertyDto, Property> {
  async onUpdatedOwner_id(entity: any, dtoField: string, propertyDto: PropertyDto) {
    if (dtoField !== 'owner_id') {
      throw new Error('dtoField is not valid')
    }
    entity[dtoField] = await getRepository(User).findOne({ id: propertyDto.owner_id })
  }
} 

PropertyBuilder.spec.ts

import ...

describe('PropertyBuilder', () => {
  let userRepository: Repository<User>

  beforeEach(async () => {
    const module: TestingModule = await Test.createTestingModule({
      providers: [
        {
          provide: getRepositoryToken(User),
          useClass: Repository,
        },
      ],
    }).compile()

    userRepository = module.get(getRepositoryToken(User))
  })

  describe('onUpdatedOwner_id', () => {
    it('should set owner_id field with User object', () => {
      const expected: any = { name: 'user' }
      const entity: Property = new Property()
      const dto: PropertyDto = new PropertyDto()
      jest.spyOn(userRepository, 'findOne').mockResolvedValue(expected)
      new PropertyBuilder(Property).onUpdatedOwner_id(entity, 'owner_id', dto)
      expect(entity.owner_id).toBe(expected)
    })
  })
})

测试失败,(node:952986) UnhandledPromiseRejectionWarning: ConnectionNotFoundError: Connection "default" was not found.

我知道我不应该提供任何东西...
我试过

describe('onUpdatedOwner_id', () => {
    it('should set owner_id field with User object', () => {
      const expected: any = { name: 'user' }
      const entity: Property = new Property()
      const dto: PropertyDto = new PropertyDto()

      const getRepositoryMock = jest.fn() as jest.MockedFunction<typeof getRepository>
      getRepositoryMock.mockImplementationOnce(() => {
        return { findOne: jest.fn().mockResolvedValueOnce(expected) }
      })

      jest.spyOn(userRepository, 'findOne').mockResolvedValue(expected)
      new PropertyBuilder(Property).onUpdatedOwner_id(entity, 'owner_id', dto)
      expect(entity.owner_id).toBe(expected)
    })
  })

但它不起作用,因为它的模拟实现与 getRepository 的签名不兼容

Argument of type '() => { findOne: jest.Mock<any, any>; }' is not assignable to parameter of type '(entityClass: EntityTarget<unknown>, connectionName?: string) => Repository<unknown>'.

测试我的方法的正确方法是什么?

1 个答案:

答案 0 :(得分:0)

您正在嘲笑 INVALID_REFRESH_TOKEN 的 Nest 提供者(在 getRepositoryToken(User) 的幕后使用的内容,而不是您在 {{ 中直接使用的 @InjectRepository(User) 的 TypeORM 实现”) 1}}. 直接用 jest 模拟一个包,你应该做类似

getRepository

最终会被提升到文件的顶部并在任何 TypeORM 导入之前运行,以便可以使用它。您也可以将您需要的任何其他方法添加到 PropertyBuilder 返回中。