我有此查询,该查询根据表文档的UUID doc_id检索1行,该查询还具有字段列类型jsonb:
select
DISTINCT ON (doc_id)
*
FROM (
select d.doc_id, c.comments
from documents as d
cross join lateral jsonb_array_elements(comments)
WITH ORDINALITY c(comments)
WHERE (c.comments ->> 'isUser'):: boolean is false
order by (c.comments ->>'timestamp')::timestamp desc
) as s;
当我尝试:
order by (c.comments ->>'timestamp')::timestamp desc
我得到完全相同的结果。我什至尝试使用timestamptz
:
order by (c.comments ->>'timestamp')::timestamptz asc
jsonb注释列的示例内容:
[...
{
"text": "30",
"timestamp": "2018-11-11T09:13:23.242Z", // older
"isUser": false
},{
"text": "31",
"timestamp": "2018-11-11T12:53:48.620Z", // LATEST
"isUser": false
}]
您会看到文本30的对象较旧,但始终会在上面的查询中返回。
答案 0 :(得分:1)
该顺序与最终结果无关,因为该顺序仅适用于使用它的SELECT语句,即您的子查询。然后,您使用DISTINCT ON
对这些结果执行另一个查询,该查询将执行任何计算并以 some 的顺序返回结果,但可能不是您想要的结果。
要允许您在外部查询中进行排序,必须在该级别上访问要在订单中使用的字段。这意味着子查询还必须返回timestamp字段,然后外部查询可以对此进行排序,但不能选择它(以使返回的列保持相同)。
select
DISTINCT ON (doc_id)
doc_id, comments
FROM (
select d.doc_id, c.comments, (c.comments ->>'timestamp')::timestamp AS comment_timestamp
from documents as d
cross join lateral jsonb_array_elements(comments)
WITH ORDINALITY c(comments)
WHERE (c.comments ->> 'isUser'):: boolean is false
) as s
ORDER BY doc_id, comment_timestamp DESC
我可能遗漏了一些东西,但看来您还是不需要子查询,这行不通吗?
select DISTINCT ON (d.doc_id) d.doc_id, c.comments
from documents as d
cross join lateral jsonb_array_elements(comments)
WITH ORDINALITY c(comments)
WHERE (c.comments ->> 'isUser'):: boolean is false
order by d.doc_id, (c.comments ->>'timestamp')::timestamp desc