By using db<>fiddle, you agree to license everything you submit by Creative Commons CC0.
Help with an interesting Postgres question: Why isn't an Index Only Scan used on a partition accessed via the parent table?.
create table level_one_table (
id int,
column1 varchar(10)
);
insert into level_one_table values
(1, 'l1_va1'),
(2, 'l1_va2');
create table level_two_table (
id int,
fk_level_one_id int,
column2 varchar(10)
);
insert into level_two_table values
(1, 1, 'l2_va1'),
(2, 1, 'l2_va2'),
(3, 1, 'l2_va3'),
(4, 1, 'l2_va4'),
(5, 2, 'l2_va5'),
(6, 2, 'l2_va6'),
(7, 2, 'l2_va7');
create table level_three_table (
id int,
fk_level_two_id int,
column3 varchar(10)
);
insert into level_three_table values
(1, 1, 'l3_va1'),
(2, 2, 'l3_va2'),
(3, 3, 'l3_va3'),
(4, 4, 'l3_va4'),
(5, 5, 'l3_va5'),
CREATE TABLE
INSERT 0 2
CREATE TABLE
INSERT 0 7
CREATE TABLE
INSERT 0 7
SELECT jsonb_pretty(
json_build_object(
'level_one_table',
json_build_object(
'id', t0.id,
'level_two_table',
json_arrayagg(
json_build_object(
'id', t1.id,
'column2', t1.column2,
'level_three_table',
json_build_object(
'id', t2.id,
'column3', t2.column3
)
)
ORDER BY t1.column2 DESC
)
)
)::jsonb
) as json_obj
FROM level_one_table t0
LEFT JOIN (SELECT *, ROW_NUMBER() OVER(PARTITION BY fk_level_one_id ORDER BY column2 DESC) AS rn FROM level_two_table) t1 ON t0.id = t1.fk_level_one_id
LEFT JOIN level_three_table t2 ON t1.id = t2.fk_level_two_id
WHERE t1.rn <= 2
GROUP BY t0.id
json_obj |
---|
{ "level_one_table": { "id": 1, "level_two_table": [ { "id": 4, "column2": "l2_va4", "level_three_table": { "id": 4, "column3": "l3_va4" } }, { "id": 3, "column2": "l2_va3", "level_three_table": { "id": 3, "column3": "l3_va3" } } ] } } |
{ "level_one_table": { "id": 2, "level_two_table": [ { "id": 7, "column2": "l2_va7", "level_three_table": { "id": 7, "column3": "l3_va7" } }, { "id": 6, "column2": "l2_va6", "level_three_table": { "id": 6, "column3": "l3_va6" } } ] } } |
SELECT 2