TSQL JSON Как добавить массив в существующий объект Json? - PullRequest
0 голосов
/ 11 июля 2019

У нас есть SQL-запрос, в котором мы создаем файл JSON для JSON Path. Мы хотим объединить 2 объекта JSON в 1 файл JSON. Но мы боремся с кодом, как выполнить эту задачу.

Мы попытались JSON_MODIFY объединить их, используя append. Но у нас это не сработало.

Мы хотели бы сделать следующее: у нас есть 2 отдельных объекта json, и мы хотим объединить их в один.

Json Объект A:

{
    "ID" : 0,
    "Name" : "a name",
    "Description" : "a description"
}

и Json Object 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?

Ответы [ 2 ]

0 голосов
/ 11 июля 2019

Итак, я добавлю еще один ответ, так как это совершенно другое, что и первый ответ:

Поскольку у меня нет ваших таблиц, я установлю для переменных 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;

Надеюсь, это ближе к вашим потребностям ...

0 голосов
/ 11 июля 2019

Пожалуйста, прочитайте о создании 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.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...