Extend object-access hook machinery to support post-alter events.
authorRobert Haas
Mon, 18 Mar 2013 02:55:14 +0000 (22:55 -0400)
committerRobert Haas
Mon, 18 Mar 2013 02:57:26 +0000 (22:57 -0400)
This also slightly widens the scope of what we support in terms of
post-create events.

KaiGai Kohei, with a few changes, mostly to the comments, by me

31 files changed:
src/backend/catalog/aclchk.c
src/backend/catalog/heap.c
src/backend/catalog/index.c
src/backend/catalog/objectaccess.c
src/backend/catalog/pg_constraint.c
src/backend/catalog/pg_db_role_setting.c
src/backend/catalog/pg_type.c
src/backend/commands/alter.c
src/backend/commands/cluster.c
src/backend/commands/dbcommands.c
src/backend/commands/event_trigger.c
src/backend/commands/extension.c
src/backend/commands/foreigncmds.c
src/backend/commands/functioncmds.c
src/backend/commands/matview.c
src/backend/commands/opclasscmds.c
src/backend/commands/schemacmds.c
src/backend/commands/sequence.c
src/backend/commands/tablecmds.c
src/backend/commands/tablespace.c
src/backend/commands/trigger.c
src/backend/commands/tsearchcmds.c
src/backend/commands/typecmds.c
src/backend/commands/user.c
src/backend/rewrite/rewriteDefine.c
src/include/catalog/heap.h
src/include/catalog/index.h
src/include/catalog/objectaccess.h
src/include/catalog/pg_constraint.h
src/include/commands/cluster.h
src/include/commands/tablecmds.h

index 340350fa3950d09a67cb03cb525a8d67bd217328..976f2d204cd2cafcf3a960dabb2d37647472f447 100644 (file)
@@ -25,6 +25,7 @@
 #include "catalog/catalog.h"
 #include "catalog/dependency.h"
 #include "catalog/indexing.h"
+#include "catalog/objectaccess.h"
 #include "catalog/pg_authid.h"
 #include "catalog/pg_collation.h"
 #include "catalog/pg_conversion.h"
@@ -1290,6 +1291,13 @@ SetDefaultACL(InternalDefaultACL *iacls)
                              iacls->roleid,
                              noldmembers, oldmembers,
                              nnewmembers, newmembers);
+
+       if (isNew)
+           InvokeObjectPostCreateHook(DefaultAclRelationId,
+                                      HeapTupleGetOid(newtuple), 0);
+       else
+           InvokeObjectPostAlterHook(DefaultAclRelationId,
+                                     HeapTupleGetOid(newtuple), 0);
    }
 
    if (HeapTupleIsValid(tuple))
index 04a927dd0c6f15917c5d38d30392a547bcd886c7..0b4c659ff0751a48e69c4b7886a7ba38804eb46a 100644 (file)
@@ -96,8 +96,9 @@ static Oid AddNewRelationType(const char *typeName,
 static void RelationRemoveInheritance(Oid relid);
 static void StoreRelCheck(Relation rel, char *ccname, Node *expr,
              bool is_validated, bool is_local, int inhcount,
-             bool is_no_inherit);
-static void StoreConstraints(Relation rel, List *cooked_constraints);
+             bool is_no_inherit, bool is_internal);
+static void StoreConstraints(Relation rel, List *cooked_constraints,
+                            bool is_internal);
 static bool MergeWithExistingConstraint(Relation rel, char *ccname, Node *expr,
                            bool allow_merge, bool is_local,
                            bool is_no_inherit);
@@ -1302,7 +1303,7 @@ heap_create_with_catalog(const char *relname,
     * entry, so the relation must be valid and self-consistent at this point.
     * In particular, there are not yet constraints and defaults anywhere.
     */
-   StoreConstraints(new_rel_desc, cooked_constraints);
+   StoreConstraints(new_rel_desc, cooked_constraints, is_internal);
 
    /*
     * If there's a special on-commit action, remember it
@@ -1836,7 +1837,8 @@ heap_drop_with_catalog(Oid relid)
  * Store a default expression for column attnum of relation rel.
  */
 void
-StoreAttrDefault(Relation rel, AttrNumber attnum, Node *expr)
+StoreAttrDefault(Relation rel, AttrNumber attnum,
+                Node *expr, bool is_internal)
 {
    char       *adbin;
    char       *adsrc;
@@ -1928,6 +1930,17 @@ StoreAttrDefault(Relation rel, AttrNumber attnum, Node *expr)
     * Record dependencies on objects used in the expression, too.
     */
    recordDependencyOnExpr(&defobject, expr, NIL, DEPENDENCY_NORMAL);
+
+   /*
+    * Post creation hook for attribute defaults.
+    *
+    * XXX. ALTER TABLE ALTER COLUMN SET/DROP DEFAULT is implemented
+    * with a couple of deletion/creation of the attribute's default entry,
+    * so the callee should check existence of an older version of this
+    * entry if it needs to distinguish.
+    */
+   InvokeObjectPostCreateHookArg(AttrDefaultRelationId,
+                                 RelationGetRelid(rel), attnum, is_internal);
 }
 
 /*
@@ -1939,7 +1952,7 @@ StoreAttrDefault(Relation rel, AttrNumber attnum, Node *expr)
 static void
 StoreRelCheck(Relation rel, char *ccname, Node *expr,
              bool is_validated, bool is_local, int inhcount,
-             bool is_no_inherit)
+             bool is_no_inherit, bool is_internal)
 {
    char       *ccbin;
    char       *ccsrc;
@@ -2023,7 +2036,8 @@ StoreRelCheck(Relation rel, char *ccname, Node *expr,
                          ccsrc,    /* Source form of check constraint */
                          is_local,     /* conislocal */
                          inhcount,     /* coninhcount */
-                         is_no_inherit);       /* connoinherit */
+                         is_no_inherit,        /* connoinherit */
+                         is_internal); /* internally constructed? */
 
    pfree(ccbin);
    pfree(ccsrc);
