get_constraint_index() does its work by going through pg_depend. It was added before pg_constraint.conindid was added, and some callers are still not changed. Are there reasons for that? Probably not. The attached patch changes get_constraint_index() to an lsyscache-style lookup instead.

The nearby get_index_constraint() should probably also be changed to scan pg_constraint instead of pg_depend, but that doesn't have a syscache to use, so it would be a different approach, so I figured I'd ask about get_constraint_index() first.


From 29371949b2e61f894f651eef990c3c6eabfa8145 Mon Sep 17 00:00:00 2001
From: Peter Eisentraut <pe...@eisentraut.org>
Date: Mon, 7 Dec 2020 10:38:36 +0100
Subject: [PATCH] Change get_constraint_index() to use pg_constraint.conindid

It was still using a scan of pg_depend instead of using the conindid
column that has been added since.
---
 src/backend/catalog/pg_depend.c      | 69 ----------------------------
 src/backend/commands/tablecmds.c     |  1 -
 src/backend/optimizer/util/plancat.c |  1 -
 src/backend/utils/adt/ruleutils.c    |  3 +-
 src/backend/utils/cache/lsyscache.c  | 27 +++++++++++
 src/include/catalog/dependency.h     |  2 -
 src/include/utils/lsyscache.h        |  1 +
 7 files changed, 29 insertions(+), 75 deletions(-)

diff --git a/src/backend/catalog/pg_depend.c b/src/backend/catalog/pg_depend.c
index 25290c821f..429791694f 100644
--- a/src/backend/catalog/pg_depend.c
+++ b/src/backend/catalog/pg_depend.c
@@ -968,75 +968,6 @@ getIdentitySequence(Oid relid, AttrNumber attnum, bool 
missing_ok)
        return linitial_oid(seqlist);
 }
 
-/*
- * get_constraint_index
- *             Given the OID of a unique, primary-key, or exclusion constraint,
- *             return the OID of the underlying index.
- *
- * Return InvalidOid if the index couldn't be found; this suggests the
- * given OID is bogus, but we leave it to caller to decide what to do.
- */
-Oid
-get_constraint_index(Oid constraintId)
-{
-       Oid                     indexId = InvalidOid;
-       Relation        depRel;
-       ScanKeyData key[3];
-       SysScanDesc scan;
-       HeapTuple       tup;
-
-       /* Search the dependency table for the dependent index */
-       depRel = table_open(DependRelationId, AccessShareLock);
-
-       ScanKeyInit(&key[0],
-                               Anum_pg_depend_refclassid,
-                               BTEqualStrategyNumber, F_OIDEQ,
-                               ObjectIdGetDatum(ConstraintRelationId));
-       ScanKeyInit(&key[1],
-                               Anum_pg_depend_refobjid,
-                               BTEqualStrategyNumber, F_OIDEQ,
-                               ObjectIdGetDatum(constraintId));
-       ScanKeyInit(&key[2],
-                               Anum_pg_depend_refobjsubid,
-                               BTEqualStrategyNumber, F_INT4EQ,
-                               Int32GetDatum(0));
-
-       scan = systable_beginscan(depRel, DependReferenceIndexId, true,
-                                                         NULL, 3, key);
-
-       while (HeapTupleIsValid(tup = systable_getnext(scan)))
-       {
-               Form_pg_depend deprec = (Form_pg_depend) GETSTRUCT(tup);
-
-               /*
-                * We assume any internal dependency of an index on the 
constraint
-                * must be what we are looking for.
-                */
-               if (deprec->classid == RelationRelationId &&
-                       deprec->objsubid == 0 &&
-                       deprec->deptype == DEPENDENCY_INTERNAL)
-               {
-                       char            relkind = 
get_rel_relkind(deprec->objid);
-
-                       /*
-                        * This is pure paranoia; there shouldn't be any other 
relkinds
-                        * dependent on a constraint.
-                        */
-                       if (relkind != RELKIND_INDEX &&
-                               relkind != RELKIND_PARTITIONED_INDEX)
-                               continue;
-
-                       indexId = deprec->objid;
-                       break;
-               }
-       }
-
-       systable_endscan(scan);
-       table_close(depRel, AccessShareLock);
-
-       return indexId;
-}
-
 /*
  * get_index_constraint
  *             Given the OID of an index, return the OID of the owning unique,
diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c
index 46f1637e77..1fa9f19f08 100644
--- a/src/backend/commands/tablecmds.c
+++ b/src/backend/commands/tablecmds.c
@@ -26,7 +26,6 @@
 #include "access/xact.h"
 #include "access/xlog.h"
 #include "catalog/catalog.h"
-#include "catalog/dependency.h"
 #include "catalog/heap.h"
 #include "catalog/index.h"
 #include "catalog/namespace.h"
diff --git a/src/backend/optimizer/util/plancat.c 
b/src/backend/optimizer/util/plancat.c
index 3e94256d34..daf1759623 100644
--- a/src/backend/optimizer/util/plancat.c
+++ b/src/backend/optimizer/util/plancat.c
@@ -26,7 +26,6 @@
 #include "access/transam.h"
 #include "access/xlog.h"
 #include "catalog/catalog.h"
-#include "catalog/dependency.h"
 #include "catalog/heap.h"
 #include "catalog/index.h"
 #include "catalog/pg_am.h"
diff --git a/src/backend/utils/adt/ruleutils.c 
b/src/backend/utils/adt/ruleutils.c
index c2c6df2a4f..ad582f99a5 100644
--- a/src/backend/utils/adt/ruleutils.c
+++ b/src/backend/utils/adt/ruleutils.c
@@ -24,7 +24,6 @@
 #include "access/relation.h"
 #include "access/sysattr.h"
 #include "access/table.h"
-#include "catalog/dependency.h"
 #include "catalog/pg_aggregate.h"
 #include "catalog/pg_am.h"
 #include "catalog/pg_authid.h"
@@ -2140,7 +2139,7 @@ pg_get_constraintdef_worker(Oid constraintId, bool 
fullCommand,
 
                                appendStringInfoChar(&buf, ')');
 
-                               indexId = get_constraint_index(constraintId);
+                               indexId = conForm->conindid;
 
                                /* Build including column list (from 
pg_index.indkeys) */
                                indtup = SearchSysCache1(INDEXRELID, 
ObjectIdGetDatum(indexId));
diff --git a/src/backend/utils/cache/lsyscache.c 
b/src/backend/utils/cache/lsyscache.c
index ae23299162..47a8365849 100644
--- a/src/backend/utils/cache/lsyscache.c
+++ b/src/backend/utils/cache/lsyscache.c
@@ -1094,6 +1094,33 @@ get_constraint_name(Oid conoid)
                return NULL;
 }
 
