Don't repeatedly register cache callbacks in pgoutput plugin.
[pgsql.git] / src / include / commands / trigger.h
blob33002ef472daa1872ac5cd669d377f77f999bd28
1 /*-------------------------------------------------------------------------
3 * trigger.h
4 * Declarations for trigger handling.
6 * Portions Copyright (c) 1996-2019, PostgreSQL Global Development Group
7 * Portions Copyright (c) 1994, Regents of the University of California
9 * src/include/commands/trigger.h
11 *-------------------------------------------------------------------------
13 #ifndef TRIGGER_H
14 #define TRIGGER_H
16 #include "catalog/objectaddress.h"
17 #include "nodes/execnodes.h"
18 #include "nodes/parsenodes.h"
21 * TriggerData is the node type that is passed as fmgr "context" info
22 * when a function is called by the trigger manager.
25 #define CALLED_AS_TRIGGER(fcinfo) \
26 ((fcinfo)->context != NULL && IsA((fcinfo)->context, TriggerData))
28 typedef uint32 TriggerEvent;
30 typedef struct TriggerData
32 NodeTag type;
33 TriggerEvent tg_event;
34 Relation tg_relation;
35 HeapTuple tg_trigtuple;
36 HeapTuple tg_newtuple;
37 Trigger *tg_trigger;
38 TupleTableSlot *tg_trigslot;
39 TupleTableSlot *tg_newslot;
40 Tuplestorestate *tg_oldtable;
41 Tuplestorestate *tg_newtable;
42 } TriggerData;
45 * The state for capturing old and new tuples into transition tables for a
46 * single ModifyTable node (or other operation source, e.g. copy.c).
48 * This is per-caller to avoid conflicts in setting tcs_map or
49 * tcs_original_insert_tuple. Note, however, that the pointed-to
50 * private data may be shared across multiple callers.
52 struct AfterTriggersTableData; /* private in trigger.c */
54 typedef struct TransitionCaptureState
57 * Is there at least one trigger specifying each transition relation on
58 * the relation explicitly named in the DML statement or COPY command?
59 * Note: in current usage, these flags could be part of the private state,
60 * but it seems possibly useful to let callers see them.
62 bool tcs_delete_old_table;
63 bool tcs_update_old_table;
64 bool tcs_update_new_table;
65 bool tcs_insert_new_table;
68 * For UPDATE and DELETE, AfterTriggerSaveEvent may need to convert the
69 * new and old tuples from a child table's format to the format of the
70 * relation named in a query so that it is compatible with the transition
71 * tuplestores. The caller must store the conversion map here if so.
73 TupleConversionMap *tcs_map;
76 * For INSERT and COPY, it would be wasteful to convert tuples from child
77 * format to parent format after they have already been converted in the
78 * opposite direction during routing. In that case we bypass conversion
79 * and allow the inserting code (copy.c and nodeModifyTable.c) to provide
80 * a slot containing the original tuple directly.
82 TupleTableSlot *tcs_original_insert_tuple;
85 * Private data including the tuplestore(s) into which to insert tuples.
87 struct AfterTriggersTableData *tcs_private;
88 } TransitionCaptureState;
91 * TriggerEvent bit flags
93 * Note that we assume different event types (INSERT/DELETE/UPDATE/TRUNCATE)
94 * can't be OR'd together in a single TriggerEvent. This is unlike the
95 * situation for pg_trigger rows, so pg_trigger.tgtype uses a different
96 * representation!
98 #define TRIGGER_EVENT_INSERT 0x00000000
99 #define TRIGGER_EVENT_DELETE 0x00000001
100 #define TRIGGER_EVENT_UPDATE 0x00000002
101 #define TRIGGER_EVENT_TRUNCATE 0x00000003
102 #define TRIGGER_EVENT_OPMASK 0x00000003
104 #define TRIGGER_EVENT_ROW 0x00000004
106 #define TRIGGER_EVENT_BEFORE 0x00000008
107 #define TRIGGER_EVENT_AFTER 0x00000000
108 #define TRIGGER_EVENT_INSTEAD 0x00000010
109 #define TRIGGER_EVENT_TIMINGMASK 0x00000018
111 /* More TriggerEvent flags, used only within trigger.c */
113 #define AFTER_TRIGGER_DEFERRABLE 0x00000020
114 #define AFTER_TRIGGER_INITDEFERRED 0x00000040
116 #define TRIGGER_FIRED_BY_INSERT(event) \
117 (((event) & TRIGGER_EVENT_OPMASK) == TRIGGER_EVENT_INSERT)
119 #define TRIGGER_FIRED_BY_DELETE(event) \
120 (((event) & TRIGGER_EVENT_OPMASK) == TRIGGER_EVENT_DELETE)
122 #define TRIGGER_FIRED_BY_UPDATE(event) \
123 (((event) & TRIGGER_EVENT_OPMASK) == TRIGGER_EVENT_UPDATE)
125 #define TRIGGER_FIRED_BY_TRUNCATE(event) \
126 (((event) & TRIGGER_EVENT_OPMASK) == TRIGGER_EVENT_TRUNCATE)
128 #define TRIGGER_FIRED_FOR_ROW(event) \
129 ((event) & TRIGGER_EVENT_ROW)
131 #define TRIGGER_FIRED_FOR_STATEMENT(event) \
132 (!TRIGGER_FIRED_FOR_ROW(event))
134 #define TRIGGER_FIRED_BEFORE(event) \
135 (((event) & TRIGGER_EVENT_TIMINGMASK) == TRIGGER_EVENT_BEFORE)
137 #define TRIGGER_FIRED_AFTER(event) \
138 (((event) & TRIGGER_EVENT_TIMINGMASK) == TRIGGER_EVENT_AFTER)
140 #define TRIGGER_FIRED_INSTEAD(event) \
141 (((event) & TRIGGER_EVENT_TIMINGMASK) == TRIGGER_EVENT_INSTEAD)
144 * Definitions for replication role based firing.
146 #define SESSION_REPLICATION_ROLE_ORIGIN 0
147 #define SESSION_REPLICATION_ROLE_REPLICA 1
148 #define SESSION_REPLICATION_ROLE_LOCAL 2
149 extern PGDLLIMPORT int SessionReplicationRole;
152 * States at which a trigger can be fired. These are the
153 * possible values for pg_trigger.tgenabled.
155 #define TRIGGER_FIRES_ON_ORIGIN 'O'
156 #define TRIGGER_FIRES_ALWAYS 'A'
157 #define TRIGGER_FIRES_ON_REPLICA 'R'
158 #define TRIGGER_DISABLED 'D'
160 extern ObjectAddress CreateTrigger(CreateTrigStmt *stmt, const char *queryString,
161 Oid relOid, Oid refRelOid, Oid constraintOid, Oid indexOid,
162 Oid funcoid, Oid parentTriggerOid, Node *whenClause,
163 bool isInternal, bool in_partition);
164 extern ObjectAddress CreateTriggerFiringOn(CreateTrigStmt *stmt, const char *queryString,
165 Oid relOid, Oid refRelOid, Oid constraintOid,
166 Oid indexOid, Oid funcoid, Oid parentTriggerOid,
167 Node *whenClause, bool isInternal, bool in_partition,
168 char trigger_fires_when);
170 extern void RemoveTriggerById(Oid trigOid);
171 extern Oid get_trigger_oid(Oid relid, const char *name, bool missing_ok);
173 extern ObjectAddress renametrig(RenameStmt *stmt);
175 extern void EnableDisableTriggerNew(Relation rel, const char *tgname,
176 char fires_when, bool skip_system, bool recurse,
177 LOCKMODE lockmode);
178 extern void EnableDisableTrigger(Relation rel, const char *tgname,
179 char fires_when, bool skip_system, LOCKMODE lockmode);
181 extern void RelationBuildTriggers(Relation relation);
183 extern TriggerDesc *CopyTriggerDesc(TriggerDesc *trigdesc);
185 extern const char *FindTriggerIncompatibleWithInheritance(TriggerDesc *trigdesc);
187 extern TransitionCaptureState *MakeTransitionCaptureState(TriggerDesc *trigdesc,
188 Oid relid, CmdType cmdType);
190 extern void FreeTriggerDesc(TriggerDesc *trigdesc);
192 extern void ExecBSInsertTriggers(EState *estate,
193 ResultRelInfo *relinfo);
194 extern void ExecASInsertTriggers(EState *estate,
195 ResultRelInfo *relinfo,
196 TransitionCaptureState *transition_capture);
197 extern bool ExecBRInsertTriggers(EState *estate,
198 ResultRelInfo *relinfo,
199 TupleTableSlot *slot);
200 extern void ExecARInsertTriggers(EState *estate,
201 ResultRelInfo *relinfo,
202 TupleTableSlot *slot,
203 List *recheckIndexes,
204 TransitionCaptureState *transition_capture);
205 extern bool ExecIRInsertTriggers(EState *estate,
206 ResultRelInfo *relinfo,
207 TupleTableSlot *slot);
208 extern void ExecBSDeleteTriggers(EState *estate,
209 ResultRelInfo *relinfo);
210 extern void ExecASDeleteTriggers(EState *estate,
211 ResultRelInfo *relinfo,
212 TransitionCaptureState *transition_capture);
213 extern bool ExecBRDeleteTriggers(EState *estate,
214 EPQState *epqstate,
215 ResultRelInfo *relinfo,
216 ItemPointer tupleid,
217 HeapTuple fdw_trigtuple,
218 TupleTableSlot **epqslot);
219 extern void ExecARDeleteTriggers(EState *estate,
220 ResultRelInfo *relinfo,
221 ItemPointer tupleid,
222 HeapTuple fdw_trigtuple,
223 TransitionCaptureState *transition_capture);
224 extern bool ExecIRDeleteTriggers(EState *estate,
225 ResultRelInfo *relinfo,
226 HeapTuple trigtuple);
227 extern void ExecBSUpdateTriggers(EState *estate,
228 ResultRelInfo *relinfo);
229 extern void ExecASUpdateTriggers(EState *estate,
230 ResultRelInfo *relinfo,
231 TransitionCaptureState *transition_capture);
232 extern bool ExecBRUpdateTriggers(EState *estate,
233 EPQState *epqstate,
234 ResultRelInfo *relinfo,
235 ItemPointer tupleid,
236 HeapTuple fdw_trigtuple,
237 TupleTableSlot *slot);
238 extern void ExecARUpdateTriggers(EState *estate,
239 ResultRelInfo *relinfo,
240 ItemPointer tupleid,
241 HeapTuple fdw_trigtuple,
242 TupleTableSlot *slot,
243 List *recheckIndexes,
244 TransitionCaptureState *transition_capture);
245 extern bool ExecIRUpdateTriggers(EState *estate,
246 ResultRelInfo *relinfo,
247 HeapTuple trigtuple,
248 TupleTableSlot *slot);
249 extern void ExecBSTruncateTriggers(EState *estate,
250 ResultRelInfo *relinfo);
251 extern void ExecASTruncateTriggers(EState *estate,
252 ResultRelInfo *relinfo);
254 extern void AfterTriggerBeginXact(void);
255 extern void AfterTriggerBeginQuery(void);
256 extern void AfterTriggerEndQuery(EState *estate);
257 extern void AfterTriggerFireDeferred(void);
258 extern void AfterTriggerEndXact(bool isCommit);
259 extern void AfterTriggerBeginSubXact(void);
260 extern void AfterTriggerEndSubXact(bool isCommit);
261 extern void AfterTriggerSetState(ConstraintsSetStmt *stmt);
262 extern bool AfterTriggerPendingOnRel(Oid relid);
266 * in utils/adt/ri_triggers.c
268 extern bool RI_FKey_pk_upd_check_required(Trigger *trigger, Relation pk_rel,
269 TupleTableSlot *old_slot, TupleTableSlot *new_slot);
270 extern bool RI_FKey_fk_upd_check_required(Trigger *trigger, Relation fk_rel,
271 TupleTableSlot *old_slot, TupleTableSlot *new_slot);
272 extern bool RI_Initial_Check(Trigger *trigger,
273 Relation fk_rel, Relation pk_rel);
274 extern void RI_PartitionRemove_Check(Trigger *trigger, Relation fk_rel,
275 Relation pk_rel);
277 /* result values for RI_FKey_trigger_type: */
278 #define RI_TRIGGER_PK 1 /* is a trigger on the PK relation */
279 #define RI_TRIGGER_FK 2 /* is a trigger on the FK relation */
280 #define RI_TRIGGER_NONE 0 /* is not an RI trigger function */
282 extern int RI_FKey_trigger_type(Oid tgfoid);
284 #endif /* TRIGGER_H */