我有一个描述对象Person的json模式。我希望能够以这种方式直接将该模式加载到typescript文件中:
import Person from './schema/person.schema.json';
为此,我创建了一个加载器,它将json文件转换为typescript接口声明(使用json-schema-to-typescript),然后将结果传递给ts-loader。
我的webpack以这种方式配置:
webpack.config.js(摘录)
module: {
rules: [
{
test: /\.ts$/,
loader: 'ts-loader',
},
{
test: /\.schema\.json$/,
loader: 'ts-loader!jsonschema-loader',
exclude: /(node_modules)/,
},
]
},
在这个question之后我配置了一个声明,以便json文件被认为是一个字符串:
declaration.d.ts:
declare module '*.schema.json' {
const schema: string;
export default schema;
}
我的加载器改变了它动态处理的文件名,所以ts-loader认为它加载的是person.schema.ts
。而且,我检查了我的装载机的结果是否正确。这里是:
/**
* This file was automatically generated by json-schema-to-typescript.
* DO NOT MODIFY IT BY HAND. Instead, modify the source JSONSchema file,
* and run json-schema-to-typescript to regenerate this file.
*/
export interface Person {
firstName: string;
lastName: string;
/**
* Age in years
*/
age?: number;
[k: string]: any;
}
但是,当我构建项目时,Person不会被识别为对象,并且编译失败:
index.js
import Person from './schema/person.schema.json';
const person: Person = {
lastName: 'Doe',
firstName: 'John',
};
console.log(person);
编译失败:
ERROR in ./src/index.ts
(3,15): error TS2304: Cannot find name 'Person'.
虽然我在声明中将.schema.json文件的导出定义为字符串,但我的加载器会动态地将文件名(this.resourcePath)更改为ts文件,因此ts-loader应将其视为标准ts文件并导出Person对象。
我究竟做错了什么?
使用appendTsSuffixTo
我认为如果您使用ts-loader
的appendTsSuffixTo option,您的设置将起作用,而不是自己在自定义加载程序中更改文件名。如评论中所述,您可能还需要调整导入或导出Person
的方式。
使用appendTsSuffixTo
,你将从你的加载器中删除this.resourcePath = this.resourcePath + '.ts';
(或类似的代码)。然后将您的webpack配置调整为以下内容:
module: {
rules: [
{
test: /\.ts$/,
loader: 'ts-loader',
options: {
appendTsSuffixTo: [/\.schema.json$/]
}
},
{
test: /\.schema\.json$/,
loader: 'ts-loader!my-own-loader',
exclude: /(node_modules)/,
},
]
},
您也可以使用这种方法摆脱typings.d.ts
。
但为什么?
我不清楚为什么你的方法不起作用;直观地说它似乎应该等同于使用appendTsSuffixTo
。所以我通过ts-loader
调试了一下,看看发生了什么。
如果我自己修改resourcePath
,在ts-loader/dist/index.js
上看起来很好,但在ts-loader/dist/servicesHost.js
开始出现问题。
具体来说,当我在装载机中更改resolveModuleName()
时,我看到undefined
为我的example.schema.json
文件返回this.resourcePath
。但是,我在使用appendTsSuffixTo
时看到它正确解析。
我不是ts-loader
的贡献者(或专家),但我对此的看法是,在加载器中修改this.resourcePath
时,你的.schema.json
文件确实会编译,但无论何时导入它都无法解决。
其他考虑因素
让你的webpack构建运行是一回事;在IDE中提供良好的开发人员体验是另一回事。有关这方面的更多想法,请参阅this answer一个密切相关的问题,有关工作示例代码的this Github repo可能会有所帮助。