| From: | Alexander Pyhalov <a(dot)pyhalov(at)postgrespro(dot)ru> |
|---|---|
| To: | Alexander Korotkov <aekorotkov(at)gmail(dot)com> |
| Cc: | solaimurugan vellaipandiyan <drsolaimurugan(dot)v(at)gmail(dot)com>, Álvaro Herrera <alvherre(at)kurilemu(dot)de>, g(dot)kashkin(at)postgrespro(dot)ru, Ashutosh Bapat <ashutosh(dot)bapat(dot)oss(at)gmail(dot)com>, PostgreSQL Hackers <pgsql-hackers(at)lists(dot)postgresql(dot)org> |
| Subject: | Re: Function scan FDW pushdown |
| Date: | 2026-05-19 15:25:54 |
| Message-ID: | e0765907e8073c105c76134b5eb6b39b@postgrespro.ru |
| Views: | Whole Thread | Raw Message | Download mbox | Resend email |
| Thread: | |
| Lists: | pgsql-hackers |
Alexander Korotkov писал(а) 2026-05-19 16:00:
> Hi, Alexander.
>
> On Mon, May 18, 2026 at 11:06 PM Alexander Pyhalov
> <a(dot)pyhalov(at)postgrespro(dot)ru> wrote:
>> Hi. I am a bit confused about this comment (and code):
>>
>> /*
>> * DirectModify on a foreign join: pass NIL/0
>> for
>> the function
>> * metadata. We don't currently push function
>> RTEs through the
>> * direct-modify path, so there are no
>> whole-row
>> Vars pointing at
>> * function-RTE tuples to reconstruct.
>> */
>> tupdesc =
>> get_tupdesc_for_join_scan_tuples(node,
>> NIL, 0);
>>
>> We evidently go through this code path when executing example
>>
>> UPDATE remote_tbl r SET b=5 FROM UNNEST(array[box '((2,3),(-2,-3))'])
>> AS
>> t (bx) WHERE r.a = area(t.bx)
>> RETURNING a,b;
>>
>> But don't need whole row var in returning list.... However, we still
>> can
>> step on this issue.
>
> Yes, we go through this code path, and it works as long as whole-row
> var is not needed.
>
>> UPDATE remote_tbl r SET b=5 FROM UNNEST(array[box '((2,3),(-2,-3))'],
>> array[int '1']) AS t (bx, i) WHERE r.a = area(t.bx)
>> RETURNING a,b,t;
>>
>> ERROR: input of anonymous composite types is not implemented
>> CONTEXT: whole-row reference to foreign table "t"
>
> But if whole row var is actually used, then the assumption is broken.
> So, we need to build a whole-row var anyway. I've fixed this in the
> attached patch, and added your sample query as a regression test case.
>
Good evening.
Found one more issue in whole row var deparsing. It can appear on a
nullable outer side, and we should use the same logic as when deparsing
table column reference. Otherwise we get records from nulls instead of
nulls (for example, "(NULL, NULL)" instead of NULL).
Also I wonder if it is possible for get_tupdesc_for_join_scan_tuples()
to get NULL rtfuncdata when it looks at RTE_FUNCTION RTE here:
1759 else if (rte->rtekind == RTE_FUNCTION && rtfuncdata
!= NIL)
1760 {
1761 /*
1762 * A whole-row Var points at a FUNCTION RTE
absorbed into the
1763 * foreign join. Synthesize an anonymous
composite TupleDesc from
1764 * the per-function return-type metadata we
saved at plan time;
1765 * the deparser emits these as
ROW(f<rti>.c1, f<rti>.c2, ...).
1766 */
1767 List *funcdata;
1768 TupleDesc rte_tupdesc;
1769 int num_funcs;
1770 int attnum;
1771 ListCell *lc1,
?
--
Best regards,
Alexander Pyhalov,
Postgres Professional
| Attachment | Content-Type | Size |
|---|---|---|
| v7-0001-postgres_fdw-push-down-FUNCTION-RTE-into-foreign-.patch | text/x-diff | 58.7 KB |
| From | Date | Subject | |
|---|---|---|---|
| Next Message | Alexander Korotkov | 2026-05-19 18:21:45 | Re: Function scan FDW pushdown |
| Previous Message | Ayush Tiwari | 2026-05-19 15:15:50 | Re: [Bug]Assertion failure in LATERAL GRAPH_TABLE with multi-label pattern |