@@ -2038,7 +2052,7 @@ StoreRelCheck(Relation rel, char *ccname, Node *expr,
  * and StoreRelCheck (see AddRelationNewConstraints()).
  */
 static void
-StoreConstraints(Relation rel, List *cooked_constraints)
+StoreConstraints(Relation rel, List *cooked_constraints, bool is_internal)
 {
    int         numchecks = 0;
    ListCell   *lc;
@@ -2060,11 +2074,12 @@ StoreConstraints(Relation rel, List *cooked_constraints)
        switch (con->contype)
        {
            case CONSTR_DEFAULT:
-               StoreAttrDefault(rel, con->attnum, con->expr);
+               StoreAttrDefault(rel, con->attnum, con->expr, is_internal);
                break;
            case CONSTR_CHECK:
                StoreRelCheck(rel, con->name, con->expr, !con->skip_validation,
-                          con->is_local, con->inhcount, con->is_no_inherit);
+                             con->is_local, con->inhcount,
+                             con->is_no_inherit, is_internal);
                numchecks++;
                break;
            default:
@@ -2090,6 +2105,7 @@ StoreConstraints(Relation rel, List *cooked_constraints)
  * newConstraints: list of Constraint nodes
  * allow_merge: TRUE if check constraints may be merged with existing ones
  * is_local: TRUE if definition is local, FALSE if it's inherited
+ * is_internal: TRUE if result of some internal process, not a user request
  *
  * All entries in newColDefaults will be processed.  Entries in newConstraints
  * will be processed only if they are CONSTR_CHECK type.
@@ -2107,7 +2123,8 @@ AddRelationNewConstraints(Relation rel,
                          List *newColDefaults,
                          List *newConstraints,
                          bool allow_merge,
-                         bool is_local)
+                         bool is_local,
+                         bool is_internal)
 {
    List       *cookedConstraints = NIL;
    TupleDesc   tupleDesc;
@@ -2170,7 +2187,7 @@ AddRelationNewConstraints(Relation rel,
            (IsA(expr, Const) &&((Const *) expr)->constisnull))
            continue;
 
-       StoreAttrDefault(rel, colDef->attnum, expr);
+       StoreAttrDefault(rel, colDef->attnum, expr, is_internal);
 
        cooked = (CookedConstraint *) palloc(sizeof(CookedConstraint));
        cooked->contype = CONSTR_DEFAULT;
@@ -2296,7 +2313,7 @@ AddRelationNewConstraints(Relation rel,
         * OK, store it.
         */
        StoreRelCheck(rel, ccname, expr, !cdef->skip_validation, is_local,
-                     is_local ? 0 : 1, cdef->is_no_inherit);
+                     is_local ? 0 : 1, cdef->is_no_inherit, is_internal);
 
        numchecks++;
 
index 33a18030b797797df7b1f2f30706b8ab2ab42886..7966558218f4f24cd9bf8953b473f212a0454fc1 100644 (file)
@@ -933,7 +933,8 @@ index_create(Relation heapRelation,
                                    false,      /* already marked primary */
                                    false,      /* pg_index entry is OK */
                                    false,      /* no old dependencies */
-                                   allow_system_table_mods);
+                                   allow_system_table_mods,
+                                   is_internal);
        }
        else
        {
@@ -1107,6 +1108,7 @@ index_create(Relation heapRelation,
  * remove_old_dependencies: if true, remove existing dependencies of index
  *     on table's columns
  * allow_system_table_mods: allow table to be a system catalog
+ * is_internal: index is constructed due to internal process
  */
 void
 index_constraint_create(Relation heapRelation,
@@ -1119,7 +1121,8 @@ index_constraint_create(Relation heapRelation,
                        bool mark_as_primary,
                        bool update_pgindex,
                        bool remove_old_dependencies,
-                       bool allow_system_table_mods)
+                       bool allow_system_table_mods,
+                       bool is_internal)
 {
    Oid         namespaceId = RelationGetNamespace(heapRelation);
    ObjectAddress myself,
@@ -1184,7 +1187,8 @@ index_constraint_create(Relation heapRelation,
                                   NULL,
                                   true,        /* islocal */
                                   0,   /* inhcount */
-                                  true);       /* noinherit */
+                                  true,        /* noinherit */
+                                  is_internal);
 
    /*
     * Register the index as internally dependent on the constraint.
@@ -1293,6 +1297,9 @@ index_constraint_create(Relation heapRelation,
        {
            simple_heap_update(pg_index, &indexTuple->t_self, indexTuple);
            CatalogUpdateIndexes(pg_index, indexTuple);
+
+           InvokeObjectPostAlterHookArg(IndexRelationId, indexRelationId, 0,
+                                        InvalidOid, is_internal);
        }
 
        heap_freetuple(indexTuple);
index 09f9db5aaf83f2c0b61c7df6e3ad2ce3dca67d24..bc565ebe497f3ef72ff67e9f6142394a9523cfe1 100644 (file)
@@ -61,3 +61,26 @@ RunObjectDropHook(Oid classId, Oid objectId, int subId,
                          classId, objectId, subId,
                          (void *) &drop_arg);
 }
+
+/*
+ * RunObjectPostAlterHook
+ *
+ * It is entrypoint of OAT_POST_ALTER event
+ */
+void
+RunObjectPostAlterHook(Oid classId, Oid objectId, int subId,
+                      Oid auxiliaryId, bool is_internal)
+{
+   ObjectAccessPostAlter   pa_arg;
+
+   /* caller should check, but just in case... */
+   Assert(object_access_hook != NULL);
+
+   memset(&pa_arg, 0, sizeof(ObjectAccessPostAlter));
+   pa_arg.auxiliary_id = auxiliaryId;
+   pa_arg.is_internal = is_internal;
+
+   (*object_access_hook)(OAT_POST_ALTER,
+                         classId, objectId, subId,
+                         (void *) &pa_arg);
+}
index 547c7ee00c623e160e708c39105ba539c6efcdbf..7ddadcce4da96b9f28cc9c7455d94d93cf64b1a7 100644 (file)
@@ -68,7 +68,8 @@ CreateConstraintEntry(const char *constraintName,
                      const char *conSrc,
                      bool conIsLocal,
                      int conInhCount,
-                     bool conNoInherit)
+                     bool conNoInherit,
+                     bool is_internal)
 {
    Relation    conDesc;
    Oid         conOid;
@@ -367,7 +368,8 @@ CreateConstraintEntry(const char *constraintName,
    }
 
    /* Post creation hook for new constraint */
-   InvokeObjectPostCreateHook(ConstraintRelationId, conOid, 0);
+   InvokeObjectPostCreateHookArg(ConstraintRelationId, conOid, 0,
+                                 is_internal);
 
    return conOid;
 }
@@ -665,6 +667,8 @@ RenameConstraintById(Oid conId, const char *newname)
    /* update the system catalog indexes */
    CatalogUpdateIndexes(conDesc, tuple);
 
+   InvokeObjectPostAlterHook(ConstraintRelationId, conId, 0);
+
    heap_freetuple(tuple);
    heap_close(conDesc, RowExclusiveLock);
 }
@@ -737,6 +741,8 @@ AlterConstraintNamespaces(Oid ownerId, Oid oldNspId,
             */
        }
 
+       InvokeObjectPostAlterHook(ConstraintRelationId, thisobj.objectId, 0);
+
        add_exact_object_address(&thisobj, objsMoved);
    }
 
index 337ccdd633b4c4afefab843251e8781d0a044a6f..45949129cfbe38a57c34c425ba0c719b1d5cfb60 100644 (file)
@@ -14,6 +14,7 @@
 #include "access/heapam.h"
 #include "access/htup_details.h"
 #include "catalog/indexing.h"
+#include "catalog/objectaccess.h"
 #include "catalog/pg_db_role_setting.h"
 #include "utils/fmgroids.h"
 #include "utils/rel.h"
@@ -160,6 +161,9 @@ AlterSetting(Oid databaseid, Oid roleid, VariableSetStmt *setstmt)
        CatalogUpdateIndexes(rel, newtuple);
    }
 
+   InvokeObjectPostAlterHookArg(DbRoleSettingRelationId,
+                                databaseid, 0, roleid, false);
+
    systable_endscan(scan);
 
    /* Close pg_db_role_setting, but keep lock till commit */
index b044400d993af128fb0a73e546b3e4bc68dbf692..23ac3dd33657006838e796825eaa601d1a103eac 100644 (file)
@@ -712,6 +712,8 @@ RenameTypeInternal(Oid typeOid, const char *newTypeName, Oid typeNamespace)
    /* update the system catalog indexes */
    CatalogUpdateIndexes(pg_type_desc, tuple);
 
+   InvokeObjectPostAlterHook(TypeRelationId, typeOid, 0);
+
    heap_freetuple(tuple);
    heap_close(pg_type_desc, RowExclusiveLock);
 
index 416a068fc755a6f2a8a610c36b5705521c65caa9..2d2ab1bcfb148079757e7789853388fb6228f44e 100644 (file)
@@ -19,6 +19,7 @@
 #include "catalog/dependency.h"
 #include "catalog/indexing.h"
 #include "catalog/namespace.h"
+#include "catalog/objectaccess.h"
 #include "catalog/pg_collation.h"
 #include "catalog/pg_conversion.h"
 #include "catalog/pg_event_trigger.h"
@@ -281,6 +282,8 @@ AlterObjectRename_internal(Relation rel, Oid objectId, const char *new_name)
    simple_heap_update(rel, &oldtup->t_self, newtup);
    CatalogUpdateIndexes(rel, newtup);
 
+   InvokeObjectPostAlterHook(classId, objectId, 0);
+
    /* Release memory */
    pfree(values);
    pfree(nulls);
@@ -657,6 +660,8 @@ AlterObjectNamespace_internal(Relation rel, Oid objid, Oid nspOid)
    changeDependencyFor(classId, objid,
                        NamespaceRelationId, oldNspOid, nspOid);
 
+   InvokeObjectPostAlterHook(classId, objid, 0);
+
    return oldNspOid;
 }
 
