Re: BUG #19099: Conditional DELETE from partitioned table with non-updatable partition raises internal error - Mailing list pgsql-bugs

From Tender Wang
Subject Re: BUG #19099: Conditional DELETE from partitioned table with non-updatable partition raises internal error
Date
Msg-id CAHewXNnD0744Vykj6ujE5c=rRP=61sh7K154uNdgEaTmJrRegQ@mail.gmail.com
Whole thread Raw
In response to Re: BUG #19099: Conditional DELETE from partitioned table with non-updatable partition raises internal error  (Amit Langote <amitlangote09@gmail.com>)
List pgsql-bugs


Amit Langote <amitlangote09@gmail.com> 于2025年11月26日周三 19:27写道:
On Thu, Nov 6, 2025 at 7:00 PM Amit Langote <amitlangote09@gmail.com> wrote:
> Among those options, I considered the following block, which adds a
> ctid for the partitioned root table when it’s the only target in the
> query after partition pruning removes all child tables due to the
> WHERE false condition in the problematic case:
>
>     /*
>      * Ordinarily, we expect that leaf result relation(s) will have added some
>      * ROWID_VAR Vars to the query.  However, it's possible that constraint
>      * exclusion suppressed every leaf relation.  The executor will get upset
>      * if the plan has no row identity columns at all, even though it will
>      * certainly process no rows.  Handle this edge case by re-opening the top
>      * result relation and adding the row identity columns it would have used,
>      * as preprocess_targetlist() would have done if it weren't marked "inh".
>      * Then re-run build_base_rel_tlists() to ensure that the added columns
>      * get propagated to the relation's reltarget.  (This is a bit ugly, but
>      * it seems better to confine the ugliness and extra cycles to this
>      * unusual corner case.)
>      */
>     if (root->row_identity_vars == NIL)
>     {
>         Relation    target_relation;
>
>         target_relation = table_open(target_rte->relid, NoLock);
>         add_row_identity_columns(root, result_relation,
>                                  target_rte, target_relation);
>         table_close(target_relation, NoLock);
>         build_base_rel_tlists(root, root->processed_tlist);
>         /* There are no ROWID_VAR Vars in this case, so we're done. */
>         return;
>     }
>
> If enable_partition_pruning is off, root->row_identity_vars already
> contains a RowIdentityVarInfo entry for the tableoid Var that was
> added while processing the foreign-table child partition. Because of
> that, the if (root->row_identity_vars == NIL) block doesn’t run in
> this case, so it won’t add any row identity columns such as ctid for
> the partitioned root table.
>
> In theory, we could prevent the planner from adding tableoid in the
> first place when the child table doesn’t support any row identity
> column -- or worse, doesn’t support the UPDATE/DELETE/MERGE command at
> all -- but doing so would require changing the order in which tableoid
> appears in root->processed_tlist. That would be too invasive for a
> back-patch.

I’ve implemented this alternative as well -- the version that prevents
adding tableoid when no other row-identity columns are added for the
child. That allows to keep root->row_identity_vars empty so the
dummy-root path can add ctid as intended by the above code block of
distribute_row_identity_vars().

This provides an alternative approach to compare against the other patch.

--
Thanks, Amit Langote

I apply the patch, and I find it forgets to update the diff for postgres_fdw.
So I add it in the v2 patch.
With this patch, the targetlists are identical whether or not enable_partition_pruning is on.

In my first email on this thread, to avoid adding "tableoid", I tried to add the following codes:
 "(childrte->relkind != RELKIND_PARTITIONED_TABLE && childrte->relkind != RELKIND_FOREIGN_TABLE)"
in expand_single_inheritance_child().

But this didn't work for all test cases. It would trigger an assert failure in fix_scan_expr_walker():
Assert(!(IsA(node, Var) && ((Var *) node)->varno == ROWID_VAR));

Your patch is much better than mine.

 --
Thanks,
Tender Wang
Attachment

pgsql-bugs by date:

Previous
From: David Rowley
Date:
Subject: Re: Segmentation fault in var_is_nonnullable when running query with COUNT() on 42473b3b
Next
From: Devrim Gündüz
Date:
Subject: Re: BUG #19337: Errors during downloading metadata for repository pgdg-rhel9-extras