+/*
+ * get_constraint_index
+ *             Given the OID of a unique, primary-key, or exclusion constraint,
+ *             return the OID of the underlying index.
+ *
+ * Return InvalidOid if the index couldn't be found; this suggests the
+ * given OID is bogus, but we leave it to caller to decide what to do.
+ */
+Oid
+get_constraint_index(Oid conoid)
+{
+       HeapTuple       tp;
+
+       tp = SearchSysCache1(CONSTROID, ObjectIdGetDatum(conoid));
+       if (HeapTupleIsValid(tp))
+       {
+               Form_pg_constraint contup = (Form_pg_constraint) GETSTRUCT(tp);
+               Oid                     result;
+
+               result = contup->conindid;
+               ReleaseSysCache(tp);
+               return result;
+       }
+       else
+               return InvalidOid;
+}
+
 /*                             ---------- LANGUAGE CACHE ----------            
                         */
 
 char *
diff --git a/src/include/catalog/dependency.h b/src/include/catalog/dependency.h
index 901d5019cd..1fcc4a39ec 100644
--- a/src/include/catalog/dependency.h
+++ b/src/include/catalog/dependency.h
@@ -235,8 +235,6 @@ extern bool sequenceIsOwned(Oid seqId, char deptype, Oid 
*tableId, int32 *colId)
 extern List *getOwnedSequences(Oid relid);
 extern Oid     getIdentitySequence(Oid relid, AttrNumber attnum, bool 
missing_ok);
 
-extern Oid     get_constraint_index(Oid constraintId);
-
 extern Oid     get_index_constraint(Oid indexId);
 
 extern List *get_index_ref_constraints(Oid indexId);
diff --git a/src/include/utils/lsyscache.h b/src/include/utils/lsyscache.h
index fecfe1f4f6..c97e12dde8 100644
--- a/src/include/utils/lsyscache.h
+++ b/src/include/utils/lsyscache.h
@@ -96,6 +96,7 @@ extern Oid    get_cast_oid(Oid sourcetypeid, Oid 
targettypeid, bool missing_ok);
 extern char *get_collation_name(Oid colloid);
 extern bool get_collation_isdeterministic(Oid colloid);
 extern char *get_constraint_name(Oid conoid);
+extern Oid     get_constraint_index(Oid conoid);
 extern char *get_language_name(Oid langoid, bool missing_ok);
 extern Oid     get_opclass_family(Oid opclass);
 extern Oid     get_opclass_input_type(Oid opclass);
-- 
2.29.2

Reply via email to