[PG19] Indexes from 18 miss rows after pg_upgrade

From: shihao zhong <zhong950419(at)gmail(dot)com>
To: pgsql-hackers <pgsql-hackers(at)lists(dot)postgresql(dot)org>
Cc: Jeff Davis <pgsql(at)j-davis(dot)com>, Peter Eisentraut <peter(at)eisentraut(dot)org>, Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>
Subject: [PG19] Indexes from 18 miss rows after pg_upgrade
Date: 2026-10-15 04:58:14
Message-ID: CAGRkXqRWpqmoCBffoLViAVAK2-_hYE_z1SW=FfejPidT6wPgdA@mail.gmail.com
Views: Whole Thread | Raw Message | Download mbox | Resend email
Thread:
Lists: pgsql-hackers

Hi hackers,

After pg_upgrade from 18 to 19, some indexes built by 18 miss rows that
a seq scan finds, and nothing tells the user to rebuild them. Three 19
commits stopped using LC_CTYPE, so these functions now give different
results for the same input. to_tsvector() and pg_trgm changed in ICU and
builtin databases (e113f9c102b). dmetaphone() changed there too, and in
multibyte libc databases with a non C locale (e39ece0343f). soundex()
and metaphone() changed in single-byte databases with a non C locale
(b96a9fd76f3), for example soundex('Éric') in LATIN1 fr_FR went from
É620 to R200.

On 18.6:

create database d template template0 encoding 'UTF8'
locale_provider builtin builtin_locale 'C.UTF-8' locale 'C';
\c d
create extension pg_trgm;
create table doc (t text);
insert into doc values ('foo—bar'), ('naïve');
create index on doc using gin (to_tsvector('simple', t));
create index on doc using gin (t gin_trgm_ops);

After pg_upgrade to 19, with enable_seqscan off, both queries return no
rows. A seq scan, or 18.6, returns one.

select * from doc
where to_tsvector('simple', t) @@ plainto_tsquery('simple',
'foo—bar');
select * from doc where t like '%naïve%';

The attached patch makes pg_upgrade find indexes that use these
functions or the pg_trgm opclasses, in the databases where the results
changed. --check warns, and the real run writes reindex_locale.sql with
a REINDEX for each one. The query takes 0.08 seconds on a database with
22000 indexes. Stored tsvector columns also keep what 18 computed and
REINDEX does not change them, so the release notes need a sentence for
those.

7dc95cc3b94 also changed some Snowball stems, like biologist to biolog
in english, so such indexes can miss rows in any database. Per Tom in
[2], that only needs a release note, so the patch leaves it out.

I tested upgrading 18.6 to REL_19_STABLE (9b505ef6cc1) on Linux. Without
the patch 24 of my index probes return fewer rows than a seq scan. After
running the generated script none do, and a cluster without such indexes
upgrades with no warning. The patch applies to master too. I think this
belongs on the open items list. It is item 9 of my list in [1].

[1]
https://postgr.es/m/CAGRkXqSFdjqZP_kwRz7dv6LHX-CSrkDnynNXgntRsCEnQTKxmg@mail.gmail.com
[2] https://postgr.es/m/12827.1462331634@sss.pgh.pa.us

Thanks,
Shihao

Attachment Content-Type Size
0001-pg_upgrade-Rebuild-indexes-affected-by-19-s-local.patch application/octet-stream 7.4 KB

Browse pgsql-hackers by date

  From Date Subject
Next Message Fujii Masao 2026-10-15 05:18:32 Re: [PG19] Promotion hangs behind a backend blocked on a stuck client
Previous Message David Rowley 2026-10-15 04:55:02 Re: Bug in logical decoding with DDL and subtransactions