From 75f7dc455bc97ead5f1be04d242146935331d698 Mon Sep 17 00:00:00 2001 From: Dilip Kumar Date: Sun, 5 Apr 2026 17:02:01 +0530 Subject: [PATCH v26 3/3] Doccumentation patch --- doc/src/sgml/logical-replication.sgml | 109 +++++++++++++++++++++- doc/src/sgml/ref/alter_subscription.sgml | 14 ++- doc/src/sgml/ref/create_subscription.sgml | 47 ++++++++++ 3 files changed, 167 insertions(+), 3 deletions(-) diff --git a/doc/src/sgml/logical-replication.sgml b/doc/src/sgml/logical-replication.sgml index 23b268273b9..b84f0b4993d 100644 --- a/doc/src/sgml/logical-replication.sgml +++ b/doc/src/sgml/logical-replication.sgml @@ -293,6 +293,19 @@ option of CREATE SUBSCRIPTION for details. + + Conflicts that occur during replication are, by default, logged as plain text + in the server log, which can make automated monitoring and analysis difficult. + The CREATE SUBSCRIPTION command provides the + + conflict_log_destination option to record detailed + conflict information in a structured, queryable format. When this parameter + is set to table or all, the system + automatically manages a dedicated conflict log table, which is created and + dropped along with the subscription. This significantly improves post-mortem + analysis and operational visibility of the replication setup. + + Logical Replication Slot Management @@ -2122,7 +2135,94 @@ Publications: - The log format for logical replication conflicts is as follows: + The conflict_log_destination + parameter can automatically creates a dedicated conflict log table. This table is created in the dedicated + pg_conflict namespace. The name of the conflict log table + is pg_conflict_<subid>. The predefined schema of this table is + detailed in + . + + + + Conflict Log Table Schema + + + + Column + Type + Description + + + + + relid + oid + The OID of the local table where the conflict occurred. + + + schemaname + text + The schema name of the conflicting table. + + + relname + text + The name of the conflicting table. + + + conflict_type + text + The type of conflict that occurred (e.g., insert_exists). + + + remote_xid + xid + The remote transaction ID that caused the conflict. + + + remote_commit_lsn + pg_lsn + The final LSN of the remote transaction. + + + remote_commit_ts + timestamptz + The remote commit timestamp of the remote transaction. + + + remote_origin + text + The origin of the remote transaction. + + + remote_tuple + json + The JSON representation of the incoming remote row that caused the conflict. + + + local_conflicts + json[] + + An array of JSON objects representing the local state for each conflict attempt. + Each object includes the local transaction ID (xid), commit + timestamp (commit_ts), origin (origin), + conflicting key data (key), and the full local row + image (tuple). + + + + +
+ + + The conflicting row data, including the incoming remote row (remote_tuple) + and the associated local conflict details (local_conflicts), is stored in + JSON formats, for flexible querying and analysis. + + + + If conflict_log_destination + is set to log conflicts to the server log, the following format is used: LOG: conflict detected on relation "schemaname.tablename": conflict=conflict_type DETAIL: detailed_explanation[: detail_values [, ... ]]. @@ -2415,6 +2515,13 @@ CONTEXT: processing remote data for replication origin "pg_16395" during "INSER key or replica identity defined for it. + + + + Conflict log tables (see conflict_log_destination parameter) + are never published, even when using FOR ALL TABLES in a publication. + + diff --git a/doc/src/sgml/ref/alter_subscription.sgml b/doc/src/sgml/ref/alter_subscription.sgml index f215fb0e5a2..23e6b5c4442 100644 --- a/doc/src/sgml/ref/alter_subscription.sgml +++ b/doc/src/sgml/ref/alter_subscription.sgml @@ -293,8 +293,9 @@ ALTER SUBSCRIPTION name RENAME TO < failover, two_phase, retain_dead_tuples, - max_retention_duration, and - wal_receiver_timeout. + max_retention_duration, + wal_receiver_timeout, and + conflict_log_destination. Only a superuser can set password_required = false. @@ -352,6 +353,15 @@ ALTER SUBSCRIPTION name RENAME TO < pg_conflict_detection, created to retain dead tuples for conflict detection, will be dropped. + + + When the conflict_log_destination + parameter is set to table or all, the system + automatically creates the internal conflict log table if it does not already + exist. Conversely, if the destination is changed to + log, logging to the table stops and the internal + table is automatically dropped. + diff --git a/doc/src/sgml/ref/create_subscription.sgml b/doc/src/sgml/ref/create_subscription.sgml index 07d5b1bd77c..3638eccffc9 100644 --- a/doc/src/sgml/ref/create_subscription.sgml +++ b/doc/src/sgml/ref/create_subscription.sgml @@ -261,6 +261,53 @@ CREATE SUBSCRIPTION subscription_name + + conflict_log_destination (enum) + + + Specifies the destination for recording logical replication conflicts. + + + The available destinations are: + + + + log: Conflict details are recorded in the server log. + This is the default behavior. + + + + + table: The system automatically creates a structured table + named pg_conflict_<subid> in the + pg_conflict schema. This allows for easy querying and + analysis of conflicts. + + + + The internal conflict log table is strictly tied to the lifecycle of the + subscription or the conflict_log_destination setting. If + the subscription is dropped, or if the destination is changed to + log, the table and all its recorded conflict data are + permanently deleted. + + + If post-mortem analysis may be needed, back up the conflict log table before + removing the subscription. + + + + + + all: Records conflict details to both destinations + log and table. + + + + + + + copy_data (boolean) -- 2.49.0