Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
425 views
in Technique[技术] by (71.8m points)

sql server - Create nested JSON arrays using FOR JSON PATH

I need to create a JSON output from a query that uses inner join between two tables with a one to many relationship.
I would like the values of the secondary table to be nested as array properties of the primary table.

Consider the following example:

DECLARE @Persons AS TABLE
(
    person_id int primary key,
    person_name varchar(20)
)

DECLARE @Pets AS TABLE
(
    pet_owner int, -- in real tables, this would be a foreign key
    pet_id int  primary key,
    pet_name varchar(10)
)

INSERT INTO @Persons (person_id, person_name) VALUES
(2, 'Jack'),
(3, 'Jill')

INSERT INTO @Pets (pet_owner, pet_id, pet_name) VALUES
(2, 4, 'Bug'),
(2, 5, 'Feature'),
(3, 6, 'Fiend')

And query:

DECLARE @Result as varchar(max)
SET @Result =
(
SELECT  person_id as [person.id],
        person_name as [person.name],
        pet_id as [person.pet.id],
        pet_name as [person.pet.name]
FROM @Persons 
JOIN @Pets ON person_id = pet_owner
FOR JSON PATH, ROOT('pet owners')
)

PRINT @Result

This will print the following JSON:

{
    "pet owners":
    [
    {"person":{"id":2,"name":"Jack","pet":{"id":4,"name":"Bug"}}},
    {"person":{"id":2,"name":"Jack","pet":{"id":5,"name":"Feature"}}},
    {"person":{"id":3,"name":"Jill","pet":{"id":6,"name":"Fiend"}}}
    ]
}

However, I would like to have the pets data as arrays inside the owners data:

{
    "pet owners":
    [
        {
            "person":
            {
                "id":2,"name":"Jack","pet":
                [
                    {"id":4,"name":"Bug"},
                    {"id":5,"name":"Feature"}
                ]
            }
        },
        {
            "person":
            {
                "id":3,"name":"Jill","pet":
                {"id":6,"name":"Fiend"}
            }
        }
    ]
}

How can I do this?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

You can use the following query:

SELECT pr.person_id AS [person.id], pr.person_name AS [person.name],
    (
        SELECT pt.pet_id AS id, pt.pet_name AS name 
        FROM @Pets pt WHERE pt.pet_owner=pr.person_id 
        FOR JSON PATH
    ) AS [person.pet]
FROM @Persons pr 
FOR JSON PATH, ROOT('pet owners')

For more information, see https://blogs.msdn.microsoft.com/sqlserverstorageengine/2015/10/09/returning-child-rows-formatted-as-json-in-sql-server-queries/


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...