我遇到了一个难题,试图用一些本地代码来实现手动模拟。基本上,有一个组件可以与异步资源交互(在本例中是lowdb)。现在,我可以模拟我从lowdb中使用的所有函数,但是这个函数的输出实际上非常简单,我宁愿模拟那个调用。但是,我正在构建的测试并不直接调用此函数。
这可能还不清楚,因此这里有一个示例(这是我想要模拟的方法):
export const getNextId = (): Promise<number> => {
return new Promise<number>((resolve, reject) => {
// not the actual call, but akin to it
getDB().then((db: LowdbAsync<Schema>) => {
resolve(db.get('count').value()) as number
}
}然后,在另一个文件中,我使用它来设置ID (这用于某些I/O)。
import { getNextId } from '../../db'
export interface Job {
id: number
}
export class Job implements Job {
constructor(public id: number) { }
}
export const getNewJob = (): Promise<Job> => {
return new Promise<Job>((resolve, reject) => {
getNextId().then((id: number) => {
resolve(new Job(id))
}
}
}尽管这很丑陋,但这才是我们所需要的。
因此,在我的测试文件中,我有一行代码来创建一个新的Job。我可以想出如何通过修改构造函数来破解这个问题,但我宁愿这样做。
到目前为止,这是我最近才能让它发挥作用的地方。这只是防止它在运行时崩溃(即测试),但它实际上并不调用我的手动模拟函数。
看:
const db = jest.createMockFromModule('../../db')
// this is ugly but i'm using TS on strict
db['getNextId'] = (): Promise<number> => {
return new Promise<number>((resolve, reject) => {
resolve(0)
}
}
import { someUtilMethod } from '../../app/util'
import { Job, getNewJob } from '../../app/job'
describe('foo', () => {
getNewJob().then((job: Job) => {
let testVal: string = someUtilMethod(job)
// then assert some value here
}
} 虽然嘲笑本地模块确实会使其运行( getNextId未定义没有问题),但它从未真正调用我的手动模拟函数。我试过几种方法,这是唯一能让测试运行的方法.但是,从未设置id值,日志记录/调试验证手动模拟的函数从未命中。
我很容易做些蠢事,但从我所读到的资料来看,这应该是可行的。我甚至尝试过基本的非Promise基调用(这显然不是我的问题),调用该方法以获得助手方法之外的ID (例如,在测试中)都是徒劳的。在jest如何加载模块的过程中,我遗漏了一些东西。
发布于 2020-10-07 20:59:37
没有尝试使用jest.createMockFromModule。我喜欢使用jest.spyOn,参阅开玩笑docs的例子,它可以模拟模块的特定功能,并且可以在每个测试中完成(即用mockRestore()将函数恢复到正常状态)。
顺便说一句,我还在describe中添加了describe以使其工作,并为测试解析添加了await。
测试:
import * as db from '../src/db';
import { Job, getNewJob } from '../src/stackoverflow2';
// import { someUtilMethod } from '../../app/util'
const someUtilMethod = (job: Job) => JSON.stringify(job);
describe('foo', () => {
it('bar', async () => {
const getNextIdSpy = jest.spyOn(db, 'getNextId');
getNextIdSpy.mockResolvedValue(5);
await getNewJob().then((job: Job) => {
let testVal: string = someUtilMethod(job);
// then assert some value here
expect(testVal).toBe('{"id":5}');
});
getNextIdSpy.mockRestore();
});
});https://stackoverflow.com/questions/50379617
复制相似问题