Refactor the methods accessing to pg_constraint

Implement internal functions to accces to pg_contraint
and utilize them in existing foreign key checks.
pull/3846/head
Onur Tirtir 2020-05-20 16:14:09 +03:00
parent 80e34382cf
commit 79a688ffe0
5 changed files with 238 additions and 250 deletions

View File

@ -23,8 +23,10 @@
#include "catalog/pg_type.h"
#include "distributed/colocation_utils.h"
#include "distributed/commands.h"
#include "distributed/listutils.h"
#include "distributed/master_protocol.h"
#include "distributed/multi_join_order.h"
#include "distributed/reference_table_utils.h"
#include "distributed/version_compat.h"
#include "utils/fmgroids.h"
#include "utils/lsyscache.h"
@ -33,68 +35,51 @@
#include "utils/ruleutils.h"
#include "utils/syscache.h"
/*
* Flags that can be passed to GetForeignKeyOids to indicate
* which foreign key constraint OIDs are to be extracted
*/
typedef enum ExtractForeignKeyConstrainstMode
{
/* extract the foreign key OIDs where the table is the referencing one */
INCLUDE_REFERENCING_CONSTRAINTS = 1 << 0,
/* extract the foreign key OIDs the table is the referenced one */
INCLUDE_REFERENCED_CONSTRAINTS = 1 << 1,
/* exclude the self-referencing foreign keys */
EXCLUDE_SELF_REFERENCES = 1 << 2
} ExtractForeignKeyConstraintMode;
/* Local functions forward declarations */
static bool HeapTupleOfForeignConstraintIncludesColumn(HeapTuple heapTuple, Oid
relationId, int pgConstraintKey,
static bool HeapTupleOfForeignConstraintIncludesColumn(HeapTuple heapTuple,
Oid relationId,
int pgConstraintKey,
char *columnName);
static Oid FindForeignKeyOidWithName(List *foreignKeyOids, const
char *inputConstraintName);
static void ForeignConstraintFindDistKeys(HeapTuple pgConstraintTuple,
Var *referencingDistColumn,
Var *referencedDistColumn,
int *referencingAttrIndex,
int *referencedAttrIndex);
static List * GetForeignConstraintCommandsInternal(Oid relationId, int flags);
static Oid get_relation_constraint_oid_compat(HeapTuple heapTuple);
static List * GetForeignKeyOidsToReferenceTables(Oid relationId);
static List * GetForeignKeyOids(Oid relationId, int flags);
/*
* ConstraintIsAForeignKeyToReferenceTable checks if the given constraint is a
* foreign key constraint from the given relation to a reference table. It does
* that by scanning pg_constraint for foreign key constraints.
* foreign key constraint from the given relation to any reference table.
*/
bool
ConstraintIsAForeignKeyToReferenceTable(char *constraintName, Oid relationId)
ConstraintIsAForeignKeyToReferenceTable(char *inputConstaintName, Oid relationId)
{
ScanKeyData scanKey[1];
int scanKeyCount = 1;
bool foreignKeyToReferenceTable = false;
List *foreignKeyOids = GetForeignKeyOidsToReferenceTables(relationId);
Oid foreignKeyOid = FindForeignKeyOidWithName(foreignKeyOids, inputConstaintName);
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_contype, BTEqualStrategyNumber, F_CHAREQ,
CharGetDatum(CONSTRAINT_FOREIGN));
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint, InvalidOid, false,
NULL, scanKeyCount, scanKey);
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
{
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
char *tupleConstraintName = (constraintForm->conname).data;
if (strncmp(constraintName, tupleConstraintName, NAMEDATALEN) != 0 ||
constraintForm->conrelid != relationId)
{
heapTuple = systable_getnext(scanDescriptor);
continue;
}
Oid referencedTableId = constraintForm->confrelid;
Assert(IsCitusTable(referencedTableId));
if (PartitionMethod(referencedTableId) == DISTRIBUTE_BY_NONE)
{
foreignKeyToReferenceTable = true;
break;
}
heapTuple = systable_getnext(scanDescriptor);
}
/* clean up scan and close system catalog */
systable_endscan(scanDescriptor);
heap_close(pgConstraint, AccessShareLock);
return foreignKeyToReferenceTable;
return OidIsValid(foreignKeyOid);
}
@ -123,9 +108,6 @@ ErrorIfUnsupportedForeignConstraintExists(Relation relation, char referencingDis
Var *referencingDistKey,
uint32 referencingColocationId)
{
ScanKeyData scanKey[1];
int scanKeyCount = 1;
Oid referencingTableId = relation->rd_id;
bool referencingNotReplicated = true;
bool referencingIsCitus = IsCitusTable(referencingTableId);
@ -141,17 +123,16 @@ ErrorIfUnsupportedForeignConstraintExists(Relation relation, char referencingDis
referencingNotReplicated = (ShardReplicationFactor == 1);
}
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_conrelid, BTEqualStrategyNumber, F_OIDEQ,
relation->rd_id);
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint,
ConstraintRelidTypidNameIndexId,
true, NULL,
scanKeyCount, scanKey);
int flags = INCLUDE_REFERENCING_CONSTRAINTS;
List *foreignKeyOids = GetForeignKeyOids(referencingTableId, flags);
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
Oid foreignKeyOid = InvalidOid;
foreach_oid(foreignKeyOid, foreignKeyOids)
{
HeapTuple heapTuple = SearchSysCache1(CONSTROID, ObjectIdGetDatum(foreignKeyOid));
Assert(HeapTupleIsValid(heapTuple));
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
int referencingAttrIndex = -1;
@ -161,13 +142,6 @@ ErrorIfUnsupportedForeignConstraintExists(Relation relation, char referencingDis
int referencedAttrIndex = -1;
uint32 referencedColocationId = INVALID_COLOCATION_ID;
/* not a foreign key constraint, skip to next one */
if (constraintForm->contype != CONSTRAINT_FOREIGN)
{
heapTuple = systable_getnext(scanDescriptor);
continue;
}
Oid referencedTableId = constraintForm->confrelid;
bool referencedIsCitus = IsCitusTable(referencedTableId);
@ -207,7 +181,7 @@ ErrorIfUnsupportedForeignConstraintExists(Relation relation, char referencingDis
*/
if (referencingIsReferenceTable && referencedIsReferenceTable)
{
heapTuple = systable_getnext(scanDescriptor);
ReleaseSysCache(heapTuple);
continue;
}
@ -330,18 +304,14 @@ ErrorIfUnsupportedForeignConstraintExists(Relation relation, char referencingDis
"https://citusdata.com/about/contact_us.")));
}
heapTuple = systable_getnext(scanDescriptor);
ReleaseSysCache(heapTuple);
}
/* clean up scan and close system catalog */
systable_endscan(scanDescriptor);
heap_close(pgConstraint, AccessShareLock);
}
/*
* ForeignConstraintFindDistKeys finds the index of the given distribution columns
* in the given foreig key constraint and returns them in referencingAttrIndex
* in the given foreign key constraint and returns them in referencingAttrIndex
* and referencedAttrIndex. If one of them is not found, it returns -1 instead.
*/
static void
@ -400,9 +370,7 @@ ForeignConstraintFindDistKeys(HeapTuple pgConstraintTuple,
/*
* ColumnAppearsInForeignKeyToReferenceTable checks if there is a foreign key
* constraint from/to a reference table on the given column. We iterate
* pg_constraint to fetch the constraint on the given relationId and find
* if any of the constraints includes the given column.
* constraint from/to any reference table on the given column.
*/
bool
ColumnAppearsInForeignKeyToReferenceTable(char *columnName, Oid relationId)
@ -413,8 +381,8 @@ ColumnAppearsInForeignKeyToReferenceTable(char *columnName, Oid relationId)
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_contype, BTEqualStrategyNumber, F_CHAREQ,
CharGetDatum(CONSTRAINT_FOREIGN));
ScanKeyInit(&scanKey[0], Anum_pg_constraint_contype, BTEqualStrategyNumber,
F_CHAREQ, CharGetDatum(CONSTRAINT_FOREIGN));
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint, InvalidOid, false,
NULL, scanKeyCount, scanKey);
@ -476,16 +444,30 @@ ColumnAppearsInForeignKeyToReferenceTable(char *columnName, Oid relationId)
/*
* GetTableForeignConstraints takes in a relationId, and returns the list of foreign
* constraint commands needed to reconstruct foreign constraints of that table.
* GetReferencingForeignConstaintCommands takes in a relationId, and
* returns the list of foreign constraint commands needed to reconstruct
* foreign key constraints that the table is involved in as the "referencing"
* one.
*/
List *
GetTableForeignConstraintCommands(Oid relationId)
GetReferencingForeignConstaintCommands(Oid relationId)
{
List *tableForeignConstraints = NIL;
int flags = INCLUDE_REFERENCING_CONSTRAINTS;
return GetForeignConstraintCommandsInternal(relationId, flags);
}
ScanKeyData scanKey[1];
int scanKeyCount = 1;
/*
* GetForeignConstraintCommandsInternal is a wrapper function to get the
* DDL commands to recreate the foreign key constraints returned by
* GetForeignKeyOids. See more details at the underlying function.
*/
static List *
GetForeignConstraintCommandsInternal(Oid relationId, int flags)
{
List *foreignKeyOids = GetForeignKeyOids(relationId, flags);
List *foreignKeyCommands = NIL;
/*
* Set search_path to NIL so that all objects outside of pg_catalog will be
@ -497,41 +479,18 @@ GetTableForeignConstraintCommands(Oid relationId)
overridePath->addCatalog = true;
PushOverrideSearchPath(overridePath);
/* open system catalog and scan all constraints that belong to this table */
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_conrelid, BTEqualStrategyNumber, F_OIDEQ,
relationId);
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint,
ConstraintRelidTypidNameIndexId,
true, NULL,
scanKeyCount, scanKey);
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
Oid foreignKeyOid = InvalidOid;
foreach_oid(foreignKeyOid, foreignKeyOids)
{
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
char *statementDef = pg_get_constraintdef_command(foreignKeyOid);
bool inheritedConstraint = OidIsValid(constraintForm->conparentid);
if (!inheritedConstraint && constraintForm->contype == CONSTRAINT_FOREIGN)
{
Oid constraintId = get_relation_constraint_oid_compat(heapTuple);
char *statementDef = pg_get_constraintdef_command(constraintId);
tableForeignConstraints = lappend(tableForeignConstraints, statementDef);
}
heapTuple = systable_getnext(scanDescriptor);
foreignKeyCommands = lappend(foreignKeyCommands, statementDef);
}
/* clean up scan and close system catalog */
systable_endscan(scanDescriptor);
heap_close(pgConstraint, AccessShareLock);
/* revert back to original search_path */
PopOverrideSearchPath();
return tableForeignConstraints;
return foreignKeyCommands;
}
@ -561,106 +520,68 @@ get_relation_constraint_oid_compat(HeapTuple heapTuple)
/*
* HasForeignKeyToReferenceTable function scans the pgConstraint table to
* fetch all of the constraints on the given relationId and see if at least one
* of them is a foreign key referencing to a reference table.
* HasForeignKeyToReferenceTable function returns true if any of the foreign
* key constraints on the relation with relationId references to a reference
* table.
*/
bool
HasForeignKeyToReferenceTable(Oid relationId)
{
ScanKeyData scanKey[1];
int scanKeyCount = 1;
bool hasForeignKeyToReferenceTable = false;
List *foreignKeyOids = GetForeignKeyOidsToReferenceTables(relationId);
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_conrelid, BTEqualStrategyNumber, F_OIDEQ,
relationId);
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint,
ConstraintRelidTypidNameIndexId,
true, NULL,
scanKeyCount, scanKey);
return list_length(foreignKeyOids) > 0;
}
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
/*
* GetForeignKeyOidsToReferenceTables function returns list of OIDs for the
* foreign key constraints on the given relationId that are referencing to
* reference tables.
*/
static List *
GetForeignKeyOidsToReferenceTables(Oid relationId)
{
int flags = INCLUDE_REFERENCING_CONSTRAINTS;
List *foreignKeyOids = GetForeignKeyOids(relationId, flags);
List *fkeyOidsToReferenceTables = NIL;
Oid foreignKeyOid = InvalidOid;
foreach_oid(foreignKeyOid, foreignKeyOids)
{
HeapTuple heapTuple =
SearchSysCache1(CONSTROID, ObjectIdGetDatum(foreignKeyOid));
Assert(HeapTupleIsValid(heapTuple));
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
if (constraintForm->contype != CONSTRAINT_FOREIGN)
Oid referencedTableOid = constraintForm->confrelid;
if (IsReferenceTable(referencedTableOid))
{
heapTuple = systable_getnext(scanDescriptor);
continue;
fkeyOidsToReferenceTables = lappend_oid(fkeyOidsToReferenceTables,
foreignKeyOid);
}
Oid referencedTableId = constraintForm->confrelid;
if (!IsCitusTable(referencedTableId))
{
heapTuple = systable_getnext(scanDescriptor);
continue;
}
if (PartitionMethod(referencedTableId) == DISTRIBUTE_BY_NONE)
{
hasForeignKeyToReferenceTable = true;
break;
}
heapTuple = systable_getnext(scanDescriptor);
ReleaseSysCache(heapTuple);
}
/* clean up scan and close system catalog */
systable_endscan(scanDescriptor);
heap_close(pgConstraint, NoLock);
return hasForeignKeyToReferenceTable;
return fkeyOidsToReferenceTables;
}
/*
* TableReferenced function checks whether given table is referenced by another table
* via foreign constraints. If it is referenced, this function returns true. To check
* that, this function searches for the given relation in the pg_constraint system
* catalog table. However since there are no indexes for the column we search for,
* this function performs sequential search. So call this function with caution.
* via foreign constraints. If it is referenced, this function returns true.
*/
bool
TableReferenced(Oid relationId)
{
ScanKeyData scanKey[1];
int scanKeyCount = 1;
Oid scanIndexId = InvalidOid;
bool useIndex = false;
int flags = INCLUDE_REFERENCED_CONSTRAINTS;
List *foreignKeyOids = GetForeignKeyOids(relationId, flags);
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_confrelid, BTEqualStrategyNumber, F_OIDEQ,
relationId);
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint, scanIndexId, useIndex,
NULL,
scanKeyCount, scanKey);
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
{
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
if (constraintForm->contype == CONSTRAINT_FOREIGN)
{
systable_endscan(scanDescriptor);
heap_close(pgConstraint, NoLock);
return true;
}
heapTuple = systable_getnext(scanDescriptor);
}
/* clean up scan and close system catalog */
systable_endscan(scanDescriptor);
heap_close(pgConstraint, NoLock);
return false;
return list_length(foreignKeyOids) > 0;
}
@ -696,89 +617,153 @@ HeapTupleOfForeignConstraintIncludesColumn(HeapTuple heapTuple, Oid relationId,
/*
* TableReferencing function checks whether given table is referencing by another table
* via foreign constraints. If it is referencing, this function returns true. To check
* that, this function searches given relation at pg_constraints system catalog. However
* since there is no index for the column we searched, this function performs sequential
* search, therefore call this function with caution.
* TableReferencing function checks whether given table is referencing to another
* table via foreign key constraints. If it is referencing, this function returns
* true.
*/
bool
TableReferencing(Oid relationId)
{
ScanKeyData scanKey[1];
int scanKeyCount = 1;
Oid scanIndexId = InvalidOid;
bool useIndex = false;
int flags = INCLUDE_REFERENCING_CONSTRAINTS;
List *foreignKeyOids = GetForeignKeyOids(relationId, flags);
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_conrelid, BTEqualStrategyNumber, F_OIDEQ,
relationId);
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint, scanIndexId, useIndex,
NULL,
scanKeyCount, scanKey);
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
{
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
if (constraintForm->contype == CONSTRAINT_FOREIGN)
{
systable_endscan(scanDescriptor);
heap_close(pgConstraint, NoLock);
return true;
}
heapTuple = systable_getnext(scanDescriptor);
}
systable_endscan(scanDescriptor);
heap_close(pgConstraint, NoLock);
return false;
return list_length(foreignKeyOids) > 0;
}
/*
* ConstraintIsAForeignKey returns true if the given constraint name
* is a foreign key to defined on the relation.
* is a foreign key defined on the relation.
*/
bool
ConstraintIsAForeignKey(char *constraintNameInput, Oid relationId)
ConstraintIsAForeignKey(char *inputConstaintName, Oid relationId)
{
int flags = INCLUDE_REFERENCING_CONSTRAINTS;
List *foreignKeyOids = GetForeignKeyOids(relationId, flags);
Oid foreignKeyOid = FindForeignKeyOidWithName(foreignKeyOids, inputConstaintName);
return OidIsValid(foreignKeyOid);
}
/*
* FindForeignKeyOidWithName searches the foreign key constraint with
* inputConstraintName in the given list of foreign key constraint OIDs.
* Returns the OID of the matching constraint. If there no matching constraint
* in the given list, then returns InvalidOid.
*/
static Oid
FindForeignKeyOidWithName(List *foreignKeyOids, const char *inputConstraintName)
{
Oid foreignKeyOid = InvalidOid;
foreach_oid(foreignKeyOid, foreignKeyOids)
{
char *constraintName = get_constraint_name(foreignKeyOid);
Assert(constraintName != NULL);
if (strncmp(constraintName, inputConstraintName, NAMEDATALEN) == 0)
{
return foreignKeyOid;
}
}
return InvalidOid;
}
/*
* GetForeignKeyOids takes in a relationId, and returns a list of OIDs for
* foreign constraints that the relation with relationId is involved according
* to "flags" argument. See ExtractForeignKeyConstrainstMode enum definition
* for usage of the flags.
*/
static List *
GetForeignKeyOids(Oid relationId, int flags)
{
AttrNumber pgConstraintTargetAttrNumber = InvalidAttrNumber;
bool extractReferencing PG_USED_FOR_ASSERTS_ONLY =
(flags & INCLUDE_REFERENCING_CONSTRAINTS);
bool extractReferenced PG_USED_FOR_ASSERTS_ONLY =
(flags & INCLUDE_REFERENCED_CONSTRAINTS);
/*
* Only one of them should be passed at a time since the way we scan
* pg_constraint differs for those columns. Anum_pg_constraint_conrelid
* supports index scan while Anum_pg_constraint_confrelid does not.
*/
Assert(!(extractReferencing && extractReferenced));
Assert(extractReferencing || extractReferenced);
bool useIndex = false;
Oid indexOid = InvalidOid;
if (flags & INCLUDE_REFERENCING_CONSTRAINTS)
{
pgConstraintTargetAttrNumber = Anum_pg_constraint_conrelid;
useIndex = true;
indexOid = ConstraintRelidTypidNameIndexId;
}
else if (flags & INCLUDE_REFERENCED_CONSTRAINTS)
{
pgConstraintTargetAttrNumber = Anum_pg_constraint_confrelid;
}
bool excludeSelfReference = (flags & EXCLUDE_SELF_REFERENCES);
List *foreignKeyOids = NIL;
ScanKeyData scanKey[1];
int scanKeyCount = 1;
Relation pgConstraint = heap_open(ConstraintRelationId, AccessShareLock);
ScanKeyInit(&scanKey[0], Anum_pg_constraint_contype, BTEqualStrategyNumber, F_CHAREQ,
CharGetDatum(CONSTRAINT_FOREIGN));
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint, InvalidOid, false,
ScanKeyInit(&scanKey[0], pgConstraintTargetAttrNumber,
BTEqualStrategyNumber, F_OIDEQ, relationId);
SysScanDesc scanDescriptor = systable_beginscan(pgConstraint, indexOid, useIndex,
NULL, scanKeyCount, scanKey);
HeapTuple heapTuple = systable_getnext(scanDescriptor);
while (HeapTupleIsValid(heapTuple))
{
Form_pg_constraint constraintForm = (Form_pg_constraint) GETSTRUCT(heapTuple);
char *constraintName = (constraintForm->conname).data;
if (strncmp(constraintName, constraintNameInput, NAMEDATALEN) == 0 &&
constraintForm->conrelid == relationId)
if (constraintForm->contype != CONSTRAINT_FOREIGN)
{
systable_endscan(scanDescriptor);
heap_close(pgConstraint, AccessShareLock);
return true;
heapTuple = systable_getnext(scanDescriptor);
continue;
}
bool inheritedConstraint = OidIsValid(constraintForm->conparentid);
if (inheritedConstraint)
{
/*
* We only consider the constraints that are explicitly created on
* the table as we already process the constraints from parent tables
* implicitly when a command is issued
*/
heapTuple = systable_getnext(scanDescriptor);
continue;
}
Oid constraintId = get_relation_constraint_oid_compat(heapTuple);
bool isSelfReference = (constraintForm->conrelid == constraintForm->confrelid);
if (excludeSelfReference && isSelfReference)
{
heapTuple = systable_getnext(scanDescriptor);
continue;
}
foreignKeyOids = lappend_oid(foreignKeyOids, constraintId);
heapTuple = systable_getnext(scanDescriptor);
}
/* clean up scan and close system catalog */
systable_endscan(scanDescriptor);
heap_close(pgConstraint, AccessShareLock);
return false;
return foreignKeyOids;
}