@@ -934,4 +939,6 @@ AlterObjectOwner_internal(Relation rel, Oid objectId, Oid new_ownerId)
        pfree(nulls);
        pfree(replaces);
    }
+
+   InvokeObjectPostAlterHook(classId, objectId, 0);
 }
index 8ab8c1751952aa9c01a477f6aa80806cb67d2793..ef9c5f1adc7242cf504f40878c4eee87019a3e06 100644 (file)
@@ -27,6 +27,7 @@
 #include "catalog/heap.h"
 #include "catalog/index.h"
 #include "catalog/namespace.h"
+#include "catalog/objectaccess.h"
 #include "catalog/toasting.h"
 #include "commands/cluster.h"
 #include "commands/matview.h"
@@ -481,7 +482,7 @@ check_index_is_clusterable(Relation OldHeap, Oid indexOid, bool recheck, LOCKMOD
  * otherwise concurrent executions of RelationGetIndexList could miss indexes.
  */
 void
-mark_index_clustered(Relation rel, Oid indexOid)
+mark_index_clustered(Relation rel, Oid indexOid, bool is_internal)
 {
    HeapTuple   indexTuple;
    Form_pg_index indexForm;
@@ -541,6 +542,10 @@ mark_index_clustered(Relation rel, Oid indexOid)
            simple_heap_update(pg_index, &indexTuple->t_self, indexTuple);
            CatalogUpdateIndexes(pg_index, indexTuple);
        }
+
+       InvokeObjectPostAlterHookArg(IndexRelationId, thisIndexOid, 0,
+                                    InvalidOid, is_internal);
+
        heap_freetuple(indexTuple);
    }
 
@@ -569,7 +574,7 @@ rebuild_relation(Relation OldHeap, Oid indexOid,
 
    /* Mark the correct index as clustered */
    if (OidIsValid(indexOid))
-       mark_index_clustered(OldHeap, indexOid);
+       mark_index_clustered(OldHeap, indexOid, true);
 
    /* Remember if it's a system catalog */
    is_system_catalog = IsSystemRelation(OldHeap);
@@ -590,7 +595,8 @@ rebuild_relation(Relation OldHeap, Oid indexOid,
     * rebuild the target's indexes and throw away the transient table.
     */
    finish_heap_swap(tableOid, OIDNewHeap, is_system_catalog,
-                    swap_toast_by_content, false, frozenXid, frozenMulti);
+                    swap_toast_by_content, false, true,
+                    frozenXid, frozenMulti);
 }
 
 
@@ -1120,6 +1126,7 @@ copy_heap_data(Oid OIDNewHeap, Oid OIDOldHeap, Oid OIDOldIndex,
 static void
 swap_relation_files(Oid r1, Oid r2, bool target_is_pg_class,
                    bool swap_toast_by_content,
+                   bool is_internal,
                    TransactionId frozenXid,
                    MultiXactId frozenMulti,
                    Oid *mapped_tables)
@@ -1283,6 +1290,15 @@ swap_relation_files(Oid r1, Oid r2, bool target_is_pg_class,
        CacheInvalidateRelcacheByTuple(reltup2);
    }
 
+   /*
+    * Post alter hook for modified relations. The change to r2 is always
+    * internal, but r1 depends on the invocation context.
+    */
+   InvokeObjectPostAlterHookArg(RelationRelationId, r1, 0,
+                                InvalidOid, is_internal);
+   InvokeObjectPostAlterHookArg(RelationRelationId, r2, 0,
+                                InvalidOid, true);
+
    /*
     * If we have toast tables associated with the relations being swapped,
     * deal with them too.
@@ -1298,6 +1314,7 @@ swap_relation_files(Oid r1, Oid r2, bool target_is_pg_class,
                                    relform2->reltoastrelid,
                                    target_is_pg_class,
                                    swap_toast_by_content,
+                                   is_internal,
                                    frozenXid,
                                    frozenMulti,
                                    mapped_tables);
@@ -1388,6 +1405,7 @@ swap_relation_files(Oid r1, Oid r2, bool target_is_pg_class,
                            relform2->reltoastidxid,
                            target_is_pg_class,
                            swap_toast_by_content,
+                           is_internal,
                            InvalidTransactionId,
                            InvalidMultiXactId,
                            mapped_tables);
@@ -1427,6 +1445,7 @@ finish_heap_swap(Oid OIDOldHeap, Oid OIDNewHeap,
                 bool is_system_catalog,
                 bool swap_toast_by_content,
                 bool check_constraints,
+                bool is_internal,
                 TransactionId frozenXid,
                 MultiXactId frozenMulti)
 {
@@ -1444,8 +1463,8 @@ finish_heap_swap(Oid OIDOldHeap, Oid OIDNewHeap,
     */
    swap_relation_files(OIDOldHeap, OIDNewHeap,
                        (OIDOldHeap == RelationRelationId),
-                       swap_toast_by_content, frozenXid, frozenMulti,
-                       mapped_tables);
+                       swap_toast_by_content, is_internal,
+                       frozenXid, frozenMulti, mapped_tables);
 
    /*
     * If it's a system catalog, queue an sinval message to flush all
@@ -1526,13 +1545,13 @@ finish_heap_swap(Oid OIDOldHeap, Oid OIDNewHeap,
            snprintf(NewToastName, NAMEDATALEN, "pg_toast_%u",
                     OIDOldHeap);
            RenameRelationInternal(newrel->rd_rel->reltoastrelid,
-                                  NewToastName);
+                                  NewToastName, true);
 
            /* ... and its index too */
            snprintf(NewToastName, NAMEDATALEN, "pg_toast_%u_index",
                     OIDOldHeap);
            RenameRelationInternal(toastidx,
-                                  NewToastName);
+                                  NewToastName, true);
        }
        relation_close(newrel, NoLock);
    }
index 76ef23a1f44ade7f3bbc12162808f048c80546de..b3911bff350e625b4be2c2f02302cb2a82423f8c 100644 (file)
@@ -997,6 +997,8 @@ RenameDatabase(const char *oldname, const char *newname)
    simple_heap_update(rel, &newtup->t_self, newtup);
    CatalogUpdateIndexes(rel, newtup);
 
+   InvokeObjectPostAlterHook(DatabaseRelationId, db_id, 0);
+
    /*
     * Close pg_database, but keep lock till commit.
     */
@@ -1234,6 +1236,9 @@ movedb(const char *dbname, const char *tblspcname)
        /* Update indexes */
        CatalogUpdateIndexes(pgdbrel, newtuple);
 
+       InvokeObjectPostAlterHook(DatabaseRelationId,
+                                 HeapTupleGetOid(newtuple), 0);
+
        systable_endscan(sysscan);
 
        /*
@@ -1431,6 +1436,9 @@ AlterDatabase(AlterDatabaseStmt *stmt, bool isTopLevel)
    /* Update indexes */
    CatalogUpdateIndexes(rel, newtuple);
 
+   InvokeObjectPostAlterHook(DatabaseRelationId,
+                             HeapTupleGetOid(newtuple), 0);
+
    systable_endscan(scan);
 
    /* Close pg_database, but keep lock till commit */
@@ -1570,6 +1578,8 @@ AlterDatabaseOwner(const char *dbname, Oid newOwnerId)
                                newOwnerId);
    }
 
+   InvokeObjectPostAlterHook(DatabaseRelationId, HeapTupleGetOid(tuple), 0);
+
    systable_endscan(scan);
 
    /* Close pg_database, but keep lock till commit */
index 2c3b6bf1dfaf68954c296cf58c666bda536a0180..fbe8f49a9e71c2fea6b4915ac2f7f1977747c588 100644 (file)
@@ -412,6 +412,9 @@ AlterEventTrigger(AlterEventTrigStmt *stmt)
    simple_heap_update(tgrel, &tup->t_self, tup);
    CatalogUpdateIndexes(tgrel, tup);
 
