我有 3 个表,它们之间有 1-n 关系
CREATE TABLE Province
(
Id BIGINT PRIMARY KEY,
Name NVARCHAR(255),
-- ...
)
CREATE TABLE District
(
Id BIGINT PRIMARY KEY,
Name NVARCHAR(255),
ProvinceId BIGINT REFERENCES [Province](Id)
)
CREATE TABLE Ward
(
Id BIGINT PRIMARY KEY,
Name NVARCHAR(255),
DistrictId BIGINT REFERENCES [District](Id)
)
我想获取一个省份的详细数据,如下所示
{
"id": 1,
"province_name": "province name",
"districts": [
{
"id": 1,
"district_name": "district-1",
"wards": [1,2,3]
},
{
"id": 2,
"district_name": "district-2",
"wards": [4,5]
}
]
}
(1省有很多区,1区有很多区)
这是我使用
STRING_AGG
内置函数实现的
select CONCAT(
'{"id":"', p.[id], '"',
',"province_name":', p.ProvinceName,
',"districts":',
CONCAT(
'[{',
STRING_AGG(
CONCAT('"id":', CAST(po.Id AS VARCHAR(10)),
',"name":"', po.[Name],
'","district_name":[', STRING_AGG(CAST(w.id AS VARCHAR(10)), ','), ']'), '},{'),
'}]'),
'}')
from
province p
left join
district d on d.provinceId = p.id
left join
ward w on w.districtId = d.id
where
p.id = @id
但是 SQL Server 抛出了这个异常:
无法对包含聚合或子查询的表达式执行聚合函数
我尝试从该网站搜索类似的问题,但找不到预期的结果。
如何实现从3个1-n层获取数据?
这是不可能用OP的数据来证明的,因为我们没有任何数据。因此,我使用了一些
sys
对象来演示如何:
JSON_ARRAYAGG
,因为它在预览之外不可用。JSON 嵌套就像 XML 嵌套一样,带有子查询。要将值聚合到数组中,则仍然使用
STRING_AGG
,但是,我们随后需要使用 JSON_QUERY
将其转换为实际的 JSON,而不是文字。这会产生如下所示的结果:
SELECT s.name AS schema_name,
(SELECT object_id,
name,
JSON_QUERY((SELECT CONCAT('[',STRING_AGG(c.column_id,','),']')
FROM sys.columns c
WHERE c.object_id = t.object_id),'$') AS column_ids
FROM sys.tables t
WHERE t.schema_id = s.schema_id
FOR JSON AUTO) AS tables
FROM sys.schemas s
FOR JSON AUTO;
得到这样的结果:
[
{
"schema_name": "dbo"
},
{
"schema_name": "guest"
},
{
"schema_name": "INFORMATION_SCHEMA"
},
{
"schema_name": "sys"
},
{
"schema_name": "fn"
},
{
"schema_name": "sp"
},
{
"schema_name": "t"
},
{
"schema_name": "tbl",
"tables": [
{
"object_id": 389576426,
"name": "Calendar",
"column_ids": [
1,
2,
3,
4,
5,
6,
7,
8
]
},
{
"object_id": 1618104805,
"name": "Clock",
"column_ids": [
1,
2,
3,
4
]
}
]
}
]