当前位置: 首页 > 面试题库 >

SQL to JSON-将结果分组到JSON数组中

卫招
2023-03-14
问题内容

我正在尝试提出一种SQL解决方案,以安排输出以匹配预期的JSON格式。

我有一些简单的SQL来突出显示问题的根源。

SELECT TOP 1 'Surname' AS 'name.family'
,'Forename, Middle Name' AS 'name.given'
,'Title' AS 'name.prefix'
,getDATE() AS 'birthdate'
,'F' AS 'gender'
,'Yes' AS 'active'
,'work' AS 'telecom.use'
,'phone' AS 'telecom.system'
,'12344556' AS 'telecom.value'
FROM tblCustomer
FOR json path

它将返回JSON为;

[
{
    "name": {
        "family": "Surname",
        "given": "Forename, Middle Name",
        "prefix": "Title"
    },
    "birthdate": "2019-02-13T12:06:45.490",
    "gender": "F",
    "active": "Yes",
    "telecom": {
        "use": "work",
        "system": "phone",
        "value": "12344556"
    }
}
]

我需要的是在“ telecome”数组中添加额外的对象,使其看起来像;

[
{
    "name": {
        "family": "Surname",
        "given": "Forename, Middle Name",
        "prefix": "Title"
    },
    "birthdate": "2019-02-13T12:06:45.490",
    "gender": "F",
    "active": "Yes",
    "telecom": {
        "use": "work",
        "system": "phone",
        "value": "12344556"
    },
    {
        "use": "work",
        "system": "home",
        "value": "12344556"
    },
}
]

我错误地认为我可以继续添加到我的SQL中,如下所示:

SELECT TOP 1 'Surname' AS 'name.family'
,'Forename, Middle Name' AS 'name.given'
,'Title' AS 'name.prefix'
,getDATE() AS 'birthdate'
,'F' AS 'gender'
,'Yes' AS 'active'
,'work' AS 'telecom.use'
,'phone' AS 'telecom.system'
,'12344556' AS 'telecom.value'
,'home' AS 'telecom.use'
FROM tblCustomer
FOR json path

但是它将按照我的命名缩进嵌套项目;

由于与另一个列名或别名冲突,无法在JSON输出中生成属性’telecom.use’。SELECT列表中的每一列使用不同的名称和别名。

有没有一种方法可以使用SQL处理这种嵌套,还是需要为JSON查询创建单独的并将其合并?

谢谢

使用@@ Version Microsoft SQL Server
2017(RTM)-14.0.1000.169(X64)2017年8月22日17:04:49版权所有(C)2017 Windows Server
2012 R2 Datacenter 6.3(Build 9600)上的Microsoft Corporation Express
Edition(64位) :)(管理程序)

对问题进行小的编辑,以使用动态值而不是强制静态成员。

SELECT TOP 1 'Surname' AS 'name.family'
    ,'Forename, Middle Name' AS 'name.given'
    ,'Title' AS 'name.prefix'
    ,getDATE() AS 'birthdate'
    ,'F' AS 'gender'
    ,'Yes' AS 'active'
    ,'work' AS 'telecom.use'
    ,'phone' AS 'telecom.system'
    ,customerWorkTelephone AS 'telecom.value'
    ,'home' AS 'telecom.use'
    ,'phone' AS 'telecom.system'
    ,customerHomeTelephone AS 'telecom.value'
FROM tblCustomer
FOR json path

“值”项将从tblCustomer表中的列中获取。我试图弥补下面的响应,但无法在子查询中获得完全正确的逻辑。

再次感谢

进一步编辑

我有一些SQL可以给我期望的输出,但是我不确定它可能是最好的,我的方法是否不够理想?

SELECT TOP 1 [name.family] = 'Surname'
,[name.given] = 'Forename, Middle Name'
,[name.prefix] = 'Title'
,[birthdate] = GETDATE()
,[gender] = 'F'
,[active] = 'Yes'
,[telecom] = (
    SELECT [use] = V.used
        ,[system] = 'phone'
        ,[value] = CASE V.used
            WHEN 'work'
                THEN cu.customerWorkTelephone
            WHEN 'home'
                THEN cu.customerHomeTelephone
            when 'mobile'
                then cu.customerMobileTelephone
            END
    FROM (
        VALUES ('work')
            ,('home')
            ,('mobile')
        ) AS V(used)

    FOR json path
    )