+   InvokeObjectPostAlterHook(EventTriggerRelationId,
+                             trigoid, 0);
+
    /* clean up */
    heap_freetuple(tup);
    heap_close(tgrel, RowExclusiveLock);
@@ -507,6 +510,9 @@ AlterEventTriggerOwner_internal(Relation rel, HeapTuple tup, Oid newOwnerId)
    changeDependencyOnOwner(EventTriggerRelationId,
                            HeapTupleGetOid(tup),
                            newOwnerId);
+
+   InvokeObjectPostAlterHook(EventTriggerRelationId,
+                             HeapTupleGetOid(tup), 0);
 }
 
 /*
index 6b7cb5bc84237a1962e8cb2248c99f3a81af5291..36df8bddcad8c94a59d91b0c7115dbcb4b5949f0 100644 (file)
@@ -2573,6 +2573,8 @@ AlterExtensionNamespace(List *names, const char *newschema)
    changeDependencyFor(ExtensionRelationId, extensionOid,
                        NamespaceRelationId, oldNspOid, nspOid);
 
+   InvokeObjectPostAlterHook(ExtensionRelationId, extensionOid, 0);
+
    return extensionOid;
 }
 
@@ -2856,6 +2858,8 @@ ApplyExtensionUpdates(Oid extensionOid,
            recordDependencyOn(&myself, &otherext, DEPENDENCY_NORMAL);
        }
 
+       InvokeObjectPostAlterHook(ExtensionRelationId, extensionOid, 0);
+
        /*
         * Finally, execute the update script file
         */
@@ -2969,6 +2973,8 @@ ExecAlterExtensionContentsStmt(AlterExtensionContentsStmt *stmt)
            extension_config_remove(extension.objectId, object.objectId);
    }
 
+   InvokeObjectPostAlterHook(ExtensionRelationId, extension.objectId, 0);
+
    /*
     * If get_object_address() opened the relation for us, we close it to keep
     * the reference count correct - but we retain any locks acquired by
index 83cdf9e3c51e90154198547394645ef419177aeb..fb311185c8beeb38a8f1144b84875b9eb8642427 100644 (file)
@@ -241,6 +241,9 @@ AlterForeignDataWrapperOwner_internal(Relation rel, HeapTuple tup, Oid newOwnerI
                                HeapTupleGetOid(tup),
                                newOwnerId);
    }
+
+   InvokeObjectPostAlterHook(ForeignDataWrapperRelationId,
+                             HeapTupleGetOid(tup), 0);
 }
 
 /*
@@ -349,6 +352,9 @@ AlterForeignServerOwner_internal(Relation rel, HeapTuple tup, Oid newOwnerId)
        changeDependencyOnOwner(ForeignServerRelationId, HeapTupleGetOid(tup),
                                newOwnerId);
    }
+
+   InvokeObjectPostAlterHook(ForeignServerRelationId,
+                             HeapTupleGetOid(tup), 0);
 }
 
 /*
@@ -764,6 +770,8 @@ AlterForeignDataWrapper(AlterFdwStmt *stmt)
        }
    }
 
+   InvokeObjectPostAlterHook(ForeignDataWrapperRelationId, fdwId, 0);
+
    heap_close(rel, RowExclusiveLock);
 
    return fdwId;
@@ -994,6 +1002,8 @@ AlterForeignServer(AlterForeignServerStmt *stmt)
    simple_heap_update(rel, &tp->t_self, tp);
    CatalogUpdateIndexes(rel, tp);
 
+   InvokeObjectPostAlterHook(ForeignServerRelationId, srvId, 0);
+
    heap_freetuple(tp);
 
    heap_close(rel, RowExclusiveLock);
index fda379a75df3b995ec3cf8d48f621e0d315d5209..9f0ac9bd50a86d8387011415c7d146e1f824f6cf 100644 (file)
@@ -1169,6 +1169,8 @@ AlterFunction(AlterFunctionStmt *stmt)
    simple_heap_update(rel, &tup->t_self, tup);
    CatalogUpdateIndexes(rel, tup);
 
+   InvokeObjectPostAlterHook(ProcedureRelationId, funcOid, 0);
+
    heap_close(rel, NoLock);
    heap_freetuple(tup);
 
index 6a0643828a4f728689c9c3057cb10a459b372823..e20fedaeaf77772a47b34f423ddeb062b429bf1f 100644 (file)
@@ -198,8 +198,8 @@ ExecRefreshMatView(RefreshMatViewStmt *stmt, const char *queryString,
     * Swap the physical files of the target and transient tables, then
     * rebuild the target's indexes and throw away the transient table.
     */
-   finish_heap_swap(matviewOid, OIDNewHeap, false, false, true, RecentXmin,
-                    ReadNextMultiXactId());
+   finish_heap_swap(matviewOid, OIDNewHeap, false, false, true, true,
+                    RecentXmin, ReadNextMultiXactId());
 
    RelationCacheInvalidateEntry(matviewOid);
 }
index e9563fbfab4bda3af3b44296572b144785fddeb5..68ec57ac4b6d683b5ce796524e4b89433b07aead 100644 (file)
@@ -1374,6 +1374,9 @@ storeOperators(List *opfamilyname, Oid amoid,
            referenced.objectSubId = 0;
            recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
        }
+       /* Post create hook of this access method operator */
+       InvokeObjectPostCreateHook(AccessMethodOperatorRelationId,
+                                  entryoid, 0);
    }
 
    heap_close(rel, RowExclusiveLock);
@@ -1473,6 +1476,9 @@ storeProcedures(List *opfamilyname, Oid amoid,
            referenced.objectSubId = 0;
            recordDependencyOn(&myself, &referenced, DEPENDENCY_AUTO);
        }
+       /* Post create hook of access method procedure */
+       InvokeObjectPostCreateHook(AccessMethodProcedureRelationId,
+                                  entryoid, 0);
    }
 
    heap_close(rel, RowExclusiveLock);
index 1e857d988fed089ba2be2570b1cc49416f3f8674..21d7e608df43bf48f045e2a20af2d269d739e94c 100644 (file)
@@ -21,6 +21,7 @@
 #include "catalog/dependency.h"
 #include "catalog/indexing.h"
 #include "catalog/namespace.h"
+#include "catalog/objectaccess.h"
 #include "catalog/pg_namespace.h"
 #include "commands/dbcommands.h"
 #include "commands/schemacmds.h"
@@ -240,6 +241,8 @@ RenameSchema(const char *oldname, const char *newname)
    simple_heap_update(rel, &tup->t_self, tup);
    CatalogUpdateIndexes(rel, tup);
 
+   InvokeObjectPostAlterHook(NamespaceRelationId, HeapTupleGetOid(tup), 0);
+
    heap_close(rel, NoLock);
    heap_freetuple(tup);
 
@@ -376,4 +379,6 @@ AlterSchemaOwner_internal(HeapTuple tup, Relation rel, Oid newOwnerId)
                                newOwnerId);
    }
 
+   InvokeObjectPostAlterHook(NamespaceRelationId,
+                             HeapTupleGetOid(tup), 0);
 }
index de41c8a1c71500d3f430110037d161432cf78802..225edd9f9b7c8e317c4c6e66151444ce6a947aed 100644 (file)
@@ -20,6 +20,7 @@
 #include "access/xlogutils.h"
 #include "catalog/dependency.h"
 #include "catalog/namespace.h"
+#include "catalog/objectaccess.h"
 #include "catalog/pg_type.h"
 #include "commands/defrem.h"
 #include "commands/sequence.h"
@@ -487,6 +488,8 @@ AlterSequence(AlterSeqStmt *stmt)
    if (owned_by)
        process_owned_by(seqrel, owned_by);
 
+   InvokeObjectPostAlterHook(RelationRelationId, relid, 0);
+
    relation_close(seqrel, NoLock);
 
    return relid;
