Re: BUG #19765: Wrong result from a chain of LEFT JOINs since v16

From: Richard Guo <guofenglinux(at)gmail(dot)com>
To: Tender Wang <tndrwang(at)gmail(dot)com>
Cc: leis(at)in(dot)tum(dot)de, pgsql-bugs(at)lists(dot)postgresql(dot)org
Subject: Re: BUG #19765: Wrong result from a chain of LEFT JOINs since v16
Date: 2026-10-16 15:04:03
Message-ID: CAMbWs4_Uy6q4CcW+gVrF8aLRFB6ZWMOTemPCUpLKrocyXj+BwQ@mail.gmail.com
Views: Whole Thread | Raw Message | Download mbox | Resend email
Thread:
Lists: pgsql-bugs

On Fri, Oct 16, 2026 at 10:11 PM Tender Wang <tndrwang(at)gmail(dot)com> wrote:
> Thus, deriving the inner-side restriction is not sufficient to
> establish that the join qual is redundant.
> In particular, replacing a strict qual with TRUE can invalidate the
> reasoning that allowed the outer joins to commute.

I came to the same conclusion. To elaborate on it a bit more, the
problem is that when an outer join gets commuted into the RHS of a
lower outer join, we don't add its relid until the lower join is
formed (see add_outer_joins_to_relids). So in the meantime, its RHS
Vars can already have gone to NULL without having its nulling bit. If
a higher outer join that commutes with it gets joined on top at that
point, clone selection sees that the relid is missing and picks the
least-nulled version of its qual.

Normally that's fine, because the qual is strict and will reject the
null-extended rows anyway, which is what identity 3 depends on. But
once we've replaced that qual with a constant-TRUE dummy, nothing
rejects them, and we get bogus matches.

I think we can fix this by only making the TRUE dummy for clauses that
are not clones. For a clone, just throw the original clause back, as
v15 and earlier did.

- Richard

In response to

Browse pgsql-bugs by date

  From Date Subject
Next Message Fujii Masao 2026-10-16 15:22:02 Re: BUG #19488: Standby connection fails after dropping on login event trigger enabled always
Previous Message Nitin Motiani 2026-10-16 14:43:59 Re: BUG #19765: Wrong result from a chain of LEFT JOINs since v16