Hi all, While reviewing the code for opclass parameters with indexes, I have noticed that opclass parameters are lost after a concurrent reindex. As we use a IndexInfo to hold the information of the new index when creating a copy of the old one, it is just a matter of making sure that ii_OpclassOptions is filled appropriately, but that was missed by 911e702.
Attached is a patch to fix the issue. After a concurrent reindex, we would not finish with a corrupted index, just with one rebuilt with default opclass parameter values. Any objections or comments? -- Michael
diff --git a/src/backend/catalog/index.c b/src/backend/catalog/index.c index 26bfa74ce7..460f84d4e8 100644 --- a/src/backend/catalog/index.c +++ b/src/backend/catalog/index.c @@ -1365,6 +1365,15 @@ index_concurrently_create_copy(Relation heapRelation, Oid oldIndexId, newInfo->ii_IndexAttrNumbers[i] = oldInfo->ii_IndexAttrNumbers[i]; } + /* Extract opclass parameters for each attribute, if any */ + if (oldInfo->ii_OpclassOptions) + { + newInfo->ii_OpclassOptions = palloc0(sizeof(Datum) * + newInfo->ii_NumIndexAttrs); + for (int i = 0; i < oldInfo->ii_NumIndexAttrs; i++) + newInfo->ii_OpclassOptions[i] = oldInfo->ii_OpclassOptions[i]; + } + /* * Now create the new index. * diff --git a/src/test/regress/expected/create_index.out b/src/test/regress/expected/create_index.out index 4750eac359..4702333fd6 100644 --- a/src/test/regress/expected/create_index.out +++ b/src/test/regress/expected/create_index.out @@ -2176,6 +2176,24 @@ SELECT indexrelid::regclass, indisreplident FROM pg_index (1 row) DROP TABLE concur_replident; +-- Check that opclass parameters are preserved +CREATE TABLE concur_appclass_tab(i tsvector, j tsvector); +CREATE INDEX concur_appclass_ind on concur_appclass_tab + USING gist (i tsvector_ops (siglen='1000'), j tsvector_ops (siglen='500')); +CREATE INDEX concur_appclass_ind_2 on concur_appclass_tab + USING gist (i tsvector_ops, j tsvector_ops (siglen='300')); +REINDEX TABLE CONCURRENTLY concur_appclass_tab; +\d concur_appclass_tab + Table "public.concur_appclass_tab" + Column | Type | Collation | Nullable | Default +--------+----------+-----------+----------+--------- + i | tsvector | | | + j | tsvector | | | +Indexes: + "concur_appclass_ind" gist (i tsvector_ops (siglen='1000'), j tsvector_ops (siglen='500')) + "concur_appclass_ind_2" gist (i, j tsvector_ops (siglen='300')) + +DROP TABLE concur_appclass_tab; -- Partitions -- Create some partitioned tables CREATE TABLE concur_reindex_part (c1 int, c2 int) PARTITION BY RANGE (c1); diff --git a/src/test/regress/sql/create_index.sql b/src/test/regress/sql/create_index.sql index 22209b0691..c26f6ff70b 100644 --- a/src/test/regress/sql/create_index.sql +++ b/src/test/regress/sql/create_index.sql @@ -888,6 +888,15 @@ REINDEX TABLE CONCURRENTLY concur_replident; SELECT indexrelid::regclass, indisreplident FROM pg_index WHERE indrelid = 'concur_replident'::regclass; DROP TABLE concur_replident; +-- Check that opclass parameters are preserved +CREATE TABLE concur_appclass_tab(i tsvector, j tsvector); +CREATE INDEX concur_appclass_ind on concur_appclass_tab + USING gist (i tsvector_ops (siglen='1000'), j tsvector_ops (siglen='500')); +CREATE INDEX concur_appclass_ind_2 on concur_appclass_tab + USING gist (i tsvector_ops, j tsvector_ops (siglen='300')); +REINDEX TABLE CONCURRENTLY concur_appclass_tab; +\d concur_appclass_tab +DROP TABLE concur_appclass_tab; -- Partitions -- Create some partitioned tables
signature.asc
Description: PGP signature