index 8bb8f54ae52d23f398e085872c4729dd013a5c78..51bf13944b2a6a54d65c7f58a7b521b9287f3e57 100644 (file)
@@ -669,7 +669,7 @@ DefineRelation(CreateStmt *stmt, char relkind, Oid ownerId)
     */
    if (rawDefaults || stmt->constraints)
        AddRelationNewConstraints(rel, rawDefaults, stmt->constraints,
-                                 true, true);
+                                 true, true, false);
 
    /*
     * Clean up.  We keep lock on new relation (although it shouldn't be
@@ -1975,6 +1975,15 @@ StoreCatalogInheritance1(Oid relationId, Oid parentOid,
 
    recordDependencyOn(&childobject, &parentobject, DEPENDENCY_NORMAL);
 
+   /*
+    * Post creation hook of this inheritance. Since object_access_hook
+    * doesn't take multiple object identifiers, we relay oid of parent
+    * relation using auxiliary_id argument.
+    */
+   InvokeObjectPostAlterHookArg(InheritsRelationId,
+                                relationId, 0,
+                                parentOid, false);
+
    /*
     * Mark the parent as having subclasses.
     */
@@ -2234,6 +2243,8 @@ renameatt_internal(Oid myrelid,
    /* keep system catalog indexes current */
    CatalogUpdateIndexes(attrelation, atttup);
 
+   InvokeObjectPostAlterHook(RelationRelationId, myrelid, attnum);
+
    heap_freetuple(atttup);
 
    heap_close(attrelation, RowExclusiveLock);
@@ -2381,7 +2392,7 @@ rename_constraint_internal(Oid myrelid,
            || con->contype == CONSTRAINT_UNIQUE
            || con->contype == CONSTRAINT_EXCLUSION))
        /* rename the index; this renames the constraint as well */
-       RenameRelationInternal(con->conindid, newconname);
+       RenameRelationInternal(con->conindid, newconname, false);
    else
        RenameConstraintById(constraintOid, newconname);
 
@@ -2461,7 +2472,7 @@ RenameRelation(RenameStmt *stmt)
    }
 
    /* Do the work */
-   RenameRelationInternal(relid, stmt->newname);
+   RenameRelationInternal(relid, stmt->newname, false);
 
    return relid;
 }
@@ -2476,7 +2487,7 @@ RenameRelation(RenameStmt *stmt)
  *           sequence, AFAIK there's no need for it to be there.
  */
 void
-RenameRelationInternal(Oid myrelid, const char *newrelname)
+RenameRelationInternal(Oid myrelid, const char *newrelname, bool is_internal)
 {
    Relation    targetrelation;
    Relation    relrelation;    /* for RELATION relation */
@@ -2518,6 +2529,9 @@ RenameRelationInternal(Oid myrelid, const char *newrelname)
    /* keep the system catalog indexes current */
    CatalogUpdateIndexes(relrelation, reltup);
 
+   InvokeObjectPostAlterHookArg(RelationRelationId, myrelid, 0,
+                                InvalidOid, is_internal);
+
    heap_freetuple(reltup);
    heap_close(relrelation, RowExclusiveLock);
 
@@ -3531,7 +3545,9 @@ ATRewriteTables(List **wqueue, LOCKMODE lockmode)
             * interest in letting this code work on system catalogs.
             */
            finish_heap_swap(tab->relid, OIDNewHeap,
-                            false, false, true, RecentXmin,
+                            false, false, true,
+                            !OidIsValid(tab->newTableSpace),
+                            RecentXmin,
                             ReadNextMultiXactId());
        }
        else
@@ -4531,7 +4547,8 @@ ATExecAddColumn(List **wqueue, AlteredTableInfo *tab, Relation rel,
         * This function is intended for CREATE TABLE, so it processes a
         * _list_ of defaults, but we just do one.
         */
-       AddRelationNewConstraints(rel, list_make1(rawEnt), NIL, false, true);
+       AddRelationNewConstraints(rel, list_make1(rawEnt), NIL,
+                                 false, true, false);
 
        /* Make the additional catalog changes visible */
        CommandCounterIncrement();
@@ -4869,6 +4886,9 @@ ATExecDropNotNull(Relation rel, const char *colName, LOCKMODE lockmode)
        CatalogUpdateIndexes(attr_rel, tuple);
    }
 
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel), attnum);
+
    heap_close(attr_rel, RowExclusiveLock);
 }
 
@@ -4921,6 +4941,9 @@ ATExecSetNotNull(AlteredTableInfo *tab, Relation rel,
        tab->new_notnull = true;
    }
 
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel), attnum);
+
    heap_close(attr_rel, RowExclusiveLock);
 }
 
@@ -4975,7 +4998,8 @@ ATExecColumnDefault(Relation rel, const char *colName,
         * This function is intended for CREATE TABLE, so it processes a
         * _list_ of defaults, but we just do one.
         */
-       AddRelationNewConstraints(rel, list_make1(rawEnt), NIL, false, true);
+       AddRelationNewConstraints(rel, list_make1(rawEnt), NIL,
+                                 false, true, false);
    }
 }
 
@@ -5060,6 +5084,9 @@ ATExecSetStatistics(Relation rel, const char *colName, Node *newValue, LOCKMODE
    /* keep system catalog indexes current */
    CatalogUpdateIndexes(attrelation, tuple);
 
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel),
+                             attrtuple->attnum);
    heap_freetuple(tuple);
 
    heap_close(attrelation, RowExclusiveLock);
@@ -5117,13 +5144,18 @@ ATExecSetOptions(Relation rel, const char *colName, Node *options,
    repl_repl[Anum_pg_attribute_attoptions - 1] = true;
    newtuple = heap_modify_tuple(tuple, RelationGetDescr(attrelation),
                                 repl_val, repl_null, repl_repl);
-   ReleaseSysCache(tuple);
 
    /* Update system catalog. */
    simple_heap_update(attrelation, &newtuple->t_self, newtuple);
    CatalogUpdateIndexes(attrelation, newtuple);
+
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel),
+                             attrtuple->attnum);
    heap_freetuple(newtuple);
 
+   ReleaseSysCache(tuple);
+
    heap_close(attrelation, RowExclusiveLock);
 }
 
@@ -5193,6 +5225,10 @@ ATExecSetStorage(Relation rel, const char *colName, Node *newValue, LOCKMODE loc
    /* keep system catalog indexes current */
    CatalogUpdateIndexes(attrelation, tuple);
 
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel),
+                             attrtuple->attnum);
+
    heap_freetuple(tuple);
 
    heap_close(attrelation, RowExclusiveLock);
@@ -5507,7 +5543,7 @@ ATExecAddIndexConstraint(AlteredTableInfo *tab, Relation rel,
        ereport(NOTICE,
                (errmsg("ALTER TABLE / ADD CONSTRAINT USING INDEX will rename index \"%s\" to \"%s\"",
                        indexName, constraintName)));
-       RenameRelationInternal(index_oid, constraintName);
+       RenameRelationInternal(index_oid, constraintName, false);
    }
 
    /* Extra checks needed if making primary key */
@@ -5531,7 +5567,8 @@ ATExecAddIndexConstraint(AlteredTableInfo *tab, Relation rel,
                            stmt->primary,
                            true, /* update pg_index */
                            true, /* remove old dependencies */
-                           allowSystemTableMods);
+                           allowSystemTableMods,
+                           false); /* is_internal */
 
    index_close(indexRel, NoLock);
 }
@@ -5643,7 +5680,8 @@ ATAddCheckConstraint(List **wqueue, AlteredTableInfo *tab, Relation rel,
    newcons = AddRelationNewConstraints(rel, NIL,
                                        list_make1(copyObject(constr)),
                                        recursing,      /* allow_merge */
-                                       !recursing);    /* is_local */
+                                       !recursing,     /* is_local */
+                                       is_readd);      /* is_internal */
 
    /* Add each to-be-validated constraint to Phase 3's queue */
    foreach(lcon, newcons)
