Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

Commit 9e9befa

Browse files
committed
Set relispartition correctly for index partitions
Oversight in commit 8b08f7d: pg_class.relispartition was not being set for index partitions, which is a bit odd, and was also causing the code to unnecessarily call has_superclass() when simply checking the flag was enough. Author: Álvaro Herrera Reported-by: Amit Langote Discussion: https://postgr.es/m/12085bc4-0bc6-0f3a-4c43-57fe0681772b@lab.ntt.co.jp
1 parent d1e9079 commit 9e9befa

File tree

2 files changed

+45
-7
lines changed

2 files changed

+45
-7
lines changed

src/backend/catalog/index.c

+1
Original file line numberDiff line numberDiff line change
@@ -933,6 +933,7 @@ index_create(Relation heapRelation,
933933
indexRelation->rd_rel->relowner = heapRelation->rd_rel->relowner;
934934
indexRelation->rd_rel->relam = accessMethodObjectId;
935935
indexRelation->rd_rel->relhasoids = false;
936+
indexRelation->rd_rel->relispartition = OidIsValid(parentIndexRelid);
936937

937938
/*
938939
* store index's pg_class entry

src/backend/commands/tablecmds.c

+44-7
Original file line numberDiff line numberDiff line change
@@ -490,6 +490,8 @@ static ObjectAddress ATExecAttachPartitionIdx(List **wqueue, Relation rel,
490490
static void validatePartitionedIndex(Relation partedIdx, Relation partedTbl);
491491
static void refuseDupeIndexAttach(Relation parentIdx, Relation partIdx,
492492
Relation partitionTbl);
493+
static void update_relispartition(Relation classRel, Oid relationId,
494+
bool newval);
493495

494496

495497
/* ----------------------------------------------------------------
@@ -14405,10 +14407,11 @@ AttachPartitionEnsureIndexes(Relation rel, Relation attachrel)
1440514407
*/
1440614408
for (i = 0; i < list_length(attachRelIdxs); i++)
1440714409
{
14410+
Oid cldIdxId = RelationGetRelid(attachrelIdxRels[i]);
1440814411
Oid cldConstrOid = InvalidOid;
1440914412

1441014413
/* does this index have a parent? if so, can't use it */
14411-
if (has_superclass(RelationGetRelid(attachrelIdxRels[i])))
14414+
if (attachrelIdxRels[i]->rd_rel->relispartition)
1441214415
continue;
1441314416

1441414417
if (CompareIndexInfo(attachInfos[i], info,
@@ -14429,7 +14432,7 @@ AttachPartitionEnsureIndexes(Relation rel, Relation attachrel)
1442914432
{
1443014433
cldConstrOid =
1443114434
get_relation_idx_constraint_oid(RelationGetRelid(attachrel),
14432-
RelationGetRelid(attachrelIdxRels[i]));
14435+
cldIdxId);
1443314436
/* no dice */
1443414437
if (!OidIsValid(cldConstrOid))
1443514438
continue;
@@ -14439,6 +14442,7 @@ AttachPartitionEnsureIndexes(Relation rel, Relation attachrel)
1443914442
IndexSetParentIndex(attachrelIdxRels[i], idx);
1444014443
if (OidIsValid(constraintOid))
1444114444
ConstraintSetParentConstraint(cldConstrOid, constraintOid);
14445+
update_relispartition(NULL, cldIdxId, true);
1444214446
found = true;
1444314447
break;
1444414448
}
@@ -14659,7 +14663,6 @@ ATExecDetachPartition(Relation rel, RangeVar *name)
1465914663
((Form_pg_class) GETSTRUCT(newtuple))->relispartition = false;
1466014664
CatalogTupleUpdate(classRel, &newtuple->t_self, newtuple);
1466114665
heap_freetuple(newtuple);
14662-
heap_close(classRel, RowExclusiveLock);
1466314666

1466414667
if (OidIsValid(defaultPartOid))
1466514668
{
@@ -14692,8 +14695,10 @@ ATExecDetachPartition(Relation rel, RangeVar *name)
1469214695

1469314696
idx = index_open(idxid, AccessExclusiveLock);
1469414697
IndexSetParentIndex(idx, InvalidOid);
14698+
update_relispartition(classRel, idxid, false);
1469514699
relation_close(idx, AccessExclusiveLock);
1469614700
}
14701+
heap_close(classRel, RowExclusiveLock);
1469714702

1469814703
/*
1469914704
* Invalidate the parent's relcache so that the partition is no longer
@@ -14815,8 +14820,8 @@ ATExecAttachPartitionIdx(List **wqueue, Relation parentIdx, RangeVar *name)
1481514820
ObjectAddressSet(address, RelationRelationId, RelationGetRelid(partIdx));
1481614821

1481714822
/* Silently do nothing if already in the right state */
14818-
currParent = !has_superclass(partIdxId) ? InvalidOid :
14819-
get_partition_parent(partIdxId);
14823+
currParent = partIdx->rd_rel->relispartition ?
14824+
get_partition_parent(partIdxId) : InvalidOid;
1482014825
if (currParent != RelationGetRelid(parentIdx))
1482114826
{
1482214827
IndexInfo *childInfo;
@@ -14909,6 +14914,7 @@ ATExecAttachPartitionIdx(List **wqueue, Relation parentIdx, RangeVar *name)
1490914914
IndexSetParentIndex(partIdx, RelationGetRelid(parentIdx));
1491014915
if (OidIsValid(constraintOid))
1491114916
ConstraintSetParentConstraint(cldConstrId, constraintOid);
14917+
update_relispartition(NULL, partIdxId, true);
1491214918

1491314919
pfree(attmap);
1491414920

@@ -15036,8 +15042,7 @@ validatePartitionedIndex(Relation partedIdx, Relation partedTbl)
1503615042
* If this index is in turn a partition of a larger index, validating it
1503715043
* might cause the parent to become valid also. Try that.
1503815044
*/
15039-
if (updated &&
15040-
has_superclass(RelationGetRelid(partedIdx)))
15045+
if (updated && partedIdx->rd_rel->relispartition)
1504115046
{
1504215047
Oid parentIdxId,
1504315048
parentTblId;
@@ -15059,3 +15064,35 @@ validatePartitionedIndex(Relation partedIdx, Relation partedTbl)
1505915064
relation_close(parentTbl, AccessExclusiveLock);
1506015065
}
1506115066
}
15067+
15068+
/*
15069+
* Update the relispartition flag of the given relation to the given value.
15070+
*
15071+
* classRel is the pg_class relation, already open and suitably locked.
15072+
* It can be passed as NULL, in which case it's opened and closed locally.
15073+
*/
15074+
static void
15075+
update_relispartition(Relation classRel, Oid relationId, bool newval)
15076+
{
15077+
HeapTuple tup;
15078+
HeapTuple newtup;
15079+
Form_pg_class classForm;
15080+
bool opened = false;
15081+
15082+
if (classRel == NULL)
15083+
{
15084+
classRel = heap_open(RelationRelationId, RowExclusiveLock);
15085+
opened = true;
15086+
}
15087+
15088+
tup = SearchSysCache1(RELOID, ObjectIdGetDatum(relationId));
15089+
newtup = heap_copytuple(tup);
15090+
classForm = (Form_pg_class) GETSTRUCT(newtup);
15091+
classForm->relispartition = newval;
15092+
CatalogTupleUpdate(classRel, &tup->t_self, newtup);
15093+
heap_freetuple(newtup);
15094+
ReleaseSysCache(tup);
15095+
15096+
if (opened)
15097+
heap_close(classRel, RowExclusiveLock);
15098+
}

0 commit comments

Comments
 (0)