TypeScript自定义对象内的函数如何被严格识别为函数类型?
解决TypeScript测试桩对象函数属性的类型识别问题
问题原因
默认情况下TypeScript对对象字面量会自动推导属性类型,虽然底层能识别出函数属性的本质,但无显式类型约束时,hover展示的是自动推导的匿名函数类型,和普通属性的展示逻辑一致,且无严格的函数签名校验,不符合单元测试的类型安全要求。
解决方案
方案1:显式定义对象类型(最推荐)
提前声明测试桩的类型别名/接口,明确指定每个函数属性的签名,声明对象时显式标注类型:
// 定义测试桩的严格类型 type UnitTestStub = { isEmpty: boolean; testName: string; // 明确指定每个函数的入参、返回值类型 getTime: () => number; success: () => void; fail: () => void; wait: () => void; } // 声明对象时绑定类型 const obj: UnitTestStub = { isEmpty: true, testName: 'unitTest', getTime: () => 5, success: () => {}, fail: () => {}, wait: () => {}, };
该方案的优势:
- hover查看属性时会明确展示你定义的函数签名,和普通属性有明显区分
- 后续如果不小心给函数属性赋值非函数类型、或函数的入参返回值不符合约定,TypeScript会直接抛出类型错误,保障测试桩的类型安全
方案2:结合单元测试框架的Mock类型
如果使用Jest、Vitest等测试框架编写桩用例,可以直接使用框架提供的Mock类型标注,同时保留mock的能力:
type UnitTestStub = { isEmpty: boolean; testName: string; getTime: jest.Mock<number, []>; success: jest.Mock<void, []>; fail: jest.Mock<void, []>; wait: jest.Mock<void, []>; } const obj: UnitTestStub = { isEmpty: true, testName: 'unitTest', getTime: jest.fn(() => 5), success: jest.fn(), fail: jest.fn(), wait: jest.fn(), };
额外配置强化严格性
可以在tsconfig.json中开启strictFunctionTypes配置项,开启后TypeScript会对函数类型进行严格的协变/逆变校验,进一步保障函数类型的准确性。
内容的提问来源于stack exchange,提问作者Sabo Boz
相关产品推荐
相关产品推荐

