扩展全局公开的第三方模块

我正在尝试添加一个自定义匹配器来在Typescript中开玩笑。这很好,但我无法让Typescript识别扩展的匹配器

myMatcher.ts

导出默认函数myMatcher(this:jest.MatcherUtils,received:any,expected:any):{pass:boolean;message():string;}{
const pass=已接收===预期值;
返回{
通过:通过,,
消息:()=>`expected${pass?'!':'='}=`,
}
}

myMatcher.d.ts

声明名称空间笑话{
接口匹配器{
myMatcher(应为:任意):布尔值;
}
}

someTest.ts

从“/myMatcher”导入myMatcher;
期待({
myMatcher,
})
它('应该工作',()=&gt{
expect('str')。myMatcher('str');
})

tsconfig.json

{
“编译器选项”:{
“outDir”:“../dist/”,
“moduleResolution”:“节点”,
“模块”:“es6”,
“目标”:“es5”,
“lib”:[
“es7”,
“dom”
]
},
“类型”:[
“开玩笑”
],
“包括”:[
“src/***”
],
“排除”:[
“节点_模块”,
“区”,
“博士”,
“***/\uuuuu mocks\uuuu/*”,
“***/\uuuuuuuuuuuuuuuuuuu测试””
]
}

在一些tests.ts中,我得到了错误

错误TS2339:类型“Matchers”上不存在属性“myMatcher”

我已经阅读了很多次Microsoft文档,但我不知道如何将名称空间与全局可用类型合并(不导出)

将它放在jest的index.d.ts中可以很好地工作,但对于快速变化的代码库和被多方扩展的类来说,这不是一个好的解决方案

好的,这里有几个问题

当源文件(.ts.tsx)文件和声明文件(.d.ts)文件都是模块解析的候选文件时,就像这里的情况一样,编译器将解析源文件

您可能有两个文件,因为您希望导出一个值并修改全局对象的类型jest。但是,您不需要两个文件,因为TypeScript有一个特定的构造,用于从模块中扩展全局范围。也就是说,您只需要以下.ts文件

myMatcher.ts

//在模块中使用declare global来引入或扩充全局声明。
宣布全球{
名称空间玩笑{
接口匹配器{
myMatcher:myMatcher的类型;
}
}
}
导出默认函数myMatcher<T>(this:jest.MatcherUtils,received:T,expected:T){
const pass=已接收===预期值;
返回{
通过
消息:()=>`应为${pass?'!':'='}==`
};
}

也就是说,如果您遇到这种情况,最好在同一个文件中执行全局突变和全局类型扩增。鉴于此,我将考虑改写如下:

myMatcher.ts

//确保将其解析为模块。
出口{};
宣布全球{
名称空间玩笑{
接口匹配器{
myMatcher:myMatcher的类型;
}
}
}
函数myMatcher<T>(this:jest.MatcherUtils,received:T,expected:T){
const pass=已接收===预期值;
返回{
通过
消息:()=>`应为${pass?'!':'='}==`
};
}
期待({
我的媒人
});

someTest.ts

导入“/myMatcher”;
它('应该工作',()=&gt{
expect('str')。myMatcher('str');
});

发表评论