@@ -6097,7 +6135,8 @@ ATAddForeignKeyConstraint(AlteredTableInfo *tab, Relation rel,
                                      NULL,
                                      true,     /* islocal */
                                      0,        /* inhcount */
-                                     true);    /* isnoinherit */
+                                     true,     /* isnoinherit */
+                                     false);   /* is_internal */
 
    /*
     * Create the triggers that will enforce the constraint.
@@ -6279,6 +6318,10 @@ ATExecValidateConstraint(Relation rel, char *constrName, bool recurse,
        copy_con->convalidated = true;
        simple_heap_update(conrel, ©Tuple->t_self, copyTuple);
        CatalogUpdateIndexes(conrel, copyTuple);
+
+       InvokeObjectPostAlterHook(ConstraintRelationId,
+                                 HeapTupleGetOid(tuple), 0);
+
        heap_freetuple(copyTuple);
    }
 
@@ -7707,6 +7750,9 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
     */
    RemoveStatistics(RelationGetRelid(rel), attnum);
 
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel), attnum);
+
    /*
     * Update the default, if present, by brute force --- remove and re-add
     * the default.  Probably unsafe to take shortcuts, since the new version
@@ -7726,7 +7772,7 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
        RemoveAttrDefault(RelationGetRelid(rel), attnum, DROP_RESTRICT, true,
                          true);
 
-       StoreAttrDefault(rel, attnum, defaultexpr);
+       StoreAttrDefault(rel, attnum, defaultexpr, true);
    }
 
    /* Cleanup */
@@ -7817,11 +7863,16 @@ ATExecAlterColumnGenericOptions(Relation rel,
 
    newtuple = heap_modify_tuple(tuple, RelationGetDescr(attrel),
                                 repl_val, repl_null, repl_repl);
-   ReleaseSysCache(tuple);
 
    simple_heap_update(attrel, &newtuple->t_self, newtuple);
    CatalogUpdateIndexes(attrel, newtuple);
 
+   InvokeObjectPostAlterHook(RelationRelationId,
+                             RelationGetRelid(rel),
+                             atttableform->attnum);
+
+   ReleaseSysCache(tuple);
+
    heap_close(attrel, RowExclusiveLock);
 
    heap_freetuple(newtuple);
@@ -8296,6 +8347,8 @@ ATExecChangeOwner(Oid relationOid, Oid newOwnerId, bool recursing, LOCKMODE lock
        }
    }
 
+   InvokeObjectPostAlterHook(RelationRelationId, relationOid, 0);
+
    ReleaseSysCache(tuple);
    heap_close(class_rel, RowExclusiveLock);
    relation_close(target_rel, NoLock);
@@ -8457,7 +8510,7 @@ ATExecClusterOn(Relation rel, const char *indexName, LOCKMODE lockmode)
    check_index_is_clusterable(rel, indexOid, false, lockmode);
 
    /* And do the work */
-   mark_index_clustered(rel, indexOid);
+   mark_index_clustered(rel, indexOid, false);
 }
 
 /*
@@ -8469,7 +8522,7 @@ ATExecClusterOn(Relation rel, const char *indexName, LOCKMODE lockmode)
 static void
 ATExecDropCluster(Relation rel, LOCKMODE lockmode)
 {
-   mark_index_clustered(rel, InvalidOid);
+   mark_index_clustered(rel, InvalidOid, false);
 }
 
 /*
@@ -8590,6 +8643,8 @@ ATExecSetRelOptions(Relation rel, List *defList, AlterTableType operation,
 
    CatalogUpdateIndexes(pgclass, newtuple);
 
+   InvokeObjectPostAlterHook(RelationRelationId, RelationGetRelid(rel), 0);
+
    heap_freetuple(newtuple);
 
    ReleaseSysCache(tuple);
@@ -8647,6 +8702,10 @@ ATExecSetRelOptions(Relation rel, List *defList, AlterTableType operation,
 
        CatalogUpdateIndexes(pgclass, newtuple);
 
+       InvokeObjectPostAlterHookArg(RelationRelationId,
+                                    RelationGetRelid(toastrel), 0,
+                                    InvalidOid, true);
+
        heap_freetuple(newtuple);
 
        ReleaseSysCache(tuple);
@@ -8688,6 +8747,9 @@ ATExecSetTableSpace(Oid tableOid, Oid newTableSpace, LOCKMODE lockmode)
    if (newTableSpace == oldTableSpace ||
        (newTableSpace == MyDatabaseTableSpace && oldTableSpace == 0))
    {
+       InvokeObjectPostAlterHook(RelationRelationId,
+                                 RelationGetRelid(rel), 0);
+
        relation_close(rel, NoLock);
        return;
    }
@@ -8785,6 +8847,8 @@ ATExecSetTableSpace(Oid tableOid, Oid newTableSpace, LOCKMODE lockmode)
    simple_heap_update(pg_class, &tuple->t_self, tuple);
    CatalogUpdateIndexes(pg_class, tuple);
 
+   InvokeObjectPostAlterHook(RelationRelationId, RelationGetRelid(rel), 0);
+
    heap_freetuple(tuple);
 
    heap_close(pg_class, RowExclusiveLock);
@@ -9487,6 +9551,15 @@ ATExecDropInherit(Relation rel, RangeVar *parent, LOCKMODE lockmode)
                           RelationRelationId,
                           RelationGetRelid(parent_rel));
 
+   /*
+    * Post alter hook of this inherits. Since object_access_hook doesn't
+    * take multiple object identifiers, we relay oid of parent relation
+    * using auxiliary_id argument.
+    */
+   InvokeObjectPostAlterHookArg(InheritsRelationId,
+                                RelationGetRelid(rel), 0,
+                                RelationGetRelid(parent_rel), false);
+
    /* keep our lock on the parent relation until commit */
    heap_close(parent_rel, NoLock);
 }
@@ -9669,6 +9742,9 @@ ATExecAddOf(Relation rel, const TypeName *ofTypename, LOCKMODE lockmode)
    ((Form_pg_class) GETSTRUCT(classtuple))->reloftype = typeid;
    simple_heap_update(relationRelation, &classtuple->t_self, classtuple);
    CatalogUpdateIndexes(relationRelation, classtuple);
+
+   InvokeObjectPostAlterHook(RelationRelationId, relid, 0);
+
    heap_freetuple(classtuple);
    heap_close(relationRelation, RowExclusiveLock);
 
@@ -9709,6 +9785,9 @@ ATExecDropOf(Relation rel, LOCKMODE lockmode)
    ((Form_pg_class) GETSTRUCT(tuple))->reloftype = InvalidOid;
    simple_heap_update(relationRelation, &tuple->t_self, tuple);
    CatalogUpdateIndexes(relationRelation, tuple);
+
+   InvokeObjectPostAlterHook(RelationRelationId, relid, 0);
+
    heap_freetuple(tuple);
    heap_close(relationRelation, RowExclusiveLock);
 }
@@ -9778,6 +9857,9 @@ ATExecGenericOptions(Relation rel, List *options)
    simple_heap_update(ftrel, &tuple->t_self, tuple);
    CatalogUpdateIndexes(ftrel, tuple);
 
+   InvokeObjectPostAlterHook(ForeignTableRelationId,
+                             RelationGetRelid(rel), 0);
+
    heap_close(ftrel, RowExclusiveLock);
 
    heap_freetuple(tuple);
@@ -9935,6 +10017,8 @@ AlterRelationNamespaceInternal(Relation classRel, Oid relOid,
                 NameStr(classForm->relname));
 
        add_exact_object_address(&thisobj, objsMoved);
+
+       InvokeObjectPostAlterHook(RelationRelationId, relOid, 0);
    }
 
    heap_freetuple(classTup);
index dfcc829b85fb04d33b957450fed4c1ab1ac127bf..8589512998a2218f8a8cca6af8e26da975018836 100644 (file)
@@ -877,6 +877,8 @@ RenameTableSpace(const char *oldname, const char *newname)
    simple_heap_update(rel, &newtuple->t_self, newtuple);
    CatalogUpdateIndexes(rel, newtuple);
 
+   InvokeObjectPostAlterHook(TableSpaceRelationId, tspId, 0);
+
    heap_close(rel, NoLock);
 
    return tspId;