View File

@ -489,7 +489,7 @@ EnsureTableListSuitableForReplication(List *tableIdList)
}
List *foreignConstraintCommandList =
GetTableForeignConstraintCommands(tableId);
GetReferencingForeignConstaintCommands(tableId);
if (foreignConstraintCommandList != NIL &&
PartitionMethod(tableId) != DISTRIBUTE_BY_NONE)
@ -812,7 +812,8 @@ CopyShardForeignConstraintCommandListGrouped(ShardInterval *shardInterval,
char *escapedSchemaName = quote_literal_cstr(schemaName);
int shardIndex = 0;
List *commandList = GetTableForeignConstraintCommands(shardInterval->relationId);
List *commandList = GetReferencingForeignConstaintCommands(
shardInterval->relationId);
/* we will only use shardIndex if there is a foreign constraint */
if (commandList != NIL)

View File

@ -378,7 +378,8 @@ CreateAppendDistributedShardPlacements(Oid relationId, int64 shardId,
int attemptCount = replicationFactor;
int workerNodeCount = list_length(workerNodeList);
int placementsCreated = 0;
List *foreignConstraintCommandList = GetTableForeignConstraintCommands(relationId);
List *foreignConstraintCommandList =
GetReferencingForeignConstaintCommands(relationId);
bool includeSequenceDefaults = false;
List *ddlCommandList = GetTableDDLEvents(relationId, includeSequenceDefaults);
uint32 connectionFlag = FOR_DDL;
@ -487,7 +488,7 @@ CreateShardsOnWorkers(Oid distributedRelationId, List *shardPlacements,
List *ddlCommandList = GetTableDDLEvents(distributedRelationId,
includeSequenceDefaults);
List *foreignConstraintCommandList =
GetTableForeignConstraintCommands(distributedRelationId);
GetReferencingForeignConstaintCommands(distributedRelationId);
int taskId = 1;
List *taskList = NIL;

View File

@ -410,7 +410,7 @@ MetadataCreateCommands(void)
foreach_ptr(cacheEntry, propagatedTableList)
{
List *foreignConstraintCommands =
GetTableForeignConstraintCommands(cacheEntry->relationId);
GetReferencingForeignConstaintCommands(cacheEntry->relationId);
metadataSnapshotCommandList = list_concat(metadataSnapshotCommandList,
foreignConstraintCommands);
@ -497,7 +497,8 @@ GetDistributedTableDDLEvents(Oid relationId)
commandList = list_concat(commandList, shardMetadataInsertCommandList);
/* commands to create foreign key constraints */
List *foreignConstraintCommands = GetTableForeignConstraintCommands(relationId);
List *foreignConstraintCommands =
GetReferencingForeignConstaintCommands(relationId);
commandList = list_concat(commandList, foreignConstraintCommands);
/* commands to create partitioning hierarchy */

View File

@ -101,11 +101,11 @@ extern void ErrorIfUnsupportedForeignConstraintExists(Relation relation,
uint32 colocationId);
extern bool ColumnAppearsInForeignKeyToReferenceTable(char *columnName, Oid
relationId);
extern List * GetTableForeignConstraintCommands(Oid relationId);
extern bool HasForeignKeyToReferenceTable(Oid relationId);
extern bool TableReferenced(Oid relationId);
extern bool TableReferencing(Oid relationId);
extern bool ConstraintIsAForeignKey(char *constraintName, Oid relationId);
extern List * GetReferencingForeignConstaintCommands(Oid relationOid);
extern bool HasForeignKeyToReferenceTable(Oid relationOid);
extern bool TableReferenced(Oid relationOid);
extern bool TableReferencing(Oid relationOid);
extern bool ConstraintIsAForeignKey(char *inputConstaintName, Oid relationOid);
/* function.c - forward declarations */