SQL Server FOR JSON PATH,如果为空则排除特定字段
SQL Server FOR JSON PATH, Exclude specific field if null
我 table 有这样的数据
Id | Name | Phone | OtherField
----+---------+--------+-----------
1 | ABC | 12344 | NULL
2 | XYZ | NULL | NULL
我想要一个 SQL 查询来像这样转换它
[
{
"ID":1,
"Name":"ABC",
"Phone":[
{"Home":"12344"}
],
"OtherFields":NULL
},
{
"ID":1,
"Name":"ABC",
"OtherFields":NULL
}
]
我知道 INCLUDE_NULL_VALUES
它包括所有空白字段。
我想包括除 Phone.
以外的所有其他字段
我已经编辑了我的答案,因为您已经更改了您的原始请求。
我不相信你可以同时拥有它,保留一些 NULL 而不是其他的。目前我能想到的最好方法是在必须保留的列上使用 ISNULL
。
例如:
DECLARE @Table TABLE ( Id INT, Name VARCHAR(10), Phone VARCHAR(10), OtherField VARCHAR(10) );
INSERT INTO @Table ( Id, Name, Phone ) VALUES
( 1, 'ABC', '12344' ), ( 2, 'XYZ', NULL );
SELECT
Id, Name,
JSON_QUERY ( CASE
WHEN t.Phone IS NOT NULL THEN x.Phone
ELSE NULL
END ) AS Phone,
ISNULL( OtherField, '' ) AS OtherFields
FROM @Table t
CROSS APPLY (
SELECT ( SELECT Phone AS Home FOR JSON PATH ) AS Phone
) x
FOR JSON PATH;
Returns
[{
"Id": 1,
"Name": "ABC",
"Phone": [{
"Home": "12344"
}],
"OtherFields": ""
}, {
"Id": 2,
"Name": "XYZ",
"OtherFields": ""
}]
更新:
原始问题已编辑,我认为您无法使用单个 FOR JSON
和 INCLUDE_NULL_VALUES
生成预期的输出,因为现在 table 有多个具有 NULL
值的列(示例中的 OtherField
)。
作为一个可能的解决方案,您可以尝试混合方法(使用 FOR JSON
和 STRING_AGG()
)来构建最终的 JSON 输出并保持所有的 NULL
值列,除了 Phones
:
CREATE TABLE Data (
Id int,
Name varchar(100),
Phone varchar(100),
OtherField varchar(1)
);
INSERT INTO Data (Id, Name, Phone, OtherField)
VALUES
(1, 'ABC', '12344', NULL),
(2, 'ABC', NULL, NULL),
(3, 'ABC', NULL, NULL)
声明:
SELECT CONCAT(
'[',
(
SELECT STRING_AGG(j.Json, ',')
FROM Data d
CROSS APPLY (
SELECT CASE
WHEN Phone IS NOT NULL THEN (
SELECT Id, Name, (SELECT Phone AS Home FOR JSON PATH) AS Phone, OtherField
FOR JSON PATH, INCLUDE_NULL_VALUES, WITHOUT_ARRAY_WRAPPER
)
ELSE (
SELECT Id, Name, OtherField
FOR JSON PATH, INCLUDE_NULL_VALUES, WITHOUT_ARRAY_WRAPPER
)
END
) j (Json)
),
']'
)
结果:
[
{"Id":1,"Name":"ABC","Phone":[{"Home":"12344"}],"OtherField":null},
{"Id":2,"Name":"ABC","OtherField":null},
{"Id":3,"Name":"ABC","OtherField":null}
]
原回答:
您可以尝试以下语句:
Table:
CREATE TABLE Data (
Id int,
Name varchar(100),
Phone varchar(100)
);
INSERT INTO Data (Id, Name, Phone)
VALUES
(1, 'ABC', '12344'),
(2, 'ABC', NULL )
声明:
SELECT
Id,
Name,
JSON_QUERY(CASE WHEN Phone IS NOT NULL THEN (SELECT Phone AS Home FOR JSON PATH) END) AS Phone
FROM Data
FOR JSON PATH
结果:
[
{"Id":1,"Name":"ABC","Phone":[{"Home":"12344"}]},
{"Id":2,"Name":"ABC"}
]
我 table 有这样的数据
Id | Name | Phone | OtherField
----+---------+--------+-----------
1 | ABC | 12344 | NULL
2 | XYZ | NULL | NULL
我想要一个 SQL 查询来像这样转换它
[
{
"ID":1,
"Name":"ABC",
"Phone":[
{"Home":"12344"}
],
"OtherFields":NULL
},
{
"ID":1,
"Name":"ABC",
"OtherFields":NULL
}
]
我知道 INCLUDE_NULL_VALUES
它包括所有空白字段。
我想包括除 Phone.
我已经编辑了我的答案,因为您已经更改了您的原始请求。
我不相信你可以同时拥有它,保留一些 NULL 而不是其他的。目前我能想到的最好方法是在必须保留的列上使用 ISNULL
。
例如:
DECLARE @Table TABLE ( Id INT, Name VARCHAR(10), Phone VARCHAR(10), OtherField VARCHAR(10) );
INSERT INTO @Table ( Id, Name, Phone ) VALUES
( 1, 'ABC', '12344' ), ( 2, 'XYZ', NULL );
SELECT
Id, Name,
JSON_QUERY ( CASE
WHEN t.Phone IS NOT NULL THEN x.Phone
ELSE NULL
END ) AS Phone,
ISNULL( OtherField, '' ) AS OtherFields
FROM @Table t
CROSS APPLY (
SELECT ( SELECT Phone AS Home FOR JSON PATH ) AS Phone
) x
FOR JSON PATH;
Returns
[{
"Id": 1,
"Name": "ABC",
"Phone": [{
"Home": "12344"
}],
"OtherFields": ""
}, {
"Id": 2,
"Name": "XYZ",
"OtherFields": ""
}]
更新:
原始问题已编辑,我认为您无法使用单个 FOR JSON
和 INCLUDE_NULL_VALUES
生成预期的输出,因为现在 table 有多个具有 NULL
值的列(示例中的 OtherField
)。
作为一个可能的解决方案,您可以尝试混合方法(使用 FOR JSON
和 STRING_AGG()
)来构建最终的 JSON 输出并保持所有的 NULL
值列,除了 Phones
:
CREATE TABLE Data (
Id int,
Name varchar(100),
Phone varchar(100),
OtherField varchar(1)
);
INSERT INTO Data (Id, Name, Phone, OtherField)
VALUES
(1, 'ABC', '12344', NULL),
(2, 'ABC', NULL, NULL),
(3, 'ABC', NULL, NULL)
声明:
SELECT CONCAT(
'[',
(
SELECT STRING_AGG(j.Json, ',')
FROM Data d
CROSS APPLY (
SELECT CASE
WHEN Phone IS NOT NULL THEN (
SELECT Id, Name, (SELECT Phone AS Home FOR JSON PATH) AS Phone, OtherField
FOR JSON PATH, INCLUDE_NULL_VALUES, WITHOUT_ARRAY_WRAPPER
)
ELSE (
SELECT Id, Name, OtherField
FOR JSON PATH, INCLUDE_NULL_VALUES, WITHOUT_ARRAY_WRAPPER
)
END
) j (Json)
),
']'
)
结果:
[
{"Id":1,"Name":"ABC","Phone":[{"Home":"12344"}],"OtherField":null},
{"Id":2,"Name":"ABC","OtherField":null},
{"Id":3,"Name":"ABC","OtherField":null}
]
原回答:
您可以尝试以下语句:
Table:
CREATE TABLE Data (
Id int,
Name varchar(100),
Phone varchar(100)
);
INSERT INTO Data (Id, Name, Phone)
VALUES
(1, 'ABC', '12344'),
(2, 'ABC', NULL )
声明:
SELECT
Id,
Name,
JSON_QUERY(CASE WHEN Phone IS NOT NULL THEN (SELECT Phone AS Home FOR JSON PATH) END) AS Phone
FROM Data
FOR JSON PATH
结果:
[
{"Id":1,"Name":"ABC","Phone":[{"Home":"12344"}]},
{"Id":2,"Name":"ABC"}
]