@@ -945,6 +947,9 @@ AlterTableSpaceOptions(AlterTableSpaceOptionsStmt *stmt)
    /* Update system catalog. */
    simple_heap_update(rel, &newtuple->t_self, newtuple);
    CatalogUpdateIndexes(rel, newtuple);
+
+   InvokeObjectPostAlterHook(TableSpaceRelationId, HeapTupleGetOid(tup), 0);
+
    heap_freetuple(newtuple);
 
    /* Conclude heap scan. */
index f79cef508c13987c32a3133d87e5c9f750648904..bebb551f7fa75dbef370925472467713eae3faca 100644 (file)
@@ -446,7 +446,8 @@ CreateTrigger(CreateTrigStmt *stmt, const char *queryString,
                                              NULL,
                                              true,     /* islocal */
                                              0,        /* inhcount */
-                                             true);    /* isnoinherit */
+                                             true,     /* isnoinherit */
+                                             isInternal);  /* is_internal */
    }
 
    /*
@@ -742,7 +743,8 @@ CreateTrigger(CreateTrigStmt *stmt, const char *queryString,
                               DEPENDENCY_NORMAL);
 
    /* Post creation hook for new trigger */
-   InvokeObjectPostCreateHook(TriggerRelationId, trigoid, 0);
+   InvokeObjectPostCreateHookArg(TriggerRelationId, trigoid, 0,
+                                 isInternal);
 
    /* Keep lock on target rel until end of xact */
    heap_close(rel, NoLock);
@@ -1276,6 +1278,9 @@ renametrig(RenameStmt *stmt)
        /* keep system catalog indexes current */
        CatalogUpdateIndexes(tgrel, tuple);
 
+       InvokeObjectPostAlterHook(TriggerRelationId,
+                                 HeapTupleGetOid(tuple), 0);
+
        /*
         * Invalidate relation's relcache entry so that other backends (and
         * this one too!) are sent SI message to make them rebuild relcache
@@ -1391,6 +1396,9 @@ EnableDisableTrigger(Relation rel, const char *tgname,
 
            changed = true;
        }
+
+       InvokeObjectPostAlterHook(TriggerRelationId,
+                                 HeapTupleGetOid(tuple), 0);
    }
 
    systable_endscan(tgscan);
index 821fdc6b31e60f918fe333b93f0a672663404e22..57b69f88ab09dcd499627d040df4258183edf40b 100644 (file)
@@ -612,6 +612,8 @@ AlterTSDictionary(AlterTSDictionaryStmt *stmt)
 
    CatalogUpdateIndexes(rel, newtup);
 
+   InvokeObjectPostAlterHook(TSDictionaryRelationId, dictId, 0);
+
    /*
     * NOTE: because we only support altering the options, not the template,
     * there is no need to update dependencies.  This might have to change if
@@ -1184,6 +1186,9 @@ AlterTSConfiguration(AlterTSConfigurationStmt *stmt)
    /* Update dependencies */
    makeConfigurationDependencies(tup, true, relMap);
 
+   InvokeObjectPostAlterHook(TSConfigMapRelationId,
+                             HeapTupleGetOid(tup), 0);
+
    heap_close(relMap, RowExclusiveLock);
 
    ReleaseSysCache(tup);
index 1ba6d5e6e99c0132ed2d220800b67819e2848fd6..2c4c6cbced17f8ca2251bc17ff15798de51f7a6f 100644 (file)
@@ -39,6 +39,7 @@
 #include "catalog/dependency.h"
 #include "catalog/heap.h"
 #include "catalog/indexing.h"
+#include "catalog/objectaccess.h"
 #include "catalog/pg_authid.h"
 #include "catalog/pg_collation.h"
 #include "catalog/pg_constraint.h"
@@ -1214,6 +1215,8 @@ AlterEnum(AlterEnumStmt *stmt, bool isTopLevel)
                 stmt->newValNeighbor, stmt->newValIsAfter,
                 stmt->skipIfExists);
 
+   InvokeObjectPostAlterHook(TypeRelationId, enum_type_oid, 0);
+
    ReleaseSysCache(tup);
 
    return enum_type_oid;
@@ -2190,6 +2193,8 @@ AlterDomainDefault(List *names, Node *defaultRaw)
                             defaultExpr,
                             true);     /* Rebuild is true */
 
+   InvokeObjectPostAlterHook(TypeRelationId, domainoid, 0);
+
    /* Clean up */
    heap_close(rel, NoLock);
    heap_freetuple(newtuple);
@@ -2299,6 +2304,8 @@ AlterDomainNotNull(List *names, bool notNull)
 
    CatalogUpdateIndexes(typrel, tup);
 
+   InvokeObjectPostAlterHook(TypeRelationId, domainoid, 0);
+
    /* Clean up */
    heap_freetuple(tup);
    heap_close(typrel, RowExclusiveLock);
@@ -2586,6 +2593,10 @@ AlterDomainValidateConstraint(List *names, char *constrName)
    copy_con->convalidated = true;
    simple_heap_update(conrel, ©Tuple->t_self, copyTuple);
    CatalogUpdateIndexes(conrel, copyTuple);
+
+   InvokeObjectPostAlterHook(ConstraintRelationId,
+                             HeapTupleGetOid(copyTuple), 0);
+
    heap_freetuple(copyTuple);
 
    systable_endscan(scan);
@@ -2993,7 +3004,8 @@ domainAddConstraint(Oid domainOid, Oid domainNamespace, Oid baseTypeOid,
                          ccsrc,    /* Source form of check constraint */
                          true, /* is local */
                          0,    /* inhcount */
-                         false);       /* connoinherit */
+                         false,    /* connoinherit */
+                         false);   /* is_internal */
 
    /*
     * Return the compiled constraint expression so the calling routine can
@@ -3188,7 +3200,7 @@ RenameType(RenameStmt *stmt)
     * RenameRelationInternal will call RenameTypeInternal automatically.
     */
    if (typTup->typtype == TYPTYPE_COMPOSITE)
-       RenameRelationInternal(typTup->typrelid, newTypeName);
+       RenameRelationInternal(typTup->typrelid, newTypeName, false);
    else
        RenameTypeInternal(typeOid, newTypeName,
                           typTup->typnamespace);
@@ -3311,6 +3323,8 @@ AlterTypeOwner(List *names, Oid newOwnerId, ObjectType objecttype)
            /* Update owner dependency reference */
            changeDependencyOnOwner(TypeRelationId, typeOid, newOwnerId);
 
+           InvokeObjectPostAlterHook(TypeRelationId, typeOid, 0);
+
            /* If it has an array type, update that too */
            if (OidIsValid(typTup->typarray))
                AlterTypeOwnerInternal(typTup->typarray, newOwnerId, false);
@@ -3333,6 +3347,8 @@ AlterTypeOwner(List *names, Oid newOwnerId, ObjectType objecttype)
  *
  * hasDependEntry should be TRUE if type is expected to have a pg_shdepend
  * entry (ie, it's not a table rowtype nor an array type).
+ * is_primary_ops should be TRUE if this function is invoked with user's
+ * direct operation (e.g, shdepReassignOwned). Elsewhere, 
  */
 void
 AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId,
@@ -3366,6 +3382,8 @@ AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId,
    if (OidIsValid(typTup->typarray))
        AlterTypeOwnerInternal(typTup->typarray, newOwnerId, false);
 
+   InvokeObjectPostAlterHook(TypeRelationId, typeOid, 0);
+
    /* Clean up */
    heap_close(rel, RowExclusiveLock);
 }
@@ -3553,6 +3571,8 @@ AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid,
            elog(ERROR, "failed to change schema dependency for type %s",
                 format_type_be(typeOid));
 
+   InvokeObjectPostAlterHook(TypeRelationId, typeOid, 0);
+
    heap_freetuple(tup);
 
    heap_close(rel, RowExclusiveLock);
index 9302416375583ac62d41651f4f150ff85376b64e..c7886ed799e6bc7be60886f15bd9984073a0d0e2 100644 (file)
@@ -777,6 +777,8 @@ AlterRole(AlterRoleStmt *stmt)
    /* Update indexes */
    CatalogUpdateIndexes(pg_authid_rel, new_tuple);
 