FROM tblCustomer cu
FOR JSON PATH

问题答案:

使用带有一些硬编码行的子选择:

SELECT TOP 1 
    'Surname' AS 'name.family'
    ,'Forename, Middle Name' AS 'name.given'
    ,'Title' AS 'name.prefix'
    ,getDATE() AS 'birthdate'
    ,'F' AS 'gender'
    ,'Yes' AS 'active'
    ,'telecom' = (
            SELECT
                'work' AS 'use'
                ,V.system AS 'system'
                ,'12344556' AS 'value'
            FROM
                (VALUES 
                    ('phone'),
                    ('home')) AS V(system)
            FOR JSON PATH)
FROM tblCustomer
FOR JSON PATH

请注意telecom.,子查询中缺少前缀。

结果(无表参考):

[
    {
        "name": {
            "family": "Surname",
            "given": "Forename, Middle Name",
            "prefix": "Title"
        },
        "birthdate": "2019-02-13T12:53:08.400",
        "gender": "F",
        "active": "Yes",
        "telecom": [
            {
                "use": "work",
                "system": "phone",
                "value": "12344556"
            },
            {
                "use": "work",
                "system": "home",
                "value": "12344556"
            }
        ]
    }
]

PD :特别是对于SQL Server,我发现使用左侧的别名更易读:

SELECT TOP 1 
    [name.family] = 'Surname',
    [name.given] = 'Forename, Middle Name',
    [name.prefix] = 'Title',

    [birthdate] = GETDATE(),
    [gender] = 'F',
    [active] = 'Yes',

    [telecom] = (
        SELECT
            [use] = 'work',
            [system] = V.system,
            [value] = '12344556'
        FROM
            (VALUES ('phone'), ('home')) AS V(system)
        FOR JSON 
            PATH)
FROM tblCustomer
FOR JSON 
    PATH


 类似资料:
  • 问题内容: 我有下表。 我正在使用ID获取分组结果 现在,我想将project_id,category_id,supplier_id插入主表,并将item_id,qty,rate插入其明细表。明细表会将主表ID作为外键。请帮忙。 问题答案: 假设这个模式: 可以做到这一点:

  • 问题内容: 我想将结果数组转换为PHP中的JSON格式。这是我的代码: 我想转换为JSON格式并将JSON数据传递给jQuery插件。 问题答案: 在php> 5.2.0中可用:

  • 问题内容: 我最近从mysql切换到mysqli并开始使用准备好的语句。在mysql中我们做 因此,我们将整个表的数组放在一个变量中。 但是在mysqli中 所以基本上这里只有一个变量绑定到变量结果。我们如何获得与从mysql获得的变量(数组)相同的变量? PS-希望我的问题足够清楚。我知道他们的方法不多,但我希望能找到最好的方法。 PSS-我对程序方式比较满意。 问题答案: 最终,这段代码可以正

  • 问题内容: 我知道这应该是简单的,我可能正直盯着问题,但我再次陷入困境,需要代码专家的帮助。 我试图从jdbc的一列中取出一行,并将它们放入数组中。 我这样做如下: creatConnection是已经定义的方法,可以执行其明显的工作。我在创建另一个结果集的同时创建了我的结果集,我将该列的字符串存储到一个数组中。然后打印出来以备不时之需。还要确保它在那里。 问题在于其将整个列存储到contactL

  • 我希望PostgreSQL将查询结果作为一个JSON数组返回。给定 我想要类似于

  • 我尝试创建一个函数,在从所有用户中删除一个用户id后,为他们重建用户id。例如: 测试表: id|text 1|aaa 2|bbb 3|ccc 4|ddd 6|fff 7|ggg 8|hhh 9|iii 10|jjj 删除记录: 5|eee 我想修复所有用户的id,并修复mysql的自动增量 固定表: id|text 1|aaa 2|bbb 3|ccc 4|ddd 5|fff 6|ggg 7|hh