JSON架构:读取带有require的文件时,会删除多个$ref
JSON Schema: multiple $ref get removed when reading file with require
我有一个json模式,定义了几个属性。我已经将其中的2个属性移动到定义中,并引用它们。我这样做是因为我想把它们组合在一起,并以通用的方式对这些属性进行一些测试。这很好,所有json数据都像以前一样处理。
但是,我注意到,当我将json模式文件读取到javascript文件中时,我只看到最后一个$ref。我不知道这是什么原因。我真的需要知道所有引用的属性。
下面是我的json模式的一个片段(在文件schemas/schema1.json中):
{
"type": "object",
"properties": {
"$ref": "#/definitions/groupedProperties/property1",
"$ref": "#/definitions/groupedProperties/property2"
},
"definitions": {
"groupedProperties": {
"type": "object",
"properties": {
"property1": {
"type": "string"
},
"property2": {
"type": "string"
}
}
}
}
}
然后我把它读到我的js文件中,如下所示(在文件test.js中):
var schemas = requireDir('./schemas')
for (var prop in schemas['schema1'].properties) {
console.log(prop)
}
当我从js文件迭代模式中的属性时,我只能看到一个$ref。我想这是因为它认为属性名称是"$ref",并且只能有唯一的名称。有没有某种方法需要这个文件,这样第一个$ref就不会被破坏?
编辑:我的语法没有通过json模式验证器,尽管我不知道为什么,所以我没有为此而烦恼,而是决定用不同的方式来做。我所想要的只是一种对某些属性进行分组的方法,所以我将属性放回主模式中,并将定义更改为仅包含该组的属性名称的枚举。所以现在我的模式看起来像:
{
"type": "object",
"properties": {
"property1": {
"type": "string"
},
"property2": {
"type": "string"
}
},
"definitions": {
"groupedProperties": {
"enum": ["property1", "property2"]
}
}
}
然后在我的js文件中:
var myGroup = (schema.definitions ? schema.definitions.groupedProperties : [])
console.log(myGroup.enum) // [ 'property1', 'property2' ]
在如何引用定义方面存在很多问题。
###JSON对象不能有重复的属性JSON或JavaScript对象中的所有属性都是唯一的。第二个将覆盖第一个。请考虑访问属性的语法以了解原因。当您将JSON读取到JavaScript对象中时,可以尝试使用schema.properties['$ref']
访问$ref
属性。如果有两个,你会得到哪一个(或两个)?JavaScript没有区分机制,因为这是不允许的。
###$ref
必须独立在对象中使用$ref
时,它必须是该对象中的唯一属性。所有其他属性都将被忽略。这只是拥有两个$ref
不起作用的又一个原因。
除"$ref";在JSON引用对象中已忽略。
- https://datatracker.ietf.org/doc/html/draft-pbryan-zyp-json-ref-03#section-3
###$ref
不应用于properties
$ref
应仅用于引用架构。在这种情况下,properties
关键字使用的是$ref
,它是一个具有模式值的对象。在JSON模式或JSON引用的文档中,没有明确禁止以这种方式使用$ref
,但它不是惯用的JSON模式,因此大多数验证器都不支持它。即使您使用的验证器确实支持这样的引用,也应该避免,因为这从来都不是必要的,而且可能会使模式变得混乱和难以维护。
###您的JSON指针错误您的JSON指针实际上并没有指向您定义的模式。正确的指针应该是#/definitions/groupedProperties/properties/property1
。
###可行的解决方案这就是你想要做的。
{
"type": "object",
"properties": {
"property1": { "$ref": "#/definitions/groupedProperties/properties/property1" },
"property2": { "$ref": "#/definitions/groupedProperties/properties/property2" }
},
"definitions": {
"groupedProperties": {
"type": "object",
"properties": {
"property1": {
"type": "string"
},
"property2": {
"type": "string"
}
}
}
}
}
这里有一个更干净的方法,可以同时包含所有的groupedProperties
。
{
"type": "object",
"allOf": [
{ "$ref": "#/definitions/groupedProperties" }
],
"definitions": {
"groupedProperties": {
"type": "object",
"properties": {
"property1": {
"type": "string"
},
"property2": {
"type": "string"
}
}
}
}
}
或者,由于您只是将其用于测试目的,因此可以将其翻转,以便定义引用模式。您可以在测试中使用该定义,而不会影响您的架构。
{
"type": "object",
"properties": {
"property1": { "type": "string" },
"property2": { "type": "string" }
},
"definitions": {
"groupedProperties": {
"type": "object",
"properties": {
"property1": { "$ref": "#/properties/property1" },
"property2": { "$ref": "#/properties/property2" }
}
}
}
}
这与require
无关,对象键不是唯一的(因为您可以在一个对象中多次声明它们),但它们是可重写的(就像两次声明的变量是可重写一样)。您将只收到在两个具有相同名称的键上声明的最后一个值。
我建议给refs一个有区别的ID,这也有助于在代码扩展
- 使用php或javascript从facebook相册URL中删除多余的部分
- RegEx删除空属性?例如,如果(class=“”||class=“”)移除;否则就下课
- 如何删除多行HTML排列中的空白
- 如何从rails中的代码中删除新行( )
- 删除对HTML元素的拖动
- 当图像转换为本地存储的DataURL时,EXIF被删除
- 按顺序添加和删除类
- iframe正在添加标签,需要删除它们
- 如何在HTML输入字段中添加不可删除的后缀
- addData()从最新图表中删除.js 2.1.3-怎么了
- 如何覆盖锚点元素's href目标,并在我点击转到目标javascript时删除其他错误
- 删除CKEditor工具栏按钮,但不删除功能
- 当浏览器上的后退按钮到达主页时,我需要删除Class
- 正在删除node.js中已验证的网站
- 正在从页面中删除iframe
- 如何从 HTML 查询中删除项目
- 如何在iOS应用程序中从Firebase中删除超过6小时的数据
- Firebase对ref调用.remove()正在删除所有父级
- 从Firebase数据库中删除ref的子对象
- JSON架构:读取带有require的文件时,会删除多个$ref