MCPcopy Create free account
hub / github.com/apache/cloudberry / ATExecDetachPartition

Function ATExecDetachPartition

src/backend/commands/tablecmds.c:22159–22343  ·  view source on GitHub ↗

* ALTER TABLE DETACH PARTITION * * Return the address of the relation that is no longer a partition of rel. * * If concurrent mode is requested, we run in two transactions. A side- * effect is that this command cannot run in a multi-part ALTER TABLE. * Currently, that's enforced by the grammar. * * The strategy for concurrency is to first modify the partition's * pg_inherit catalog row t

Source from the content-addressed store, hash-verified

22157 * metadata (pg_inherits and pg_class.relpartbounds).
22158 */
22159static ObjectAddress
22160ATExecDetachPartition(List **wqueue, AlteredTableInfo *tab, Relation rel,
22161 RangeVar *name, bool concurrent)
22162{
22163 Relation partRel;
22164 ObjectAddress address;
22165 Oid defaultPartOid;
22166
22167 /*
22168 * We must lock the default partition, because detaching this partition
22169 * will change its partition constraint.
22170 */
22171 defaultPartOid =
22172 get_default_oid_from_partdesc(RelationGetPartitionDesc(rel, true));
22173
22174 /* GPDB_14_MERGE_FIXME: detach partition is not supported now. We need to
22175 * implement how to control cmd which will be executed in two transactions.
22176 */
22177 if (concurrent)
22178 ereport(ERROR,
22179 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
22180 errmsg("cannot support detach partitions concurrently now")));
22181
22182 if (OidIsValid(defaultPartOid))
22183 {
22184 /*
22185 * Concurrent detaching when a default partition exists is not
22186 * supported. The main problem is that the default partition
22187 * constraint would change. And there's a definitional problem: what
22188 * should happen to the tuples that are being inserted that belong to
22189 * the partition being detached? Putting them on the partition being
22190 * detached would be wrong, since they'd become "lost" after the
22191 * detaching completes but we cannot put them in the default partition
22192 * either until we alter its partition constraint.
22193 *
22194 * I think we could solve this problem if we effected the constraint
22195 * change before committing the first transaction. But the lock would
22196 * have to remain AEL and it would cause concurrent query planning to
22197 * be blocked, so changing it that way would be even worse.
22198 */
22199 if (concurrent)
22200 ereport(ERROR,
22201 (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
22202 errmsg("cannot detach partitions concurrently when a default partition exists")));
22203 LockRelationOid(defaultPartOid, AccessExclusiveLock);
22204 }
22205
22206 /*
22207 * In concurrent mode, the partition is locked with share-update-exclusive
22208 * in the first transaction. This allows concurrent transactions to be
22209 * doing DML to the partition.
22210 */
22211 partRel = table_openrv(name, concurrent ? ShareUpdateExclusiveLock :
22212 AccessExclusiveLock);
22213
22214 /*
22215 * Check inheritance conditions and either delete the pg_inherits row (in
22216 * non-concurrent mode) or just set the inhdetachpending flag.

Callers 1

ATExecCmdFunction · 0.85

Calls 15

RelationGetPartitionDescFunction · 0.85
LockRelationOidFunction · 0.85
table_openrvFunction · 0.85
RemoveInheritanceFunction · 0.85
MarkInheritDetachedFunction · 0.85
MemoryContextStrdupFunction · 0.85
CacheInvalidateRelcacheFunction · 0.85
table_closeFunction · 0.85

Tested by

no test coverage detected