使用postgresql 9.4访问JSON的更深层元素

时间:2015-07-14 20:42:05

标签: json postgresql

我希望能够访问存储在postgresql数据库中的字段json中存储在json中的更深层元素。例如,我希望能够从下面提供的json访问遍历路径状态 - > events->时间的元素。这是我正在使用的postgreSQL查询:

SELECT 
    data#>> '{userId}' as user, 
    data#>> '{region}' as region, 
    data#>>'{priorTimeSpentInApp}' as priotTimeSpentInApp, 
    data#>>'{userAttributes, "Total Friends"}' as totalFriends 
from game_json 
WHERE game_name LIKE 'myNewGame' 
LIMIT 1000

这是json字段的示例记录

{
    "region": "oh",
    "deviceModel": "inHouseDevice",
    "states": [
        {
            "events": [
                {
                    "time": 1430247045.176,
                    "name": "Session Start",
                    "value": 0,
                    "parameters": {
                        "Balance": "40"
                    },
                    "info": ""
                },
                {
                    "time": 1430247293.501,
                    "name": "Mission1",
                    "value": 1,
                    "parameters": {
                        "Result": "Win ",
                        "Replay": "no",
                        "Attempt Number": "1"
                    },
                    "info": ""
                }
            ]
        }
    ],
    "priorTimeSpentInApp": 28989.41467999999,
    "country": "CA",
    "city": "vancouver",
    "isDeveloper": true,
    "time": 1430247044.414,
    "duration": 411.53,
    "timezone": "America/Cleveland",
    "priorSessions": 47,
    "experiments": [],
    "systemVersion": "3.8.1",
    "appVersion": "14312",
    "userId": "ef617d7ad4c6982e2cb7f6902801eb8a",
    "isSession": true,
    "firstRun": 1429572011.15,
    "priorEvents": 69,
    "userAttributes": {
        "Total Friends": "0",
        "Device Type": "Tablet",
        "Social Connection": "None",
        "Item Slots Owned": "12",
        "Total Levels Played": "0",
        "Retention Cohort": "Day 0",
        "Player Progression": "0",
        "Characters Owned": "1"
    },
    "deviceId": "ef617d7ad4c6982e2cb7f6902801eb8a"
}

该SQL查询有效,但它不会为totalFriends提供任何返回值(例如,数据#>>'{userAttributes,“Total Friends”}'作为totalFriends)。我假设问题的一部分是事件落在一个方括号内(我不知道json格式中的含义)而不是大括号,但我也无法从userAttributes键中提取值。

如果有人能帮助我,我将不胜感激。

如果在别处问过这个问题,我很抱歉。我对postgresql甚至json都很陌生,以至于我无法找到适当的术语来找到这个(和相关的)问题的答案。

2 个答案:

答案 0 :(得分:9)

你一定要熟悉the basics of jsonjson functions and operators in Postgres

在第二个来源中,请注意运营商->->>。 一般规则:使用->获取json对象,->>以获取json值作为文本。 使用这些运算符,您可以以返回正确值'Total Friends'

的方式重写查询
select
    data->>'userId' as user, 
    data->>'region' as region, 
    data->>'priorTimeSpentInApp' as priotTimeSpentInApp, 
    data->'userAttributes'->>'Total Friends' as totalFriends 
from game_json 
where game_name like 'myNewGame';

方括号中的Json对象是json数组的元素。 Json数组可能有许多元素。 元素由索引访问。 Json数组从0开始索引(数组的第一个元素的索引为0)。 例如:

select
    data->'states'->0->'events'->1->>'name'
from game_json 
where game_name like 'myNewGame'; 
-- returns "Mission1"

答案 1 :(得分:0)

select
    data->'states'->0->'events'->1->>'name'
from game_json 
where game_name like 'myNewGame';

这确实对我有帮助