从原始表列中的对象的 JSON 字符串化数组构建视图

问题描述 投票:0回答:1

给出 Athena 中的原始表格,类似于下面这个人为的示例:

原表:

a b cms消息 c
... ... {"asset": {"metadata": {"item": [{"key": "author", "value": "Rob"}, { "key": "id", "value": "123 "}, {"key": "version", "value": "1"}]}}} ...
... ... {“资产”:{“元数据”:{“项目”:[{“键”:“id”,“值”:“456”},{“键”:“作者”,“值”:“约翰"}, {"key": "version", "value": "3"}]}}} ...
... ... {"asset": {"metadata": {"item": [{"key": "version", "value": "2"}, {"key": "author", "value": "Sally "}, {"key": "id", "value": "789" }]}}} ...

我正在尝试从

cmsmessage
列中的字符串化 JSON 创建一个视图:

所需的结果视图:

id 作者 版本
123 罗布 1
456 约翰 3
789 莎莉 3

正如您在“所需结果视图”中看到的那样我本质上是想根据

item
值的值从
key
数组的每个对象中提取数据。

[{"key": "author", "value": "Rob"}, { "key": "id", "value": "123"}, {"key": "version", "value": "1"}]


我已经看到/尝试过通过索引访问数组中的项目的各种示例,例如

[0]
例如 Athena 文档中的 示例。但是,鉴于原始表的
cmsmessage
列中的 json/字符串,数组中的索引位置可能会有所不同。


我失败的尝试:

下面显示了我失败的尝试:

WITH dataset AS 
(
   SELECT *
   FROM (VALUES 
     ('{"asset": {"metadata": {"item": [{"key": "author", "value": "Rob"}, { "key": "id", "value": "123"}, {"key": "version", "value": "1"}]}}}'),
     ('{"asset": {"metadata": {"item": [{ "key": "id", "value": "456"}, {"key": "author", "value": "John"}, {"key": "version", "value": "3"}]}}}'),
     ('{"asset": {"metadata": {"item": [{"key": "version", "value": "2"}, {"key": "author", "value": "Sally"}, {"key": "id", "value": "789" }]}}}')
  ) AS t (cmsmessage)
)

SELECT
    json_extract_scalar(objArray, '$.key') as _keys,
    json_extract_scalar(objArray, '$.value') as _values
FROM dataset

CROSS JOIN UNNEST(CAST(json_extract(cmsmessage, '$.asset.metadata.item') as array(json))) as t (objArray)
arrays json amazon-athena presto trino
1个回答
0
投票

可以说,最简单的选择是使用

json_query
,它对 JSON 路径语法有更好的支持:

SELECT json_query(cmsmessage, 'lax $.asset.metadata.item[*]?(@.key=="id").value') AS id
    , json_query(cmsmessage, 'lax $.asset.metadata.item[*]?(@.key=="author").value') AS author
    , json_query(cmsmessage, 'lax $.asset.metadata.item[*]?(@.key=="version").value') AS version
FROM dataset;

应该适用于基于 Trino 的 Athena 引擎版本 3。

对于版本 2,您可以通过数组操作实现类似的效果。

© www.soinside.com 2019 - 2024. All rights reserved.