我们有一个SQL查询,其中我们使用JSON Path创建一个JSON文件。 我们想将2个JSON对象合并为1个JSON。但是我们在代码中很难完成这项任务。
我们尝试使用JSON_MODIFY将它们合并在一起。但这对我们不起作用。
我们想做的是,我们有2个独立的json对象,我们想将它们合并为一个。
Json对象A:
{
"ID" : 0,
"Name" : "a name",
"Description" : "a description"
}
和Json对象B
"Nodes" : [
{
"NodeID" : 10,
"NodeName" : "Node 0"
},
{
"NodeID" : 11,
"NodeName" : "Node 1"
}
]
我们想要拥有的东西:
{
"ID" : 0,
"Name" : "a name",
"Description" : "a description",
"Nodes" : [
{
"NodeID" : 10,
"NodeName" : "Node 0"
},
{
"NodeID" : 11,
"NodeName" : "Node 1"
}
]
}
我们当前的SQL查询如下:
set @JsonCourse = ( select c.name, c.id, c.description from dbo.courses c where c.id = @id for json path)
set @JsonNodes = ( select n.id, n.name from dbo.nodes n where n.courseId = @id for json path, root('Nodes'))
set @CompleteJson = JSON_MODIFY(@JsonCourse,'append $',JSON_QUERY(@JsonNodes));
print @CompleteJson
但是我们的结果是这样的:
[
{
"ID" : 0,
"Name" : "a name",
"Description" : "a description"
},
{
"Nodes" : [
{
"NodeID" : 10,
"NodeName" : "Node 0"
},
{
"NodeID" : 11,
"NodeName" : "Node 1"
}
]
}
]
注意:我们在这里使用了假设数据。
我们如何使用JSON_MODIFY修复此问题?
答案 0 :(得分:0)
请阅读有关creating a MCVE的信息。这是一个独立示例,可以使您的问题重现,并帮助我们提供简单的答案...
如果我正确理解了这一点,则存在一个1:n
相关的结构,其中“对象A”中的每个节点可以在“对象B”中具有多个节点。
我的以下代码将通过INFORMATION_SCHEMA
对此进行模拟。每个表为1或许多列。
我们用相关子查询解决了这个问题。这是创建嵌套JSON数组的方法:
SELECT TOP 3 t.TABLE_NAME AS NodeName
,t.TABLE_TYPE AS NodeType
,(
SELECT TOP 3 c.COLUMN_NAME AS ColumnName
,c.DATA_TYPE AS ColumnType
FROM INFORMATION_SCHEMA.COLUMNS c
WHERE c.TABLE_CATALOG=t.TABLE_CATALOG
AND c.TABLE_SCHEMA=t.TABLE_SCHEMA
AND c.TABLE_NAME=t.TABLE_NAME
FOR JSON PATH
) AS MyColumns
FROM INFORMATION_SCHEMA.TABLES t
FOR JSON PATH;
结果
[
{
"NodeName": "spt_fallback_db",
"NodeType": "BASE TABLE",
"MyColumns": [
{
"ColumnName": "xserver_name",
"ColumnType": "varchar"
},
{
"ColumnName": "xdttm_ins",
"ColumnType": "datetime"
},
{
"ColumnName": "xdttm_last_ins_upd",
"ColumnType": "datetime"
}
]
},
{
"NodeName": "spt_fallback_dev",
"NodeType": "BASE TABLE",
"MyColumns": [
{
"ColumnName": "xserver_name",
"ColumnType": "varchar"
},
{
"ColumnName": "xdttm_ins",
"ColumnType": "datetime"
},
{
"ColumnName": "xdttm_last_ins_upd",
"ColumnType": "datetime"
}
]
},
{
"NodeName": "spt_fallback_usg",
"NodeType": "BASE TABLE",
"MyColumns": [
{
"ColumnName": "xserver_name",
"ColumnType": "varchar"
},
{
"ColumnName": "xdttm_ins",
"ColumnType": "datetime"
},
{
"ColumnName": "xdttm_last_ins_upd",
"ColumnType": "datetime"
}
]
}
]
如您所见,每个表都是一组嵌套的列,通过JSON数组表示。
答案 1 :(得分:0)
因此,我将添加另一个答案,因为这与第一个答案完全不同:
由于我没有您的表,因此将JSON变量设置为您提供的值
DECLARE @json1 NVARCHAR(MAX)=
N'{
"ID" : 0,
"Name" : "a name",
"Description" : "a description"
}'
DECLARE @json2 NVARCHAR(MAX)= --<-- had to add the surrounding {}, otherwise this was invalid JSON
N'{"Nodes" :
[
{
"NodeID" : 10,
"NodeName" : "Node 0"
},
{
"NodeID" : 11,
"NodeName" : "Node 1"
}
]}';
-我们在这里不需要append
。
-我们必须告诉引擎新节点的名称。
-为避免重复输入键Nodes
,我使用@json2
作为路径从$.Nodes
读取
DECLARE @CompleteJSON NVARCHAR(MAX)=JSON_MODIFY(@Json1,'$.Nodes',JSON_QUERY(@Json2,'$.Nodes'));
PRINT @CompleteJSON;
我希望这更接近您的需求...