+   InvokeObjectPostAlterHook(AuthIdRelationId, roleid, 0);
+
    ReleaseSysCache(tuple);
    heap_freetuple(new_tuple);
 
@@ -1161,6 +1163,8 @@ RenameRole(const char *oldname, const char *newname)
 
    CatalogUpdateIndexes(rel, newtuple);
 
+   InvokeObjectPostAlterHook(AuthIdRelationId, roleid, 0);
+
    ReleaseSysCache(oldtuple);
 
    /*
index ca92fb56417cb44c9f8add3e37bfcf9cd8e57ae8..cb59f139e143097acdf8fae5076a4bf4232e7e83 100644 (file)
@@ -815,6 +815,9 @@ EnableDisableRule(Relation rel, const char *rulename,
        changed = true;
    }
 
+   InvokeObjectPostAlterHook(RewriteRelationId,
+                             HeapTupleGetOid(ruletup), 0);
+
    heap_freetuple(ruletup);
    heap_close(pg_rewrite_desc, RowExclusiveLock);
 
index 989089a25afe80d7e8d4d91eb6b7dea9774d8198..97d507e4c2321fbd3c35fd6a2ff58fadc99f33df 100644 (file)
@@ -96,9 +96,11 @@ extern List *AddRelationNewConstraints(Relation rel,
                          List *newColDefaults,
                          List *newConstraints,
                          bool allow_merge,
-                         bool is_local);
+                         bool is_local,
+                         bool is_internal);
 
-extern void StoreAttrDefault(Relation rel, AttrNumber attnum, Node *expr);
+extern void StoreAttrDefault(Relation rel, AttrNumber attnum,
+                            Node *expr, bool is_internal);
 
 extern Node *cookDefault(ParseState *pstate,
            Node *raw_default,
index fb323f7201112d553c32be11b54486b7982fee7c..e6972752448351c10b2315d5d236a9cfd3e1b124 100644 (file)
@@ -72,7 +72,8 @@ extern void index_constraint_create(Relation heapRelation,
                        bool mark_as_primary,
                        bool update_pgindex,
                        bool remove_old_dependencies,
-                       bool allow_system_table_mods);
+                       bool allow_system_table_mods,
+                       bool is_internal);
 
 extern void index_drop(Oid indexId, bool concurrent);
 
index b9bb1bcd2f5efa2ebd291bbcfd1b9bca69d2254a..25f963b0748f13f661b3ae3154529cca2a36ae68 100644 (file)
  * OAT_DROP should be invoked just before deletion of objects; typically
  * deleteOneObject(). Its arguments are packed within ObjectAccessDrop.
  *
+ * OAT_POST_ALTER should be invoked just after the object is altered,
+ * but before the command counter is incremented.  An extension using the
+ * hook can use SnapshotNow and SnapshotSelf to get the old and new
+ * versions of the tuple.
+ *
  * Other types may be added in the future.
  */
 typedef enum ObjectAccessType
@@ -57,20 +62,51 @@ typedef struct
 } ObjectAccessDrop;
 
 /*
- * Hook, and a macro to invoke it.
+ * Arguments of OAT_POST_ALTER event
  */
+typedef struct
+{
+   /*
+    * This identifier is used when system catalog takes two IDs
+    * to identify a particular tuple of the catalog.
+    * It is only used when the caller want to identify an entry
+    * of pg_inherits, pg_db_role_setting or pg_user_mapping.
+    * Elsewhere, InvalidOid should be set.
+    */
+   Oid         auxiliary_id;
+
+   /*
+    * If this flag is set, the user hasn't requested that the object be
+    * altered, but we're doing it anyway for some internal reason.
+    * Permissions-checking hooks may want to skip checks if, say, we're
+    * alter the constraints of a temporary heap during CLUSTER.
+    */
+   bool        is_internal;
+} ObjectAccessPostAlter;
+
+/* Plugin provides a hook function matching this signature. */
 typedef void (*object_access_hook_type) (ObjectAccessType access,
                                                     Oid classId,
                                                     Oid objectId,
                                                     int subId,
                                                     void *arg);
 
+/* Plugin sets this variable to a suitable hook function. */
 extern PGDLLIMPORT object_access_hook_type object_access_hook;
 
+/* Core code uses these functions to call the hook (see macros below). */
 extern void RunObjectPostCreateHook(Oid classId, Oid objectId, int subId,
                                    bool is_internal);
 extern void RunObjectDropHook(Oid classId, Oid objectId, int subId,
                              int dropflags);
+extern void RunObjectPostAlterHook(Oid classId, Oid objectId, int subId,
+                                  Oid auxiliaryId, bool is_internal);
+
+/*
+ * The following macros are wrappers around the functions above; these should
+ * normally be used to invoke the hook in lieu of calling the above functions
+ * directly.
+ */
 
 #define InvokeObjectPostCreateHook(classId,objectId,subId)         \
    InvokeObjectPostCreateHookArg((classId),(objectId),(subId),false)
@@ -90,4 +126,15 @@ extern void RunObjectDropHook(Oid classId, Oid objectId, int subId,
                              (dropflags));                         \
    } while(0)
 
+#define InvokeObjectPostAlterHook(classId,objectId,subId)          \
+   InvokeObjectPostAlterHookArg((classId),(objectId),(subId),      \
+                                InvalidOid,false)
+#define InvokeObjectPostAlterHookArg(classId,objectId,subId,       \
+                                    auxiliaryId,is_internal)       \
+   do {                                                            \
+       if (object_access_hook)                                     \
+           RunObjectPostAlterHook((classId),(objectId),(subId),    \
+                                  (auxiliaryId),(is_internal));    \
+   } while(0)
+
 #endif   /* OBJECTACCESS_H */
index 29f71f1be5d7e51e9554bb55e3015e1ef0a3810c..4a6a18f0e7ace857b9b88243c90895ef866a6fd4 100644 (file)
@@ -232,7 +232,8 @@ extern Oid CreateConstraintEntry(const char *constraintName,
                      const char *conSrc,
                      bool conIsLocal,
                      int conInhCount,
-                     bool conNoInherit);
+                     bool conNoInherit,
+                     bool is_internal);
 
 extern void RemoveConstraintById(Oid conId);
 extern void RenameConstraintById(Oid conId, const char *newname);
index 73c701fe53eed0b47346eacf82d1eefd05b868e8..aa6d332e9d2e7e2b90fd4fd0e9c840c6f80a446d 100644 (file)
@@ -23,13 +23,14 @@ extern void cluster_rel(Oid tableOid, Oid indexOid, bool recheck,
            bool verbose, int freeze_min_age, int freeze_table_age);
 extern void check_index_is_clusterable(Relation OldHeap, Oid indexOid,
                           bool recheck, LOCKMODE lockmode);
-extern void mark_index_clustered(Relation rel, Oid indexOid);
+extern void mark_index_clustered(Relation rel, Oid indexOid, bool is_internal);
 
 extern Oid make_new_heap(Oid OIDOldHeap, Oid NewTableSpace);
 extern void finish_heap_swap(Oid OIDOldHeap, Oid OIDNewHeap,
                 bool is_system_catalog,
                 bool swap_toast_by_content,
                 bool check_constraints,
+                bool is_internal,
                 TransactionId frozenXid,
                 MultiXactId frozenMulti);
 
index 031c77c9efd0278767ba610874e99a46031235e3..7b86c444f66a46294ad344cc3df6c4d3b4cbabba 100644 (file)
@@ -58,7 +58,7 @@ extern Oid RenameConstraint(RenameStmt *stmt);
 extern Oid RenameRelation(RenameStmt *stmt);
 
 extern void RenameRelationInternal(Oid myrelid,
-                      const char *newrelname);
+                      const char *newrelname, bool is_internal);
 
 extern void find_composite_type_dependencies(Oid typeOid,
                                 Relation origRelation,