23#include "catalog/pg_am_d.h"
94 Anum_pg_index_indclass);
105 int table_attno = indkey->
values[index_attoff];
125 elog(
ERROR,
"missing equal strategy for opclass %u", opclass->
values[index_attoff]);
132 elog(
ERROR,
"missing operator %d(%u,%u) in opfamily %u",
133 eq_strategy, optype, optype, opfamily);
168 bool refetch =
false;
179 errmsg(
"tuple to be locked was already moved to another partition due to concurrent update, retrying")));
183 errmsg(
"concurrent update, retrying")));
190 errmsg(
"concurrent delete, retrying")));
194 elog(
ERROR,
"attempted to lock invisible tuple");
197 elog(
ERROR,
"unexpected table_tuple_lock status: %u",
res);
224 bool isIdxSafeToSkipDuplicates;
251 if (!isIdxSafeToSkipDuplicates)
337 if (att->attisdropped || att->attgenerated)
353 typentry = eq[attrnum];
354 if (typentry == NULL)
360 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
361 errmsg(
"could not identify an equality operator for type %s",
363 eq[attrnum] = typentry;
485 *conflictslot = NULL;
495 *conflictslot = NULL;
543 searchslot, conflictslot, remoteslot,
544 uniqueidx, xmin, origin, committs);
559 bool skip_tuple =
false;
578 List *conflictindexes;
579 bool conflict =
false;
590 if (rel->
rd_rel->relispartition)
601 conflictindexes ?
true :
false,
603 conflictindexes,
false);
622 recheckIndexes, NULL, slot);
626 recheckIndexes, NULL);
649 bool skip_tuple =
false;
667 tid, NULL, slot, NULL, NULL))
675 List *conflictindexes;
676 bool conflict =
false;
687 if (rel->
rd_rel->relispartition)
698 conflictindexes ?
true :
false,
699 &conflict, conflictindexes,
709 recheckIndexes, searchslot, slot);
715 recheckIndexes, NULL,
false);
732 bool skip_tuple =
false;
743 tid, NULL, NULL, NULL, NULL);
753 tid, NULL, NULL,
false);
769 if (rel->
rd_rel->relkind == RELKIND_PARTITIONED_TABLE)
802 (
errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
803 errmsg(
"cannot update table \"%s\"",
805 errdetail(
"Column used in the publication WHERE expression is not part of the replica identity.")));
808 (
errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
809 errmsg(
"cannot update table \"%s\"",
811 errdetail(
"Column list used by the publication does not cover the replica identity.")));
814 (
errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
815 errmsg(
"cannot update table \"%s\"",
817 errdetail(
"Replica identity must not contain unpublished generated columns.")));
820 (
errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
821 errmsg(
"cannot delete from table \"%s\"",
823 errdetail(
"Column used in the publication WHERE expression is not part of the replica identity.")));
826 (
errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
827 errmsg(
"cannot delete from table \"%s\"",
829 errdetail(
"Column list used by the publication does not cover the replica identity.")));
832 (
errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
833 errmsg(
"cannot delete from table \"%s\"",
835 errdetail(
"Replica identity must not contain unpublished generated columns.")));
842 if (rel->
rd_rel->relreplident == REPLICA_IDENTITY_FULL)
852 (
errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
853 errmsg(
"cannot update table \"%s\" because it does not have a replica identity and publishes updates",
855 errhint(
"To enable updating the table, set REPLICA IDENTITY using ALTER TABLE.")));
858 (
errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
859 errmsg(
"cannot delete from table \"%s\" because it does not have a replica identity and publishes deletes",
861 errhint(
"To enable deleting from the table, set REPLICA IDENTITY using ALTER TABLE.")));
874 if (relkind != RELKIND_RELATION && relkind != RELKIND_PARTITIONED_TABLE)
876 (
errcode(ERRCODE_WRONG_OBJECT_TYPE),
877 errmsg(
"cannot use relation \"%s.%s\" as logical replication target",
#define AttributeNumberIsValid(attributeNumber)
#define PG_USED_FOR_ASSERTS_ONLY
#define Assert(condition)
#define OidIsValid(objectId)
bool IsCatalogRelation(Relation relation)
void ReportApplyConflict(EState *estate, ResultRelInfo *relinfo, int elevel, ConflictType type, TupleTableSlot *searchslot, TupleTableSlot *localslot, TupleTableSlot *remoteslot, Oid indexoid, TransactionId localxmin, RepOriginId localorigin, TimestampTz localts)
bool GetTupleTransactionInfo(TupleTableSlot *localslot, TransactionId *xmin, RepOriginId *localorigin, TimestampTz *localts)
static void PGresult * res
int errdetail(const char *fmt,...)
int errhint(const char *fmt,...)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereport(elevel,...)
bool ExecCheckIndexConstraints(ResultRelInfo *resultRelInfo, TupleTableSlot *slot, EState *estate, ItemPointer conflictTid, ItemPointer tupleid, List *arbiterIndexes)
List * ExecInsertIndexTuples(ResultRelInfo *resultRelInfo, TupleTableSlot *slot, EState *estate, bool update, bool noDupErr, bool *specConflict, List *arbiterIndexes, bool onlySummarizing)
bool ExecPartitionCheck(ResultRelInfo *resultRelInfo, TupleTableSlot *slot, EState *estate, bool emitError)
void ExecConstraints(ResultRelInfo *resultRelInfo, TupleTableSlot *slot, EState *estate)
bool RelationFindReplTupleSeq(Relation rel, LockTupleMode lockmode, TupleTableSlot *searchslot, TupleTableSlot *outslot)
bool RelationFindReplTupleByIndex(Relation rel, Oid idxoid, LockTupleMode lockmode, TupleTableSlot *searchslot, TupleTableSlot *outslot)
void ExecSimpleRelationDelete(ResultRelInfo *resultRelInfo, EState *estate, EPQState *epqstate, TupleTableSlot *searchslot)
void CheckSubscriptionRelkind(char relkind, const char *nspname, const char *relname)
static bool tuples_equal(TupleTableSlot *slot1, TupleTableSlot *slot2, TypeCacheEntry **eq)
static bool should_refetch_tuple(TM_Result res, TM_FailureData *tmfd)
void ExecSimpleRelationUpdate(ResultRelInfo *resultRelInfo, EState *estate, EPQState *epqstate, TupleTableSlot *searchslot, TupleTableSlot *slot)
void CheckCmdReplicaIdentity(Relation rel, CmdType cmd)
void ExecSimpleRelationInsert(ResultRelInfo *resultRelInfo, EState *estate, TupleTableSlot *slot)
static bool FindConflictTuple(ResultRelInfo *resultRelInfo, EState *estate, Oid conflictindex, TupleTableSlot *slot, TupleTableSlot **conflictslot)
static int build_replindex_scan_key(ScanKey skey, Relation rel, Relation idxrel, TupleTableSlot *searchslot)
static void CheckAndReportConflict(ResultRelInfo *resultRelInfo, EState *estate, ConflictType type, List *recheckIndexes, TupleTableSlot *searchslot, TupleTableSlot *remoteslot)
StrategyNumber get_equal_strategy_number(Oid opclass)
void ExecDropSingleTupleTableSlot(TupleTableSlot *slot)
Datum FunctionCall2Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2)
StrategyNumber GistTranslateStratnum(Oid opclass, StrategyNumber strat)
bool index_getnext_slot(IndexScanDesc scan, ScanDirection direction, TupleTableSlot *slot)
void index_close(Relation relation, LOCKMODE lockmode)
IndexScanDesc index_beginscan(Relation heapRelation, Relation indexRelation, Snapshot snapshot, int nkeys, int norderbys)
void index_endscan(IndexScanDesc scan)
Relation index_open(Oid relationId, LOCKMODE lockmode)
void index_rescan(IndexScanDesc scan, ScanKey keys, int nkeys, ScanKey orderbys, int norderbys)
static bool ItemPointerIndicatesMovedPartitions(const ItemPointerData *pointer)
void list_free(List *list)
bool list_member_oid(const List *list, Oid datum)
void XactLockTableWait(TransactionId xid, Relation rel, ItemPointer ctid, XLTW_Oper oper)
Oid get_opclass_method(Oid opclass)
Oid get_opclass_input_type(Oid opclass)
Oid get_opclass_family(Oid opclass)
RegProcedure get_opcode(Oid opno)
Oid get_opfamily_member(Oid opfamily, Oid lefttype, Oid righttype, int16 strategy)
void * palloc0(Size size)
void ExecComputeStoredGenerated(ResultRelInfo *resultRelInfo, EState *estate, TupleTableSlot *slot, CmdType cmdtype)
FormData_pg_attribute * Form_pg_attribute
int errdetail_relkind_not_supported(char relkind)
#define list_make1_oid(x1)
#define foreach_oid(var, lst)
#define ERRCODE_T_R_SERIALIZATION_FAILURE
static bool DatumGetBool(Datum X)
static Pointer DatumGetPointer(Datum X)
#define RelationGetDescr(relation)
#define RelationGetRelationName(relation)
#define IndexRelationGetNumberOfKeyAttributes(relation)
void RelationBuildPublicationDesc(Relation relation, PublicationDesc *pubdesc)
Oid RelationGetReplicaIndex(Relation relation)
void ScanKeyInit(ScanKey entry, AttrNumber attributeNumber, StrategyNumber strategy, RegProcedure procedure, Datum argument)
Snapshot GetLatestSnapshot(void)
void PushActiveSnapshot(Snapshot snapshot)
void PopActiveSnapshot(void)
#define InitDirtySnapshot(snapshotdata)
Oid GetRelationIdentityOrPK(Relation rel)
#define RTEqualStrategyNumber
#define HTEqualStrategyNumber
#define BTEqualStrategyNumber
PublicationActions pubactions
bool cols_valid_for_delete
bool gencols_valid_for_update
bool cols_valid_for_update
bool gencols_valid_for_delete
struct HeapTupleData * rd_indextuple
List * ri_onConflictArbiterIndexes
TriggerDesc * ri_TrigDesc
bool trig_delete_before_row
bool trig_update_before_row
bool trig_insert_before_row
bool has_generated_stored
TupleDesc tts_tupleDescriptor
int16 values[FLEXIBLE_ARRAY_MEMBER]
Oid values[FLEXIBLE_ARRAY_MEMBER]
Datum SysCacheGetAttrNotNull(int cacheId, HeapTuple tup, AttrNumber attributeNumber)
TupleTableSlot * table_slot_create(Relation relation, List **reglist)
void simple_table_tuple_update(Relation rel, ItemPointer otid, TupleTableSlot *slot, Snapshot snapshot, TU_UpdateIndexes *update_indexes)
void simple_table_tuple_insert(Relation rel, TupleTableSlot *slot)
void simple_table_tuple_delete(Relation rel, ItemPointer tid, Snapshot snapshot)
static TableScanDesc table_beginscan(Relation rel, Snapshot snapshot, int nkeys, struct ScanKeyData *key)
static void table_endscan(TableScanDesc scan)
static void table_rescan(TableScanDesc scan, struct ScanKeyData *key)
static TM_Result table_tuple_lock(Relation rel, ItemPointer tid, Snapshot snapshot, TupleTableSlot *slot, CommandId cid, LockTupleMode mode, LockWaitPolicy wait_policy, uint8 flags, TM_FailureData *tmfd)
static bool table_scan_getnextslot(TableScanDesc sscan, ScanDirection direction, TupleTableSlot *slot)
#define TransactionIdIsValid(xid)
bool ExecBRUpdateTriggers(EState *estate, EPQState *epqstate, ResultRelInfo *relinfo, ItemPointer tupleid, HeapTuple fdw_trigtuple, TupleTableSlot *newslot, TM_Result *tmresult, TM_FailureData *tmfd)
void ExecARDeleteTriggers(EState *estate, ResultRelInfo *relinfo, ItemPointer tupleid, HeapTuple fdw_trigtuple, TransitionCaptureState *transition_capture, bool is_crosspart_update)
bool ExecBRInsertTriggers(EState *estate, ResultRelInfo *relinfo, TupleTableSlot *slot)
void ExecARUpdateTriggers(EState *estate, ResultRelInfo *relinfo, ResultRelInfo *src_partinfo, ResultRelInfo *dst_partinfo, ItemPointer tupleid, HeapTuple fdw_trigtuple, TupleTableSlot *newslot, List *recheckIndexes, TransitionCaptureState *transition_capture, bool is_crosspart_update)
bool ExecBRDeleteTriggers(EState *estate, EPQState *epqstate, ResultRelInfo *relinfo, ItemPointer tupleid, HeapTuple fdw_trigtuple, TupleTableSlot **epqslot, TM_Result *tmresult, TM_FailureData *tmfd)
void ExecARInsertTriggers(EState *estate, ResultRelInfo *relinfo, TupleTableSlot *slot, List *recheckIndexes, TransitionCaptureState *transition_capture)
bool equalTupleDescs(TupleDesc tupdesc1, TupleDesc tupdesc2)
static FormData_pg_attribute * TupleDescAttr(TupleDesc tupdesc, int i)
static void slot_getallattrs(TupleTableSlot *slot)
static TupleTableSlot * ExecCopySlot(TupleTableSlot *dstslot, TupleTableSlot *srcslot)
static void ExecMaterializeSlot(TupleTableSlot *slot)
TypeCacheEntry * lookup_type_cache(Oid type_id, int flags)
#define TYPECACHE_EQ_OPR_FINFO
CommandId GetCurrentCommandId(bool used)