从PostgreSQL JSON列

时间:2016-02-11 22:14:56

标签: json postgresql

我们的数据库包含一个表“log”,如下所示:

id | purchases (json)
1    {"apple":{"price":5,"seller":"frank"}, "bred":{"price":3,"seller":"kathy"}}
2    {"milk":{"price":3,"seller":"anne"}, "banana":{"price":2,"seller":"frank"}}
3    {"bred":{"price":4,"seller":"kathy"}}

我们想要检索包含"seller":"kathy"的所有记录。我们尝试过这样简单的查询:

SELECT id FROM log WHERE purchases ->> 'seller' LIKE 'kathy'
SELECT id FROM log WHERE purchases = '{"seller":"kathy"}'

我们在这里和其他地方研究了几个小时......它似乎有点复杂,因为这些值是嵌套的?我们发现例如一些java或pgplsql实现,但我们仍然希望有一种“纯SQL”方式。什么是适当的解决方案?或者我们应该重新组织这样的内容:

id | purchases (json)
1    [{"product":"apple","price":5,"seller":"frank"},{"product":"bred","price":3,"seller":"kathy"}]
2    [{"product":"milk","price":3,"seller":"anne"},{"product":"banana","price":2,"seller":"frank"}]
3    [{"product":"bred","price":4,"seller":"kathy"}]

但是我们发现,这将更加复杂,因为我们必须在查询中爆炸数组。任何短促的提示?谢谢!

1 个答案:

答案 0 :(得分:1)

检查json_each()#>> Postgres JSON functions

WITH log(id,purchases) AS ( VALUES
  (1,'{"apple":{"price":5,"seller":"frank"}, "bred":{"price":3,"seller":"kathy"}}'::JSON),
  (2,'{"milk":{"price":3,"seller":"anne"}, "banana":{"price":2,"seller":"frank"}}'::JSON),
  (3,'{"bred":{"price":4,"seller":"kathy"}}'::JSON)
)
SELECT log.* FROM log,
  json_each(log.purchases) as purchase
WHERE
  purchase.value#>>'{seller}' = 'kathy';

结果:

 id |                                  purchases                                  
----+-----------------------------------------------------------------------------
  1 | {"apple":{"price":5,"seller":"frank"}, "bred":{"price":3,"seller":"kathy"}}
  3 | {"bred":{"price":4,"seller":"kathy"}}
(2 rows)