#json #sql-server
Вопрос:
Мне было интересно, можно ли будет изменить формат JSON и вернуть его в качестве JSON. У меня есть JSON, который в упрощенной форме выглядит так:
- Имя
- Подробные сведения
- fieldId
- Значение поля
- Другое
- ID
- Ценность
И хотел бы вернуться:
- Имя
- Подробные сведения
- fieldId
- Значение поля
Я могу вернуть имя и сведения с JSON_VALUE
помощью и JSON_QUERY
, но хотел бы, чтобы это было одно объединенное поле JSON.
create table #test (
[id] int,
[json] varchar(max)
);
insert into #test (id, json) values (1, '{
"Name": "Test 1",
"Details": [
{
"fieldId": "100",
"fieldValue": "ABC"
}],
"Other": [
{
"Id": "1",
"Value": "ABC"
}]
}');
insert into #test (id, json) values (2, '{
"Name": "Test 2",
"Details": [
{
"fieldId": "101",
"fieldValue": "ABCD"
}],
"Other": [
{
"Id": "2",
"Value": "ABCD"
}]
}');
select id, JSON_VALUE(json, '$.Name'), JSON_QUERY(json, '$.Details')
from #test
Ответ №1:
В качестве дополнительной опции вы можете проанализировать JSON с OPENJSON()
помощью и явной схемы (определения столбцов), а затем снова создать новый JSON:
SELECT
id,
newjson = (
SELECT Name, Details
FROM OPENJSON(json) WITH (
Name varchar(max) '$.Name',
Details nvarchar(max) '$.Details' AS JSON
)
FOR JSON PATH, WITHOUT_ARRAY_WRAPPER
)
FROM #test
И тот же подход с JSON_VALUE()
и JSON_QUERY()
:
SELECT
id,
newjson = (
SELECT JSON_VALUE(json, '$.Name') AS [Name], JSON_QUERY(json, '$.Details') AS [Details]
FOR JSON PATH, WITHOUT_ARRAY_WRAPPER
)
FROM #test
Ответ №2:
Одним из решений является использование JSON_MODIFY
для повторного построения JSON:
SELECT
id,
JSON_MODIFY(
JSON_MODIFY(
'{}',
'$.Name',
JSON_VALUE(json, '$.Name')
),
'$.Details',
JSON_QUERY(json, '$.Details')
) AS new_json
FROM #test
Альтернативным вариантом было бы удалить Other
узел с помощью JSON_MODIFY
, но вы должны знать имя узла(ов) для удаления.