aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/backend/commands/tablecmds.c15
-rw-r--r--src/test/regress/expected/indexing.out63
-rw-r--r--src/test/regress/sql/indexing.sql43
3 files changed, 117 insertions, 4 deletions
diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c
index a9e2a1a1ad2..4dc029f91f1 100644
--- a/src/backend/commands/tablecmds.c
+++ b/src/backend/commands/tablecmds.c
@@ -19174,17 +19174,24 @@ validatePartitionedIndex(Relation partedIdx, Relation partedTbl)
if (tuples == RelationGetPartitionDesc(partedTbl, true)->nparts)
{
Relation idxRel;
- HeapTuple newtup;
+ HeapTuple indTup;
+ Form_pg_index indexForm;
idxRel = table_open(IndexRelationId, RowExclusiveLock);
+ indTup = SearchSysCacheCopy1(INDEXRELID,
+ ObjectIdGetDatum(RelationGetRelid(partedIdx)));
+ if (!HeapTupleIsValid(indTup))
+ elog(ERROR, "cache lookup failed for index %u",
+ RelationGetRelid(partedIdx));
+ indexForm = (Form_pg_index) GETSTRUCT(indTup);
- newtup = heap_copytuple(partedIdx->rd_indextuple);
- ((Form_pg_index) GETSTRUCT(newtup))->indisvalid = true;
+ indexForm->indisvalid = true;
updated = true;
- CatalogTupleUpdate(idxRel, &partedIdx->rd_indextuple->t_self, newtup);
+ CatalogTupleUpdate(idxRel, &indTup->t_self, indTup);
table_close(idxRel, RowExclusiveLock);
+ heap_freetuple(indTup);
}
/*
diff --git a/src/test/regress/expected/indexing.out b/src/test/regress/expected/indexing.out
index 2be8ffa7ec4..598c75279af 100644
--- a/src/test/regress/expected/indexing.out
+++ b/src/test/regress/expected/indexing.out
@@ -1537,3 +1537,66 @@ select indexrelid::regclass, indisvalid,
(5 rows)
drop table parted_isvalid_tab;
+-- Check state of replica indexes when attaching a partition.
+begin;
+create table parted_replica_tab (id int not null) partition by range (id);
+create table parted_replica_tab_1 partition of parted_replica_tab
+ for values from (1) to (10) partition by range (id);
+create table parted_replica_tab_11 partition of parted_replica_tab_1
+ for values from (1) to (5);
+create unique index parted_replica_idx
+ on only parted_replica_tab using btree (id);
+create unique index parted_replica_idx_1
+ on only parted_replica_tab_1 using btree (id);
+-- This triggers an update of pg_index.indisreplident for parted_replica_idx.
+alter table only parted_replica_tab_1 replica identity
+ using index parted_replica_idx_1;
+create unique index parted_replica_idx_11 on parted_replica_tab_11 USING btree (id);
+select indexrelid::regclass, indisvalid, indisreplident,
+ indrelid::regclass, inhparent::regclass
+ from pg_index idx left join
+ pg_inherits inh on (idx.indexrelid = inh.inhrelid)
+ where indexrelid::regclass::text like 'parted_replica%'
+ order by indexrelid::regclass::text collate "C";
+ indexrelid | indisvalid | indisreplident | indrelid | inhparent
+-----------------------+------------+----------------+-----------------------+-----------
+ parted_replica_idx | f | f | parted_replica_tab |
+ parted_replica_idx_1 | f | t | parted_replica_tab_1 |
+ parted_replica_idx_11 | t | f | parted_replica_tab_11 |
+(3 rows)
+
+-- parted_replica_idx is not valid yet here, because parted_replica_idx_1
+-- is not valid.
+alter index parted_replica_idx ATTACH PARTITION parted_replica_idx_1;
+select indexrelid::regclass, indisvalid, indisreplident,
+ indrelid::regclass, inhparent::regclass
+ from pg_index idx left join
+ pg_inherits inh on (idx.indexrelid = inh.inhrelid)
+ where indexrelid::regclass::text like 'parted_replica%'
+ order by indexrelid::regclass::text collate "C";
+ indexrelid | indisvalid | indisreplident | indrelid | inhparent
+-----------------------+------------+----------------+-----------------------+--------------------
+ parted_replica_idx | f | f | parted_replica_tab |
+ parted_replica_idx_1 | f | t | parted_replica_tab_1 | parted_replica_idx
+ parted_replica_idx_11 | t | f | parted_replica_tab_11 |
+(3 rows)
+
+-- parted_replica_idx becomes valid here.
+alter index parted_replica_idx_1 ATTACH PARTITION parted_replica_idx_11;
+alter table only parted_replica_tab_1 replica identity
+ using index parted_replica_idx_1;
+commit;
+select indexrelid::regclass, indisvalid, indisreplident,
+ indrelid::regclass, inhparent::regclass
+ from pg_index idx left join
+ pg_inherits inh on (idx.indexrelid = inh.inhrelid)
+ where indexrelid::regclass::text like 'parted_replica%'
+ order by indexrelid::regclass::text collate "C";
+ indexrelid | indisvalid | indisreplident | indrelid | inhparent
+-----------------------+------------+----------------+-----------------------+----------------------
+ parted_replica_idx | t | f | parted_replica_tab |
+ parted_replica_idx_1 | t | t | parted_replica_tab_1 | parted_replica_idx
+ parted_replica_idx_11 | t | f | parted_replica_tab_11 | parted_replica_idx_1
+(3 rows)
+
+drop table parted_replica_tab;
diff --git a/src/test/regress/sql/indexing.sql b/src/test/regress/sql/indexing.sql
index b69c41832ca..c3473589bfd 100644
--- a/src/test/regress/sql/indexing.sql
+++ b/src/test/regress/sql/indexing.sql
@@ -855,3 +855,46 @@ select indexrelid::regclass, indisvalid,
where indexrelid::regclass::text like 'parted_isvalid%'
order by indexrelid::regclass::text collate "C";
drop table parted_isvalid_tab;
+
+-- Check state of replica indexes when attaching a partition.
+begin;
+create table parted_replica_tab (id int not null) partition by range (id);
+create table parted_replica_tab_1 partition of parted_replica_tab
+ for values from (1) to (10) partition by range (id);
+create table parted_replica_tab_11 partition of parted_replica_tab_1
+ for values from (1) to (5);
+create unique index parted_replica_idx
+ on only parted_replica_tab using btree (id);
+create unique index parted_replica_idx_1
+ on only parted_replica_tab_1 using btree (id);
+-- This triggers an update of pg_index.indisreplident for parted_replica_idx.
+alter table only parted_replica_tab_1 replica identity
+ using index parted_replica_idx_1;
+create unique index parted_replica_idx_11 on parted_replica_tab_11 USING btree (id);
+select indexrelid::regclass, indisvalid, indisreplident,
+ indrelid::regclass, inhparent::regclass
+ from pg_index idx left join
+ pg_inherits inh on (idx.indexrelid = inh.inhrelid)
+ where indexrelid::regclass::text like 'parted_replica%'
+ order by indexrelid::regclass::text collate "C";
+-- parted_replica_idx is not valid yet here, because parted_replica_idx_1
+-- is not valid.
+alter index parted_replica_idx ATTACH PARTITION parted_replica_idx_1;
+select indexrelid::regclass, indisvalid, indisreplident,
+ indrelid::regclass, inhparent::regclass
+ from pg_index idx left join
+ pg_inherits inh on (idx.indexrelid = inh.inhrelid)
+ where indexrelid::regclass::text like 'parted_replica%'
+ order by indexrelid::regclass::text collate "C";
+-- parted_replica_idx becomes valid here.
+alter index parted_replica_idx_1 ATTACH PARTITION parted_replica_idx_11;
+alter table only parted_replica_tab_1 replica identity
+ using index parted_replica_idx_1;
+commit;
+select indexrelid::regclass, indisvalid, indisreplident,
+ indrelid::regclass, inhparent::regclass
+ from pg_index idx left join
+ pg_inherits inh on (idx.indexrelid = inh.inhrelid)
+ where indexrelid::regclass::text like 'parted_replica%'
+ order by indexrelid::regclass::text collate "C";
+drop table parted_replica_tab;