Jest模拟TypeORM链式方法失败,Express单元测试求助
解决TypeORM链式调用的Jest单元测试问题
问题场景
在Express+TypeORM项目中,编写Jest单元测试验证RoleRepository的findByRole方法时,执行测试触发AuthServiceException,错误信息为:
AuthServiceException: Error occurred when finding role by rolename from DB
错误原因
findByRole方法中使用了TypeORM的链式调用:createQueryBuilder().select().where().getOne()。当前测试仅mock了createQueryBuilder方法,但未处理后续的链式调用环节——select、where方法需要返回QueryBuilder实例自身才能继续链式调用,否则调用这些方法时会因找不到对应方法抛出异常,被方法内的catch块捕获后抛出自定义错误。
修复方案
需要完整mock链式调用的每个环节,确保createQueryBuilder返回的对象包含select、where(返回自身)和getOne(返回mock数据)方法。
修复后的测试代码
const RoleRepository = require('../../src/repository/RoleRepository'); const { getRepository } = require('../../src/repository/Repository'); jest.mock('../../src/repository/Repository', () => { return { getRepository: jest.fn(), } }); const role = new Role(); role.setProperty(EntityProperty.ID, "rid-123"); let mockedGetRepository: jest.Mock; let RoleRepositoryInstance: typeof RoleRepository; mockedGetRepository = getRepository as jest.Mock; describe('RoleRepository, findByRole method test', () => { beforeEach(() => { // 构建完整的链式调用mock const mockQueryBuilder = { select: jest.fn().mockReturnThis(), where: jest.fn().mockReturnThis(), getOne: jest.fn().mockResolvedValue(role) }; mockedGetRepository.mockReturnValue({ createQueryBuilder: jest.fn().mockReturnValue(mockQueryBuilder) }); RoleRepositoryInstance = new RoleRepository(); }); test('Should return role, when finding by role is successful', async () => { const result = await RoleRepositoryInstance.findByRole(RoleType.USER); expect(result).toBe(role); expect(result.getProperty(EntityProperty.ID)).toBe("rid-123"); // 可选:验证链式方法是否被正确调用 const mockQueryBuilder = mockedGetRepository.mock.results[0].value.createQueryBuilder(); expect(mockQueryBuilder.select).toHaveBeenCalledWith("Role"); expect(mockQueryBuilder.where).toHaveBeenCalledWith("role.role=:role", { role: RoleType.USER }); expect(mockQueryBuilder.getOne).toHaveBeenCalled(); }); })
关键说明
mockReturnThis()用于让select和where方法返回mockQueryBuilder自身,维持链式调用的连续性。getOne方法用mockResolvedValue返回预设的role对象,模拟数据库查询成功的场景。- 可选添加对链式方法调用的断言,确保方法逻辑符合预期。
内容的提问来源于stack exchange,提问作者CleanCodeOnline
相关产品推荐
相关产品推荐

