Re: BUG #19864: pg_get_publication_tables() gets cache lookup error after concurrent DROP PUBLICATION

From: Ajin Cherian <itsajin(at)gmail(dot)com>
To: shveta malik <shveta(dot)malik(at)gmail(dot)com>
Cc: imchifan8(at)gmail(dot)com, pgsql-bugs(at)lists(dot)postgresql(dot)org, Masahiko Sawada <sawada(dot)mshk(at)gmail(dot)com>, shveta malik <shvetamalik(at)gmail(dot)com>
Subject: Re: BUG #19864: pg_get_publication_tables() gets cache lookup error after concurrent DROP PUBLICATION
Date: 2026-11-13 03:51:09
Message-ID: CAFPTHDbJMJMOgTQoAgqouC3fqg2NeCopLYBSpyL4aZKO=OuODQ@mail.gmail.com
Views: Whole Thread | Raw Message | Download mbox | Resend email
Thread:
Lists: pgsql-bugs

On Thu, Nov 12, 2026 at 11:16 PM shveta malik <shveta(dot)malik(at)gmail(dot)com> wrote:
>
>
> I verified the known cases, they work well. I will verify a bit more tomorrow.
> A few code comments:
>
> 1)
> I noticed that the same condition now produces 2 different msgs
> depending on timing, which I initially thought was okay.
>
> (Cases: If the publication is dropped before its name is resolved on
> the first call, the result is publication "pub" does not exist. If
> it's dropped later, while a row is being formed, the result is
> publication "pub" was concurrently dropped).
>
> But on rethinking, it will be better to make the messages consistent.
> How about moving 'concurrently dropped' part to errdetail?
>
> ereport(ERROR,
> (errcode(ERRCODE_UNDEFINED_OBJECT),
> errmsg("publication \"%s\" does not exist", pubname),
> errdetail("The publication was dropped concurrently.")));
>
> 2)
> Also I feel, it will be better to separate the logic of finding
> pub-name from core logic. Suggestion:
>
> pub = get_publication_internal(table_info->pubid, true);
> if (pub == NULL)
> {
> if (!pub_missing_ok)
> ereport(ERROR,
> errcode(ERRCODE_UNDEFINED_OBJECT),
> errmsg("publication \"%s\" does not exist",
> get_pubname_from_list(ptstate->pubs,
> table_info->pubid)),
> errdetail("The publication was dropped concurrently."));
>
> table_close(rel, AccessShareLock);
> continue;
> }
>
> static char *
> get_pubname_from_list(List *pubs, Oid pubid)
> {
> foreach_ptr(Publication, p, pubs)
> {
> if (p->oid == pubid)
> return p->name;
> }
>
> Assert(false);
> return NULL;
> }
>
> thanks
> Shveta

Thanks for the review and the testing, Shveta.
Both suggestions make sense, and the attached v3 does both. The error
now uses the same message as when the publication is already gone on
the first call, with the concurrent drop in the detail: ERROR:
publication “pub” does not exist DETAIL: The publication was dropped
concurrently. I also moved the name lookup into a separate helper,
get_pubname_from_list(), as you suggested. One small difference:
instead of Assert(false) followed by return NULL, the helper ends with
an elog(ERROR), so that a non-assert build never passes NULL to the %s
in the error message if that case were ever reached.

regards,
Ajin Cherian
Fujitsu Australia

Attachment Content-Type Size
v3-0001-Fix-cache-lookup-failure-in-pg_get_publication_ta.patch application/octet-stream 8.9 KB

In response to

Responses

Browse pgsql-bugs by date

  From Date Subject
Next Message Nitin Motiani 2026-11-13 04:33:21 Re: BUG #19737: Empty `JSON_OBJECT` cannot use documented `ON NULL` or unique-key clauses
Previous Message Daniel Gustafsson 2026-11-13 00:00:07 Re: BUG #19702: decode() accepts Base64 payload after terminal padding