agora inbox for [email protected]
help / color / mirror / Atom feedRe: Quorum commit for multiple synchronous replication.
267+ messages / 11 participants
[nested] [flat]
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-07 15:25 Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-11-07 15:25 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Tue, Oct 25, 2016 at 10:35 PM, Michael Paquier
<[email protected]> wrote:
> On Mon, Oct 17, 2016 at 4:00 PM, Masahiko Sawada <[email protected]> wrote:
>> Attached latest patch.
>> Please review it.
>
> Okay, so let's move on with this patch...
Thank you for reviewing this patch.
> + <para>
> + The keyword <literal>ANY</> is omissible, but note that there is
> + not compatibility between <productname>PostgreSQL</> version 10 and
> + 9.6 or before. For example, <literal>1 (s1, s2)</> is the same as the
> + configuration with <literal>FIRST</> and <replaceable
> class="parameter">
> + num_sync</replaceable> equal to 1 in <productname>PostgreSQL</> 9.6
> + or before. On the other hand, It's the same as the configuration with
> + <literal>ANY</> and <replaceable
> class="parameter">num_sync</> equal to
> + 1 in <productname>PostgreSQL</> 10 or later.
> + </para>
> This paragraph could be reworded:
> If FIRST or ANY are not specified, this parameter behaves as ANY. Note
> that this grammar is incompatible with PostgreSQL 9.6, where no
> keyword specified is equivalent as if FIRST was specified.
> In short, there is no real need to specify num_sync as this behavior
> does not have changed, as well as it is not necessary to mention
> pre-9.6 versions as the multi-sync grammar has been added in 9.6.
Fixed.
> - Specifying more than one standby name can allow very high availability.
> Why removing this sentence?
>
> + The keyword <literal>ANY</>, coupeld with an interger number N,
> s/coupeld/coupled/ and s/interger/integer/, for a double hit in one
> line, still...
>
> + The keyword <literal>ANY</>, coupeld with an interger number N,
> + chooses N standbys in a set of standbys with the same, lowest,
> + priority and makes transaction commit when WAL records are received
> + those N standbys.
> This could be reworded more simply, for example: The keyword ANY,
> coupled with an integer number N, makes transaction commits wait until
> WAL records are received from N connected standbys among those defined
> in the list of synchronous_standby_names.
>
> + <literal>s2</> and <literal>s3</> wil be considered as synchronous standby
> s/wil/will/
>
> + when standby is considered as a condidate of quorum commit.</entry>
> s/condidate/candidate/
>
> [... stopping here ...] Please be more careful with the documentation
> and comment grammar. There are other things in the patch..
I fix some typo as much as I found.
> A bunch of comments at the top of syncrep.c need to be updated.
>
> +extern List *SyncRepGetSyncStandbysPriority(bool *am_sync);
> +extern List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
> Those two should be static routines in syncrep.c, let's keep the whole
> logic about quorum and higher-priority definition only there and not
> bother the callers of them about that.
Fixed.
> + if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
> + return SyncRepGetSyncStandbysPriority(am_sync);
> + else /* SYNC_REP_QUORUM */
> + return SyncRepGetSyncStandbysQuorum(am_sync);
> Both routines share the same logic to detect if a WAL sender can be
> selected as a candidate for sync evaluation or not, still per the
> selection they do I agree that it is better to keep them as separate.
>
> + /* In quroum method, all sync standby priorities are always 1 */
> + if (found && SyncRepConfig->sync_method == SYNC_REP_QUORUM)
> + priority = 1;
> Honestly I don't understand why you are enforcing that. Priority can
> be important for users willing to switch from ANY to FIRST to have a
> look immediately at what are the standbys that would become sync or
> potential.
I thought that since all standbys appearing in s_s_names list are
treated equally in quorum method, these standbys should have same
priority.
If these standby have different sync_priority, it looks like that
master server replicates to standby server based on priority.
> else if (list_member_int(sync_standbys, i))
> - values[7] = CStringGetTextDatum("sync");
> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
> The comment at the top of this code block needs to be refreshed.
Fixed.
> The representation given to the user in pg_stat_replication is not
> enough IMO. For example, imagine a cluster with 4 standbys:
> =# select application_name, sync_priority, sync_state from pg_stat_replication ;
> application_name | sync_priority | sync_state
> ------------------+---------------+------------
> node_5433 | 0 | async
> node_5434 | 0 | async
> node_5435 | 0 | async
> node_5436 | 0 | async
> (4 rows)
>
> If FIRST N is used, is it easy for the user to understand what are the
> nodes in sync:
> =# alter system set synchronous_standby_names = 'FIRST 2 (node_5433,
> node_5434, node_5435)';
> ALTER SYSTEM
> =# select pg_reload_conf();
> pg_reload_conf
> ----------------
> t
> (1 row)
> =# select application_name, sync_priority, sync_state from pg_stat_replication ;
> application_name | sync_priority | sync_state
> ------------------+---------------+------------
> node_5433 | 1 | sync
> node_5434 | 2 | sync
> node_5435 | 3 | potential
> node_5436 | 0 | async
> (4 rows)
>
> In this case it is easy to understand that two nodes are required to be in sync.
>
> When using ANY similarly for three nodes, here is what
> pg_stat_replication tells:
> =# select application_name, sync_priority, sync_state from pg_stat_replication ;
> application_name | sync_priority | sync_state
> ------------------+---------------+------------
> node_5433 | 1 | quorum
> node_5434 | 1 | quorum
> node_5435 | 1 | quorum
> node_5436 | 0 | async
> (4 rows)
>
> It is not possible to guess from how many standbys this needs to wait
> for. One idea would be to mark the sync_state not as "quorum", but
> "quorum-N", or just add a new column to indicate how many in the set
> need to give a commit confirmation.
As Simon suggested before, we could support another feature that
allows the client to control the quorum number.
Considering adding that feature, I thought it's better to have and
control that information as a GUC parameter.
Thought?
Attached latest v5 patch.
Please review it.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[text/x-diff] 000_quorum_commit_v5.patch (27.1K, ../../CAD21AoC9ZgYEJpw+75AJPM_NUbfqmSeG8q2EMP5ubKHM9dJ-zg@mail.gmail.com/2-000_quorum_commit_v5.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index adab2f8..8078cda 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3028,42 +3028,76 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
- <literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ANY] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+FIRST <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method of
+ that how master server controls the standby servers.
</para>
<para>
- The second syntax was used before <productname>PostgreSQL</>
+ The keyword <literal>FIRST</>, coupled with an integer
+ number N higher-priority standbys and makes transaction commit
+ when their WAL records are received.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with an integer number N,
+ makes transaction commits wait until WAL records are received
+ from N connected standbys among those defined in the list of
+ <varname>synchronous_standby_names</>. For example, a setting
+ of <literal>ANY 3 (s1, s2, s3, s4)</> makes transaction commits
+ wait until receiving receipts from at least any three standbys
+ of four listed servers <literal>s1</>, <literal>s2</>, <literal>s3</>,
+ <literal>s4</>.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive word
+ and the standby name having these words are must be double-quoted.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
- </para>
+ with <literal>FIRST</> and <replaceable class="parameter">num_sync</replaceable>
+ equal to 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
+ </para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this parameter
+ behaves as <literal>ANY</>. Note that this grammar is incompatible with
+ <productname>PostgresSQL</> 9.6, where no keyword specified is equivalent
+ as if <literal>FIRST</> was specified. In short, there is no real need to
+ specify <replaceable class="parameter">num_sync</replaceable> as this
+ behavior does not have changed, as well as it is not necessary to mention
+ pre-9.6 versions are the multi-sync grammar has been added in 9.6.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 5bedaf2..7a0a22a 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1161,6 +1161,18 @@ synchronous_standby_names = '2 (s1, s2, s3)'
<literal>s2</> fails. <literal>s4</> is an asynchronous standby since
its name is not in the list.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys <literal>s1</>,
+ <literal>s2</> and <literal>s3</> will be considered as synchronous standby
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 3de489e..b44dadb 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1389,7 +1389,10 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<row>
<entry><structfield>sync_state</></entry>
<entry><type>text</></entry>
- <entry>Synchronous state of this standby server</entry>
+ <entry>Synchronous state of this standby server. <literal>quorum-N</>
+ , where N is the number of synchronous standbys that transactions
+ need to wait for replies from, when standby is considered as a
+ candidate of quorum commit.</entry>
</row>
</tbody>
</tgroup>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..74093cd 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,19 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are specified
+ * in synchronous_standby_names. This parameter also specifies a list
+ * of standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the standbys
+ * whose names appear earlier in the list are given higher priority
+ * and will be considered as synchronous. Other standby servers appearing
+ * later in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, the all standbys appearing in the list are
+ * considered as a candidate for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +76,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +392,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +419,10 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the synced
+ * positions among all sync standbys using method.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +440,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +476,45 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys using according to synchronous method,
+ * or NIL if no sync standby is connected. The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else /* SYNC_REP_QUORUM */
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, we need the oldest these positions among sync
+ * standbys. In quorum method, we need the newest these positions
+ * specified by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -507,29 +540,74 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
return false;
}
- /*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
- */
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else /* SYNC_REP_QUORUM */
+ {
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i]= walsnd->flush;
+ apply_array[i] = walsnd->flush;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th newest Write, Flush, Apply positions
+ * specified by SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
list_free(sync_standbys);
@@ -537,17 +615,66 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
+ * standbys except for the standbys which are not active, or connected
+ * as async.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as candidate of sync and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +687,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -749,6 +870,10 @@ SyncRepGetStandbyPriority(void)
standby_name += strlen(standby_name) + 1;
}
+ /* In quorum method, all sync standby priorities are always 1 */
+ if (found && SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ priority = 1;
+
return (found ? priority : 0);
}
@@ -892,6 +1017,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..403fd7d 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,14 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index bc5e508..ecfbd78 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2860,12 +2860,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, we add the number to indicate
+ * how many in the set need to give a commit confirmation.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..8dd74a3 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..c6af72f 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 10;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'First 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'First 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'First 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'First 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,25 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check that the state of standbys listed as a voter are having
+# same priority when synchronous_standby_names uses quorum method.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby4|0|async),
+'2 quorum and 1 async',
+'Any 2(standby1, standby2)');
+
+# Start Standby3 which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that set setting of 'Any 2(*)' chooses all standbys as
+# voter.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+'all standbys are considered as candidates for quorum commit',
+'Any 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-08 13:12 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-11-08 13:12 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Tue, Nov 8, 2016 at 12:25 AM, Masahiko Sawada <[email protected]> wrote:
> On Tue, Oct 25, 2016 at 10:35 PM, Michael Paquier
> <[email protected]> wrote:
>> + if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
>> + return SyncRepGetSyncStandbysPriority(am_sync);
>> + else /* SYNC_REP_QUORUM */
>> + return SyncRepGetSyncStandbysQuorum(am_sync);
>> Both routines share the same logic to detect if a WAL sender can be
>> selected as a candidate for sync evaluation or not, still per the
>> selection they do I agree that it is better to keep them as separate.
>>
>> + /* In quroum method, all sync standby priorities are always 1 */
>> + if (found && SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>> + priority = 1;
>> Honestly I don't understand why you are enforcing that. Priority can
>> be important for users willing to switch from ANY to FIRST to have a
>> look immediately at what are the standbys that would become sync or
>> potential.
>
> I thought that since all standbys appearing in s_s_names list are
> treated equally in quorum method, these standbys should have same
> priority.
> If these standby have different sync_priority, it looks like that
> master server replicates to standby server based on priority.
No actually, because we know that they are a quorum set, and that they
work in the same set. The concept of priorities has no real meaning
for quorum as there is no ordering of the elements. Another, perhaps
cleaner idea may be to mark the field as NULL actually.
>> It is not possible to guess from how many standbys this needs to wait
>> for. One idea would be to mark the sync_state not as "quorum", but
>> "quorum-N", or just add a new column to indicate how many in the set
>> need to give a commit confirmation.
>
> As Simon suggested before, we could support another feature that
> allows the client to control the quorum number.
> Considering adding that feature, I thought it's better to have and
> control that information as a GUC parameter.
> Thought?
Similarly that would be a SIGHUP parameter? Why not. Perhaps my worry
is not that much legitimate, users could just look at s_s_names to
guess how many in hte set a commit needs to wait for.
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive word
+ and the standby name having these words are must be double-quoted.
+ </para>
s/word/words/.
+ <literal>FIRST</> and <literal>ANY</> specify the method of
+ that how master server controls the standby servers.
A little bit hard to understand, I would suggest:
FIRST and ANY specify the method used by the master to control the
standby servers.
+ The keyword <literal>FIRST</>, coupled with an integer
+ number N higher-priority standbys and makes transaction commit
+ when their WAL records are received.
This is unclear to me. Here is a correction:
The keyword FIRST, coupled with an integer N, makes transaction commit
wait until WAL records are received fron the N standbys with higher
priority number.
+ <varname>synchronous_standby_names</>. For example, a setting
+ of <literal>ANY 3 (s1, s2, s3, s4)</> makes transaction commits
+ wait until receiving receipts from at least any three standbys
+ of four listed servers <literal>s1</>, <literal>s2</>, <literal>s3</>,
This could just mention WAL records instead of "receipts".
Instead of saying "an integer number N", we could use <literal>num_sync</>.
+ If <literal>FIRST</> or <literal>ANY</> are not specified,
this parameter
+ behaves as <literal>ANY</>. Note that this grammar is
incompatible with
+ <productname>PostgresSQL</> 9.6, where no keyword specified
is equivalent
+ as if <literal>FIRST</> was specified. In short, there is no
real need to
+ specify <replaceable class="parameter">num_sync</replaceable> as this
+ behavior does not have changed, as well as it is not
necessary to mention
+ pre-9.6 versions are the multi-sync grammar has been added in 9.6.
This paragraph could be reworked, say:
if FIRST or ANY are not specified this parameter behaves as if ANY is
used. Note that this grammar is incompatible with PostgreSQL 9.6 which
is the first version supporting multiple standbys with synchronous
replication, where no such keyword FIRST or ANY can be used. Note that
the grammar behaves as if FIRST is used, which is incompatible with
the post-9.6 behavior.
+ <entry>Synchronous state of this standby server. <literal>quorum-N</>
+ , where N is the number of synchronous standbys that transactions
+ need to wait for replies from, when standby is considered as a
+ candidate of quorum commit.</entry>
Nitpicking: I think that the comma goes to the previous line if it is
the first character of a line.
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else /* SYNC_REP_QUORUM */
+ return SyncRepGetSyncStandbysQuorum(am_sync)
Or that?
if (PRIORITY)
return StandbysPriority();
else if (QUORUM)
return StandbysQuorum();
else
elog(ERROR, "Boom");
+ * In priority method, we need the oldest these positions among sync
+ * standbys. In quorum method, we need the newest these positions
+ * specified by SyncRepConfig->num_sync.
Last sentence is grammatically incorrect, and it would be more correct
to precise the Nth LSN positions to be able to select k standbys from
a set of n ones.
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i]= walsnd->flush;
+ apply_array[i] = walsnd->flush;
+ SpinLockRelease(&walsnd->mutex);
A nit: adding a space on the self of the second = character. And you
need to save the apply position of the WAL sender, not the flush
position in the array that is going to be ordered.
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, we add the number to indicate
+ * how many in the set need to give a commit confirmation.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum")
This code block and its explanation comments tell two different
stories. The comment is saying that something like "quorum-N" is used
but the code always prints "quorum".
It may be a good idea in the test to check that when no keywords is
specified the group of standbys is in quorum mode.
The code looks in good shape, I am still willing to run more advanced
tests manually.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-14 08:39 Masahiko Sawada <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-11-14 08:39 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Tue, Nov 8, 2016 at 10:12 PM, Michael Paquier
<[email protected]> wrote:
> On Tue, Nov 8, 2016 at 12:25 AM, Masahiko Sawada <[email protected]> wrote:
>> On Tue, Oct 25, 2016 at 10:35 PM, Michael Paquier
>> <[email protected]> wrote:
>>> + if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
>>> + return SyncRepGetSyncStandbysPriority(am_sync);
>>> + else /* SYNC_REP_QUORUM */
>>> + return SyncRepGetSyncStandbysQuorum(am_sync);
>>> Both routines share the same logic to detect if a WAL sender can be
>>> selected as a candidate for sync evaluation or not, still per the
>>> selection they do I agree that it is better to keep them as separate.
>>>
>>> + /* In quroum method, all sync standby priorities are always 1 */
>>> + if (found && SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>>> + priority = 1;
>>> Honestly I don't understand why you are enforcing that. Priority can
>>> be important for users willing to switch from ANY to FIRST to have a
>>> look immediately at what are the standbys that would become sync or
>>> potential.
>>
>> I thought that since all standbys appearing in s_s_names list are
>> treated equally in quorum method, these standbys should have same
>> priority.
>> If these standby have different sync_priority, it looks like that
>> master server replicates to standby server based on priority.
>
> No actually, because we know that they are a quorum set, and that they
> work in the same set. The concept of priorities has no real meaning
> for quorum as there is no ordering of the elements. Another, perhaps
> cleaner idea may be to mark the field as NULL actually.
We know that but I'm concerned it might confuse the user.
If these priorities are the same, it can obviously imply that all of
the standby listed in s_s_names are handled equally.
>>> It is not possible to guess from how many standbys this needs to wait
>>> for. One idea would be to mark the sync_state not as "quorum", but
>>> "quorum-N", or just add a new column to indicate how many in the set
>>> need to give a commit confirmation.
>>
>> As Simon suggested before, we could support another feature that
>> allows the client to control the quorum number.
>> Considering adding that feature, I thought it's better to have and
>> control that information as a GUC parameter.
>> Thought?
>
> Similarly that would be a SIGHUP parameter? Why not. Perhaps my worry
> is not that much legitimate, users could just look at s_s_names to
> guess how many in hte set a commit needs to wait for.
It would be PGC_USRSET similar to synchronous_commit. The user can
specify it in statement level.
> + <para>
> + <literal>FIRST</> and <literal>ANY</> are case-insensitive word
> + and the standby name having these words are must be double-quoted.
> + </para>
> s/word/words/.
>
> + <literal>FIRST</> and <literal>ANY</> specify the method of
> + that how master server controls the standby servers.
> A little bit hard to understand, I would suggest:
> FIRST and ANY specify the method used by the master to control the
> standby servers.
>
> + The keyword <literal>FIRST</>, coupled with an integer
> + number N higher-priority standbys and makes transaction commit
> + when their WAL records are received.
> This is unclear to me. Here is a correction:
> The keyword FIRST, coupled with an integer N, makes transaction commit
> wait until WAL records are received fron the N standbys with higher
> priority number.
>
> + <varname>synchronous_standby_names</>. For example, a setting
> + of <literal>ANY 3 (s1, s2, s3, s4)</> makes transaction commits
> + wait until receiving receipts from at least any three standbys
> + of four listed servers <literal>s1</>, <literal>s2</>, <literal>s3</>,
> This could just mention WAL records instead of "receipts".
>
> Instead of saying "an integer number N", we could use <literal>num_sync</>.
>
> + If <literal>FIRST</> or <literal>ANY</> are not specified,
> this parameter
> + behaves as <literal>ANY</>. Note that this grammar is
> incompatible with
> + <productname>PostgresSQL</> 9.6, where no keyword specified
> is equivalent
> + as if <literal>FIRST</> was specified. In short, there is no
> real need to
> + specify <replaceable class="parameter">num_sync</replaceable> as this
> + behavior does not have changed, as well as it is not
> necessary to mention
> + pre-9.6 versions are the multi-sync grammar has been added in 9.6.
> This paragraph could be reworked, say:
> if FIRST or ANY are not specified this parameter behaves as if ANY is
> used. Note that this grammar is incompatible with PostgreSQL 9.6 which
> is the first version supporting multiple standbys with synchronous
> replication, where no such keyword FIRST or ANY can be used. Note that
> the grammar behaves as if FIRST is used, which is incompatible with
> the post-9.6 behavior.
>
> + <entry>Synchronous state of this standby server. <literal>quorum-N</>
> + , where N is the number of synchronous standbys that transactions
> + need to wait for replies from, when standby is considered as a
> + candidate of quorum commit.</entry>
> Nitpicking: I think that the comma goes to the previous line if it is
> the first character of a line.
>
> + if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
> + return SyncRepGetSyncStandbysPriority(am_sync);
> + else /* SYNC_REP_QUORUM */
> + return SyncRepGetSyncStandbysQuorum(am_sync)
> Or that?
> if (PRIORITY)
> return StandbysPriority();
> else if (QUORUM)
> return StandbysQuorum();
> else
> elog(ERROR, "Boom");
>
> + * In priority method, we need the oldest these positions among sync
> + * standbys. In quorum method, we need the newest these positions
> + * specified by SyncRepConfig->num_sync.
> Last sentence is grammatically incorrect, and it would be more correct
> to precise the Nth LSN positions to be able to select k standbys from
> a set of n ones.
>
> + SpinLockAcquire(&walsnd->mutex);
> + write_array[i] = walsnd->write;
> + flush_array[i]= walsnd->flush;
> + apply_array[i] = walsnd->flush;
> + SpinLockRelease(&walsnd->mutex);
> A nit: adding a space on the self of the second = character. And you
> need to save the apply position of the WAL sender, not the flush
> position in the array that is going to be ordered.
>
> /*
> * More easily understood version of standby state. This is purely
> - * informational, not different from priority.
> + * informational. In quorum method, we add the number to indicate
> + * how many in the set need to give a commit confirmation.
> */
> if (priority == 0)
> values[7] = CStringGetTextDatum("async");
> else if (list_member_int(sync_standbys, i))
> - values[7] = CStringGetTextDatum("sync");
> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum")
> This code block and its explanation comments tell two different
> stories. The comment is saying that something like "quorum-N" is used
> but the code always prints "quorum".
>
> It may be a good idea in the test to check that when no keywords is
> specified the group of standbys is in quorum mode.
Yeah, I will add some tests.
I will post new version patch incorporated other comments.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-16 03:08 Masahiko Sawada <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-11-16 03:08 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Mon, Nov 14, 2016 at 5:39 PM, Masahiko Sawada <[email protected]> wrote:
> On Tue, Nov 8, 2016 at 10:12 PM, Michael Paquier
> <[email protected]> wrote:
>> On Tue, Nov 8, 2016 at 12:25 AM, Masahiko Sawada <[email protected]> wrote:
>>> On Tue, Oct 25, 2016 at 10:35 PM, Michael Paquier
>>> <[email protected]> wrote:
>>>> + if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
>>>> + return SyncRepGetSyncStandbysPriority(am_sync);
>>>> + else /* SYNC_REP_QUORUM */
>>>> + return SyncRepGetSyncStandbysQuorum(am_sync);
>>>> Both routines share the same logic to detect if a WAL sender can be
>>>> selected as a candidate for sync evaluation or not, still per the
>>>> selection they do I agree that it is better to keep them as separate.
>>>>
>>>> + /* In quroum method, all sync standby priorities are always 1 */
>>>> + if (found && SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>>>> + priority = 1;
>>>> Honestly I don't understand why you are enforcing that. Priority can
>>>> be important for users willing to switch from ANY to FIRST to have a
>>>> look immediately at what are the standbys that would become sync or
>>>> potential.
>>>
>>> I thought that since all standbys appearing in s_s_names list are
>>> treated equally in quorum method, these standbys should have same
>>> priority.
>>> If these standby have different sync_priority, it looks like that
>>> master server replicates to standby server based on priority.
>>
>> No actually, because we know that they are a quorum set, and that they
>> work in the same set. The concept of priorities has no real meaning
>> for quorum as there is no ordering of the elements. Another, perhaps
>> cleaner idea may be to mark the field as NULL actually.
>
> We know that but I'm concerned it might confuse the user.
> If these priorities are the same, it can obviously imply that all of
> the standby listed in s_s_names are handled equally.
>
>>>> It is not possible to guess from how many standbys this needs to wait
>>>> for. One idea would be to mark the sync_state not as "quorum", but
>>>> "quorum-N", or just add a new column to indicate how many in the set
>>>> need to give a commit confirmation.
>>>
>>> As Simon suggested before, we could support another feature that
>>> allows the client to control the quorum number.
>>> Considering adding that feature, I thought it's better to have and
>>> control that information as a GUC parameter.
>>> Thought?
>>
>> Similarly that would be a SIGHUP parameter? Why not. Perhaps my worry
>> is not that much legitimate, users could just look at s_s_names to
>> guess how many in hte set a commit needs to wait for.
>
> It would be PGC_USRSET similar to synchronous_commit. The user can
> specify it in statement level.
>
>> + <para>
>> + <literal>FIRST</> and <literal>ANY</> are case-insensitive word
>> + and the standby name having these words are must be double-quoted.
>> + </para>
>> s/word/words/.
>>
>> + <literal>FIRST</> and <literal>ANY</> specify the method of
>> + that how master server controls the standby servers.
>> A little bit hard to understand, I would suggest:
>> FIRST and ANY specify the method used by the master to control the
>> standby servers.
>>
>> + The keyword <literal>FIRST</>, coupled with an integer
>> + number N higher-priority standbys and makes transaction commit
>> + when their WAL records are received.
>> This is unclear to me. Here is a correction:
>> The keyword FIRST, coupled with an integer N, makes transaction commit
>> wait until WAL records are received fron the N standbys with higher
>> priority number.
>>
>> + <varname>synchronous_standby_names</>. For example, a setting
>> + of <literal>ANY 3 (s1, s2, s3, s4)</> makes transaction commits
>> + wait until receiving receipts from at least any three standbys
>> + of four listed servers <literal>s1</>, <literal>s2</>, <literal>s3</>,
>> This could just mention WAL records instead of "receipts".
>>
>> Instead of saying "an integer number N", we could use <literal>num_sync</>.
>>
>> + If <literal>FIRST</> or <literal>ANY</> are not specified,
>> this parameter
>> + behaves as <literal>ANY</>. Note that this grammar is
>> incompatible with
>> + <productname>PostgresSQL</> 9.6, where no keyword specified
>> is equivalent
>> + as if <literal>FIRST</> was specified. In short, there is no
>> real need to
>> + specify <replaceable class="parameter">num_sync</replaceable> as this
>> + behavior does not have changed, as well as it is not
>> necessary to mention
>> + pre-9.6 versions are the multi-sync grammar has been added in 9.6.
>> This paragraph could be reworked, say:
>> if FIRST or ANY are not specified this parameter behaves as if ANY is
>> used. Note that this grammar is incompatible with PostgreSQL 9.6 which
>> is the first version supporting multiple standbys with synchronous
>> replication, where no such keyword FIRST or ANY can be used. Note that
>> the grammar behaves as if FIRST is used, which is incompatible with
>> the post-9.6 behavior.
>>
>> + <entry>Synchronous state of this standby server. <literal>quorum-N</>
>> + , where N is the number of synchronous standbys that transactions
>> + need to wait for replies from, when standby is considered as a
>> + candidate of quorum commit.</entry>
>> Nitpicking: I think that the comma goes to the previous line if it is
>> the first character of a line.
>>
>> + if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
>> + return SyncRepGetSyncStandbysPriority(am_sync);
>> + else /* SYNC_REP_QUORUM */
>> + return SyncRepGetSyncStandbysQuorum(am_sync)
>> Or that?
>> if (PRIORITY)
>> return StandbysPriority();
>> else if (QUORUM)
>> return StandbysQuorum();
>> else
>> elog(ERROR, "Boom");
>>
>> + * In priority method, we need the oldest these positions among sync
>> + * standbys. In quorum method, we need the newest these positions
>> + * specified by SyncRepConfig->num_sync.
>> Last sentence is grammatically incorrect, and it would be more correct
>> to precise the Nth LSN positions to be able to select k standbys from
>> a set of n ones.
>>
>> + SpinLockAcquire(&walsnd->mutex);
>> + write_array[i] = walsnd->write;
>> + flush_array[i]= walsnd->flush;
>> + apply_array[i] = walsnd->flush;
>> + SpinLockRelease(&walsnd->mutex);
>> A nit: adding a space on the self of the second = character. And you
>> need to save the apply position of the WAL sender, not the flush
>> position in the array that is going to be ordered.
>>
>> /*
>> * More easily understood version of standby state. This is purely
>> - * informational, not different from priority.
>> + * informational. In quorum method, we add the number to indicate
>> + * how many in the set need to give a commit confirmation.
>> */
>> if (priority == 0)
>> values[7] = CStringGetTextDatum("async");
>> else if (list_member_int(sync_standbys, i))
>> - values[7] = CStringGetTextDatum("sync");
>> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
>> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum")
>> This code block and its explanation comments tell two different
>> stories. The comment is saying that something like "quorum-N" is used
>> but the code always prints "quorum".
>>
>> It may be a good idea in the test to check that when no keywords is
>> specified the group of standbys is in quorum mode.
>
> Yeah, I will add some tests.
>
> I will post new version patch incorporated other comments.
>
Attached latest version patch incorporated review comments. After more
thought, I agree and changed the value of standby priority in quorum
method so that it's not set 1 forcibly. The all standby priorities are
1 If s_s_names = 'ANY(*)'.
Please review this patch.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[application/x-patch] 000_quorum_commit_v6.patch (27.1K, ../../CAD21AoBGXB286o1eL0vGidg05iWUzXGebMOB3pYeD5cq9Ocerg@mail.gmail.com/2-000_quorum_commit_v6.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index adab2f8..e125dff 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3028,42 +3028,75 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
- <literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ANY] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+FIRST <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servres.
</para>
<para>
- The second syntax was used before <productname>PostgreSQL</>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>, makes
+ transaction commit wait until WAL records are received from the
+ <literal>num_sync</> standbys with higher priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ any three standbys of four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name having these words are must be double-quoted.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
- </para>
+ with <literal>FIRST</> and <replaceable class="parameter">num_sync</replaceable>
+ equal to 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
+ </para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this parameter
+ behaves as if <literal>ANY</> is used. Note that this grammar is incompatible
+ with <productname>PostgresSQL</> 9.6 which is first version supporting multiple
+ standbys with synchronous replication, where no such keyword <literal>FIRST</>
+ or <literal>ANY</> can be used. Note that the grammer behaves as if <literal>FIRST</>
+ is used, which is incompatible with the post-9.6 version behavior.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 5bedaf2..7a0a22a 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1161,6 +1161,18 @@ synchronous_standby_names = '2 (s1, s2, s3)'
<literal>s2</> fails. <literal>s4</> is an asynchronous standby since
its name is not in the list.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys <literal>s1</>,
+ <literal>s2</> and <literal>s3</> will be considered as synchronous standby
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 3de489e..2c5f3de 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1389,7 +1389,8 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<row>
<entry><structfield>sync_state</></entry>
<entry><type>text</></entry>
- <entry>Synchronous state of this standby server</entry>
+ <entry>Synchronous state of this standby server. It is <literal>quorum</>
+ when standby is considered as a candidate of quorum commit.</entry>
</row>
</tbody>
</tgroup>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..bcc1317 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,19 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are specified
+ * in synchronous_standby_names. This parameter also specifies a list
+ * of standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the standbys
+ * whose names appear earlier in the list are given higher priority
+ * and will be considered as synchronous. Other standby servers appearing
+ * later in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, the all standbys appearing in the list are
+ * considered as a candidate for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +76,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +392,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +419,10 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the synced
+ * positions among all sync standbys using method.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +440,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +476,50 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys using according to synchronous method,
+ * or NIL if no sync standby is connected. The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ "invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, we need the oldest these positions among sync
+ * standbys. In quorum method, we need the newest these positions
+ * specified by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -507,29 +545,74 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
return false;
}
- /*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
- */
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else /* SYNC_REP_QUORUM */
+ {
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th newest Write, Flush, Apply positions
+ * specified by SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
list_free(sync_standbys);
@@ -537,17 +620,66 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
+ * standbys except for the standbys which are not active, or connected
+ * as async.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as candidate of sync and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +692,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1018,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..403fd7d 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,14 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index bc5e508..04fe994 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2860,12 +2860,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are considered as
+ * a candidate of quorum commit standby state is always 'quorum'.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..8dd74a3 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..c502d20 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'FIRST 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'FIRST 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'FIRST 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'FIRST 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,34 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check that the state of standbys listed as a voter are having
+# same priority when synchronous_standby_names uses quorum method.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'2 quorum and 1 async',
+'ANY 2(standby1, standby2)');
+
+# Check that state of standbys are not the same as the behaviour of that
+# 'ANY' is specified.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'not specify synchronization method',
+'2(standby1, standby2)');
+
+# Start Standby3 which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that set setting of 'ANY 2(*)' chooses all standbys as
+# voter.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+'all standbys are considered as candidates for quorum commit',
+'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-26 13:27 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-11-26 13:27 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Tue, Nov 15, 2016 at 7:08 PM, Masahiko Sawada <[email protected]> wrote:
> Attached latest version patch incorporated review comments. After more
> thought, I agree and changed the value of standby priority in quorum
> method so that it's not set 1 forcibly. The all standby priorities are
> 1 If s_s_names = 'ANY(*)'.
> Please review this patch.
Sorry for my late reply. Here is my final lookup.
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable
class="parameter">standby_name</replaceable> [, ...] )
+[ANY] <replaceable class="parameter">num_sync</replaceable> (
<replaceable class="parameter">standby_name</replaceable> [, ...] )
+FIRST <replaceable class="parameter">num_sync</replaceable> (
<replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...
This can just be replaced with [ ANY | FIRST ]. There is no need for
braces as the keyword is not mandatory.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servres.
</para>
s/servres/servers/.
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
This can be simplified a bit as "quorum" is the state value for all
standbys with a non-zero priority when the method is set to
SYNC_REP_QUORUM:
if (priority == 0)
values[7] = CStringGetTextDatum("async");
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ values[7] = CStringGetTextDatum("quorum");
else if (list_member_int(sync_standbys, i))
values[7] = CStringGetTextDatum("sync");
else
SyncRepConfig data is made external to syncrep.c with this patch as
walsender.c needs to look at the sync method in place, no complain
about that after considering if there could be a more elegant way to
do things without this change.
While reviewing the patch, I have found a couple of incorrectly shaped
sentences, both in the docs and some comments. Attached is a new
version with this word-smithing. The patch is now switched as ready
for committer.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[application/x-patch] 000_quorum_commit_v7.patch (27.3K, ../../CAB7nPqR6-ytYMrrkMGbAz1R7pqFQu1pGJX166uBZqAfZapisXg@mail.gmail.com/2-000_quorum_commit_v7.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index dcd0663..bff932b 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3029,42 +3029,76 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
- <literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ ANY | FIRST ] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servers.
</para>
<para>
- The second syntax was used before <productname>PostgreSQL</>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from the <literal>num_sync</> standbys with highest priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by the three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ three standbys among the four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name including those words must use double quotes.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
- </para>
+ with <literal>FIRST</> and <literal>num_sync</replaceable> equal to
+ 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
+ </para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this
+ parameter behaves as if <literal>ANY</> is used. Note that this
+ grammar is incompatible with <productname>PostgresSQL</> 9.6 which
+ is first version supporting multiple standbys with synchronous
+ replication, where no such keyword <literal>FIRST</> or
+ <literal>ANY</> can be used. Note that the grammer behaves as if
+ <literal>FIRST</> is used, which is incompatible with the post-9.6
+ version behavior.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 5bedaf2..b57b4ca 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1161,6 +1161,19 @@ synchronous_standby_names = '2 (s1, s2, s3)'
<literal>s2</> fails. <literal>s4</> is an asynchronous standby since
its name is not in the list.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys
+ <literal>s1</>, <literal>s2</> and <literal>s3</> will be considered as
+ synchronous standby candidates. The master server will wait for at least
+ 2 replies from them. <literal>s4</> is an asynchronous standby since its
+ name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 3de489e..2c5f3de 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1389,7 +1389,8 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<row>
<entry><structfield>sync_state</></entry>
<entry><type>text</></entry>
- <entry>Synchronous state of this standby server</entry>
+ <entry>Synchronous state of this standby server. It is <literal>quorum</>
+ when standby is considered as a candidate of quorum commit.</entry>
</row>
</tbody>
</tgroup>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..efe7182 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,19 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are specified
+ * in synchronous_standby_names. This parameter also specifies a list
+ * of standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the standbys
+ * whose names appear earlier in the list are given higher priority
+ * and will be considered as synchronous. Other standby servers appearing
+ * later in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, all standbys appearing in the list are considered
+ * as candidates for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +76,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +392,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +419,12 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the flush
+ * apply and write LSN positions among all sync standbys using the
+ * method specified.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr,
+ &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +442,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +478,55 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys using according to synchronous method,
+ * or NIL if no sync standby is connected.
+ *
+ * The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ "incorrect synchronization method for standbys is specified \"%d\"",
+ SyncRepConfig->sync_method));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, the oldest flush, apply and write positions among
+ * all the sync standbys are calculated. In quorum method, in order to
+ * select the subset of standbys in the existing quorum set that will
+ * satisfy the conditions to be selected as synchronous, calculate the
+ * N-th newest flush, apply and write positions. In the latter case,
+ * the N-th element is defined by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -508,46 +553,145 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
+ * Switch through the calculation methods.
*/
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ {
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th newest Write, Flush, Apply positions specified by
+ * SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
+ else
+ elog(ERROR, "incorrect synchronization method for standbys");
list_free(sync_standbys);
return true;
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or NIL if no sync
+ * standby is connected. So this function returns the list of standbys except
+ * for the standbys which are not active or connected as asynchronous
+ * standbys.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as synchrounous candidate and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +704,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1030,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..403fd7d 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,14 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index aa42d59..8d29dc4 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2862,10 +2862,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are
+ * considered as a candidate of quorum commit, state is always
+ * set to 'quorum' for all the standbys.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ values[7] = CStringGetTextDatum("quorum");
else if (list_member_int(sync_standbys, i))
values[7] = CStringGetTextDatum("sync");
else
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..8dd74a3 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..13978bb 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'FIRST 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'FIRST 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'FIRST 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'FIRST 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,33 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check state of a quorum set made of two standbys with an asynchronous
+# standby.
+test_sync_state(
+ $node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+ 'quorum set of two standbys with one async standby',
+ 'ANY 2(standby1, standby2)');
+
+# Check that the state of standbys does not change when 'ANY' is omitted.
+test_sync_state(
+ $node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+ 'synchronization method definition omitted, switching to default quorum',
+ '2(standby1, standby2)');
+
+# Start standby3, which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that setting of 'ANY 2(*)' chooses all standbys as candidates for
+# quorum commit.
+test_sync_state(
+ $node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+ 'all standbys selected as candidates for quorum commit',
+ 'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-28 11:03 Masahiko Sawada <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 2 replies; 267+ messages in thread
From: Masahiko Sawada @ 2016-11-28 11:03 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Sat, Nov 26, 2016 at 10:27 PM, Michael Paquier
<[email protected]> wrote:
> On Tue, Nov 15, 2016 at 7:08 PM, Masahiko Sawada <[email protected]> wrote:
>> Attached latest version patch incorporated review comments. After more
>> thought, I agree and changed the value of standby priority in quorum
>> method so that it's not set 1 forcibly. The all standby priorities are
>> 1 If s_s_names = 'ANY(*)'.
>> Please review this patch.
>
> Sorry for my late reply. Here is my final lookup.
Thank you for reviewing!
> <synopsis>
> -<replaceable class="parameter">num_sync</replaceable> ( <replaceable
> class="parameter">standby_name</replaceable> [, ...] )
> +[ANY] <replaceable class="parameter">num_sync</replaceable> (
> <replaceable class="parameter">standby_name</replaceable> [, ...] )
> +FIRST <replaceable class="parameter">num_sync</replaceable> (
> <replaceable class="parameter">standby_name</replaceable> [, ...] )
> <replaceable class="parameter">standby_name</replaceable> [, ...
> This can just be replaced with [ ANY | FIRST ]. There is no need for
> braces as the keyword is not mandatory.
>
> + is the name of a standby server.
> + <literal>FIRST</> and <literal>ANY</> specify the method used by
> + the master to control the standby servres.
> </para>
> s/servres/servers/.
>
> if (priority == 0)
> values[7] = CStringGetTextDatum("async");
> else if (list_member_int(sync_standbys, i))
> - values[7] = CStringGetTextDatum("sync");
> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
> else
> values[7] = CStringGetTextDatum("potential");
> This can be simplified a bit as "quorum" is the state value for all
> standbys with a non-zero priority when the method is set to
> SYNC_REP_QUORUM:
> if (priority == 0)
> values[7] = CStringGetTextDatum("async");
> + else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
> + values[7] = CStringGetTextDatum("quorum");
> else if (list_member_int(sync_standbys, i))
> values[7] = CStringGetTextDatum("sync");
> else
>
> SyncRepConfig data is made external to syncrep.c with this patch as
> walsender.c needs to look at the sync method in place, no complain
> about that after considering if there could be a more elegant way to
> do things without this change.
Agreed.
> While reviewing the patch, I have found a couple of incorrectly shaped
> sentences, both in the docs and some comments. Attached is a new
> version with this word-smithing. The patch is now switched as ready
> for committer.
Thanks. I found a typo in v7 patch, so attached latest v8 patch.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[application/x-patch] 000_quorum_commit_v8.patch (27.3K, ../../CAD21AoCnjxfAcinbh5hK=p5tav3Sxq1UdvDdMqqO4-i2QpjQtA@mail.gmail.com/2-000_quorum_commit_v8.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index d8d207e..4baff32 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3032,42 +3032,76 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
- <literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ ANY | FIRST ] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servers.
</para>
<para>
- The second syntax was used before <productname>PostgreSQL</>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from the <literal>num_sync</> standbys with highest priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by the three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ three standbys among the four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name including those words must use double quotes.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
- </para>
+ with <literal>FIRST</> and <literal>num_sync</replaceable> equal to
+ 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
+ </para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this
+ parameter behaves as if <literal>ANY</> is used. Note that this
+ grammar is incompatible with <productname>PostgresSQL</> 9.6 which
+ is first version supporting multiple standbys with synchronous
+ replication, where no such keyword <literal>FIRST</> or
+ <literal>ANY</> can be used. Note that the grammer behaves as if
+ <literal>FIRST</> is used, which is incompatible with the post-9.6
+ version behavior.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 5bedaf2..b57b4ca 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1161,6 +1161,19 @@ synchronous_standby_names = '2 (s1, s2, s3)'
<literal>s2</> fails. <literal>s4</> is an asynchronous standby since
its name is not in the list.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys
+ <literal>s1</>, <literal>s2</> and <literal>s3</> will be considered as
+ synchronous standby candidates. The master server will wait for at least
+ 2 replies from them. <literal>s4</> is an asynchronous standby since its
+ name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 3de489e..2c5f3de 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1389,7 +1389,8 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<row>
<entry><structfield>sync_state</></entry>
<entry><type>text</></entry>
- <entry>Synchronous state of this standby server</entry>
+ <entry>Synchronous state of this standby server. It is <literal>quorum</>
+ when standby is considered as a candidate of quorum commit.</entry>
</row>
</tbody>
</tgroup>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..26f04e8 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,19 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are specified
+ * in synchronous_standby_names. This parameter also specifies a list
+ * of standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the standbys
+ * whose names appear earlier in the list are given higher priority
+ * and will be considered as synchronous. Other standby servers appearing
+ * later in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, all standbys appearing in the list are considered
+ * as candidates for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +76,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +392,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +419,12 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the flush
+ * apply and write LSN positions among all sync standbys using the
+ * method specified.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr,
+ &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +442,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +478,55 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys using according to synchronous method,
+ * or NIL if no sync standby is connected.
+ *
+ * The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ "incorrect synchronization method for standbys is specified \"%d\"",
+ SyncRepConfig->sync_method));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, the oldest flush, apply and write positions among
+ * all the sync standbys are calculated. In quorum method, in order to
+ * select the subset of standbys in the existing quorum set that will
+ * satisfy the conditions to be selected as synchronous, calculate the
+ * N-th newest flush, apply and write positions. In the latter case,
+ * the N-th element is defined by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -508,46 +553,145 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
+ * Switch through the calculation methods.
*/
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ {
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th newest Write, Flush, Apply positions specified by
+ * SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
+ else
+ elog(ERROR, "incorrect synchronization method for standbys");
list_free(sync_standbys);
return true;
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or NIL if no sync
+ * standby is connected. So this function returns the list of standbys except
+ * for the standbys which are not active or connected as asynchronous
+ * standbys.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as synchronous candidate and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +704,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1030,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..403fd7d 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,14 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index aa42d59..8d29dc4 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2862,10 +2862,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are
+ * considered as a candidate of quorum commit, state is always
+ * set to 'quorum' for all the standbys.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ values[7] = CStringGetTextDatum("quorum");
else if (list_member_int(sync_standbys, i))
values[7] = CStringGetTextDatum("sync");
else
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..8dd74a3 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..13978bb 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'FIRST 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'FIRST 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'FIRST 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'FIRST 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,33 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check state of a quorum set made of two standbys with an asynchronous
+# standby.
+test_sync_state(
+ $node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+ 'quorum set of two standbys with one async standby',
+ 'ANY 2(standby1, standby2)');
+
+# Check that the state of standbys does not change when 'ANY' is omitted.
+test_sync_state(
+ $node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+ 'synchronization method definition omitted, switching to default quorum',
+ '2(standby1, standby2)');
+
+# Start standby3, which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that setting of 'ANY 2(*)' chooses all standbys as candidates for
+# quorum commit.
+test_sync_state(
+ $node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+ 'all standbys selected as candidates for quorum commit',
+ 'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-11-29 04:32 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
1 sibling, 0 replies; 267+ messages in thread
From: Michael Paquier @ 2016-11-29 04:32 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; Fujii Masao <[email protected]>; pgsql-hackers
On Mon, Nov 28, 2016 at 8:03 PM, Masahiko Sawada <[email protected]> wrote:
> On Sat, Nov 26, 2016 at 10:27 PM, Michael Paquier
> <[email protected]> wrote:
>> On Tue, Nov 15, 2016 at 7:08 PM, Masahiko Sawada <[email protected]> wrote:
>>> Attached latest version patch incorporated review comments. After more
>>> thought, I agree and changed the value of standby priority in quorum
>>> method so that it's not set 1 forcibly. The all standby priorities are
>>> 1 If s_s_names = 'ANY(*)'.
>>> Please review this patch.
>>
>> Sorry for my late reply. Here is my final lookup.
>
> Thank you for reviewing!
>
>> <synopsis>
>> -<replaceable class="parameter">num_sync</replaceable> ( <replaceable
>> class="parameter">standby_name</replaceable> [, ...] )
>> +[ANY] <replaceable class="parameter">num_sync</replaceable> (
>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>> +FIRST <replaceable class="parameter">num_sync</replaceable> (
>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>> <replaceable class="parameter">standby_name</replaceable> [, ...
>> This can just be replaced with [ ANY | FIRST ]. There is no need for
>> braces as the keyword is not mandatory.
>>
>> + is the name of a standby server.
>> + <literal>FIRST</> and <literal>ANY</> specify the method used by
>> + the master to control the standby servres.
>> </para>
>> s/servres/servers/.
>>
>> if (priority == 0)
>> values[7] = CStringGetTextDatum("async");
>> else if (list_member_int(sync_standbys, i))
>> - values[7] = CStringGetTextDatum("sync");
>> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
>> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
>> else
>> values[7] = CStringGetTextDatum("potential");
>> This can be simplified a bit as "quorum" is the state value for all
>> standbys with a non-zero priority when the method is set to
>> SYNC_REP_QUORUM:
>> if (priority == 0)
>> values[7] = CStringGetTextDatum("async");
>> + else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>> + values[7] = CStringGetTextDatum("quorum");
>> else if (list_member_int(sync_standbys, i))
>> values[7] = CStringGetTextDatum("sync");
>> else
>>
>> SyncRepConfig data is made external to syncrep.c with this patch as
>> walsender.c needs to look at the sync method in place, no complain
>> about that after considering if there could be a more elegant way to
>> do things without this change.
>
> Agreed.
>
>> While reviewing the patch, I have found a couple of incorrectly shaped
>> sentences, both in the docs and some comments. Attached is a new
>> version with this word-smithing. The patch is now switched as ready
>> for committer.
>
> Thanks. I found a typo in v7 patch, so attached latest v8 patch.
Moved patch to CF 2017-01, with same status "Ready for committer".
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-06 04:11 Fujii Masao <[email protected]>
parent: Masahiko Sawada <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-06 04:11 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Mon, Nov 28, 2016 at 8:03 PM, Masahiko Sawada <[email protected]> wrote:
> On Sat, Nov 26, 2016 at 10:27 PM, Michael Paquier
> <[email protected]> wrote:
>> On Tue, Nov 15, 2016 at 7:08 PM, Masahiko Sawada <[email protected]> wrote:
>>> Attached latest version patch incorporated review comments. After more
>>> thought, I agree and changed the value of standby priority in quorum
>>> method so that it's not set 1 forcibly. The all standby priorities are
>>> 1 If s_s_names = 'ANY(*)'.
>>> Please review this patch.
>>
>> Sorry for my late reply. Here is my final lookup.
>
> Thank you for reviewing!
>
>> <synopsis>
>> -<replaceable class="parameter">num_sync</replaceable> ( <replaceable
>> class="parameter">standby_name</replaceable> [, ...] )
>> +[ANY] <replaceable class="parameter">num_sync</replaceable> (
>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>> +FIRST <replaceable class="parameter">num_sync</replaceable> (
>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>> <replaceable class="parameter">standby_name</replaceable> [, ...
>> This can just be replaced with [ ANY | FIRST ]. There is no need for
>> braces as the keyword is not mandatory.
>>
>> + is the name of a standby server.
>> + <literal>FIRST</> and <literal>ANY</> specify the method used by
>> + the master to control the standby servres.
>> </para>
>> s/servres/servers/.
>>
>> if (priority == 0)
>> values[7] = CStringGetTextDatum("async");
>> else if (list_member_int(sync_standbys, i))
>> - values[7] = CStringGetTextDatum("sync");
>> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
>> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
>> else
>> values[7] = CStringGetTextDatum("potential");
>> This can be simplified a bit as "quorum" is the state value for all
>> standbys with a non-zero priority when the method is set to
>> SYNC_REP_QUORUM:
>> if (priority == 0)
>> values[7] = CStringGetTextDatum("async");
>> + else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>> + values[7] = CStringGetTextDatum("quorum");
>> else if (list_member_int(sync_standbys, i))
>> values[7] = CStringGetTextDatum("sync");
>> else
>>
>> SyncRepConfig data is made external to syncrep.c with this patch as
>> walsender.c needs to look at the sync method in place, no complain
>> about that after considering if there could be a more elegant way to
>> do things without this change.
>
> Agreed.
>
>> While reviewing the patch, I have found a couple of incorrectly shaped
>> sentences, both in the docs and some comments. Attached is a new
>> version with this word-smithing. The patch is now switched as ready
>> for committer.
>
> Thanks. I found a typo in v7 patch, so attached latest v8 patch.
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
In quorum commit, we need to calculate the N-th largest LSN from
M quorum synchronous standbys' LSN. N would be usually 1 - 3 and
M would be 1 - 10, I guess. You used the algorithm using qsort for
that calculation. But I'm not sure if that's enough effective algorithm
or not.
If M (i.e., number of quorum sync standbys) is enough large,
your choice would be good. But usually M seems not so large.
Thought?
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-06 09:57 Masahiko Sawada <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 2 replies; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-06 09:57 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 6, 2016 at 1:11 PM, Fujii Masao <[email protected]> wrote:
> On Mon, Nov 28, 2016 at 8:03 PM, Masahiko Sawada <[email protected]> wrote:
>> On Sat, Nov 26, 2016 at 10:27 PM, Michael Paquier
>> <[email protected]> wrote:
>>> On Tue, Nov 15, 2016 at 7:08 PM, Masahiko Sawada <[email protected]> wrote:
>>>> Attached latest version patch incorporated review comments. After more
>>>> thought, I agree and changed the value of standby priority in quorum
>>>> method so that it's not set 1 forcibly. The all standby priorities are
>>>> 1 If s_s_names = 'ANY(*)'.
>>>> Please review this patch.
>>>
>>> Sorry for my late reply. Here is my final lookup.
>>
>> Thank you for reviewing!
>>
>>> <synopsis>
>>> -<replaceable class="parameter">num_sync</replaceable> ( <replaceable
>>> class="parameter">standby_name</replaceable> [, ...] )
>>> +[ANY] <replaceable class="parameter">num_sync</replaceable> (
>>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>>> +FIRST <replaceable class="parameter">num_sync</replaceable> (
>>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>>> <replaceable class="parameter">standby_name</replaceable> [, ...
>>> This can just be replaced with [ ANY | FIRST ]. There is no need for
>>> braces as the keyword is not mandatory.
>>>
>>> + is the name of a standby server.
>>> + <literal>FIRST</> and <literal>ANY</> specify the method used by
>>> + the master to control the standby servres.
>>> </para>
>>> s/servres/servers/.
>>>
>>> if (priority == 0)
>>> values[7] = CStringGetTextDatum("async");
>>> else if (list_member_int(sync_standbys, i))
>>> - values[7] = CStringGetTextDatum("sync");
>>> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
>>> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
>>> else
>>> values[7] = CStringGetTextDatum("potential");
>>> This can be simplified a bit as "quorum" is the state value for all
>>> standbys with a non-zero priority when the method is set to
>>> SYNC_REP_QUORUM:
>>> if (priority == 0)
>>> values[7] = CStringGetTextDatum("async");
>>> + else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>>> + values[7] = CStringGetTextDatum("quorum");
>>> else if (list_member_int(sync_standbys, i))
>>> values[7] = CStringGetTextDatum("sync");
>>> else
>>>
>>> SyncRepConfig data is made external to syncrep.c with this patch as
>>> walsender.c needs to look at the sync method in place, no complain
>>> about that after considering if there could be a more elegant way to
>>> do things without this change.
>>
>> Agreed.
>>
>>> While reviewing the patch, I have found a couple of incorrectly shaped
>>> sentences, both in the docs and some comments. Attached is a new
>>> version with this word-smithing. The patch is now switched as ready
>>> for committer.
>>
>> Thanks. I found a typo in v7 patch, so attached latest v8 patch.
>
> + qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
> + qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
> + qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
>
> In quorum commit, we need to calculate the N-th largest LSN from
> M quorum synchronous standbys' LSN. N would be usually 1 - 3 and
> M would be 1 - 10, I guess. You used the algorithm using qsort for
> that calculation. But I'm not sure if that's enough effective algorithm
> or not.
>
> If M (i.e., number of quorum sync standbys) is enough large,
> your choice would be good. But usually M seems not so large.
>
Thank you for the comment.
One another possible idea is to use the partial selection sort[1],
which takes O(MN) time. Since this is more efficient if N is small
this would be better than qsort for this case. But I'm not sure that
we can see such a difference by result of performance measurement.
[1] https://en.wikipedia.org/wiki/Selection_algorithm#Partial_selection_sort
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-06 10:14 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
1 sibling, 0 replies; 267+ messages in thread
From: Michael Paquier @ 2016-12-06 10:14 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Fujii Masao <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 6, 2016 at 6:57 PM, Masahiko Sawada <[email protected]> wrote:
> On Tue, Dec 6, 2016 at 1:11 PM, Fujii Masao <[email protected]> wrote:
>> If M (i.e., number of quorum sync standbys) is enough large,
>> your choice would be good. But usually M seems not so large.
>>
>
> Thank you for the comment.
>
> One another possible idea is to use the partial selection sort[1],
> which takes O(MN) time. Since this is more efficient if N is small
> this would be better than qsort for this case. But I'm not sure that
> we can see such a difference by result of performance measurement.
>
> [1] https://en.wikipedia.org/wiki/Selection_algorithm#Partial_selection_sort
We'll begin to see a minimal performance impact when selecting a sync
standby across hundreds of them, which is less than say what 0.1% (or
less) of existing deployments are doing. The current approach taken
seems simple enough to be kept, and performance is not something to
worry much IMHO.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-07 03:32 Fujii Masao <[email protected]>
parent: Masahiko Sawada <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-07 03:32 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 6, 2016 at 6:57 PM, Masahiko Sawada <[email protected]> wrote:
> On Tue, Dec 6, 2016 at 1:11 PM, Fujii Masao <[email protected]> wrote:
>> On Mon, Nov 28, 2016 at 8:03 PM, Masahiko Sawada <[email protected]> wrote:
>>> On Sat, Nov 26, 2016 at 10:27 PM, Michael Paquier
>>> <[email protected]> wrote:
>>>> On Tue, Nov 15, 2016 at 7:08 PM, Masahiko Sawada <[email protected]> wrote:
>>>>> Attached latest version patch incorporated review comments. After more
>>>>> thought, I agree and changed the value of standby priority in quorum
>>>>> method so that it's not set 1 forcibly. The all standby priorities are
>>>>> 1 If s_s_names = 'ANY(*)'.
>>>>> Please review this patch.
>>>>
>>>> Sorry for my late reply. Here is my final lookup.
>>>
>>> Thank you for reviewing!
>>>
>>>> <synopsis>
>>>> -<replaceable class="parameter">num_sync</replaceable> ( <replaceable
>>>> class="parameter">standby_name</replaceable> [, ...] )
>>>> +[ANY] <replaceable class="parameter">num_sync</replaceable> (
>>>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>>>> +FIRST <replaceable class="parameter">num_sync</replaceable> (
>>>> <replaceable class="parameter">standby_name</replaceable> [, ...] )
>>>> <replaceable class="parameter">standby_name</replaceable> [, ...
>>>> This can just be replaced with [ ANY | FIRST ]. There is no need for
>>>> braces as the keyword is not mandatory.
>>>>
>>>> + is the name of a standby server.
>>>> + <literal>FIRST</> and <literal>ANY</> specify the method used by
>>>> + the master to control the standby servres.
>>>> </para>
>>>> s/servres/servers/.
>>>>
>>>> if (priority == 0)
>>>> values[7] = CStringGetTextDatum("async");
>>>> else if (list_member_int(sync_standbys, i))
>>>> - values[7] = CStringGetTextDatum("sync");
>>>> + values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
>>>> + CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
>>>> else
>>>> values[7] = CStringGetTextDatum("potential");
>>>> This can be simplified a bit as "quorum" is the state value for all
>>>> standbys with a non-zero priority when the method is set to
>>>> SYNC_REP_QUORUM:
>>>> if (priority == 0)
>>>> values[7] = CStringGetTextDatum("async");
>>>> + else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
>>>> + values[7] = CStringGetTextDatum("quorum");
>>>> else if (list_member_int(sync_standbys, i))
>>>> values[7] = CStringGetTextDatum("sync");
>>>> else
>>>>
>>>> SyncRepConfig data is made external to syncrep.c with this patch as
>>>> walsender.c needs to look at the sync method in place, no complain
>>>> about that after considering if there could be a more elegant way to
>>>> do things without this change.
>>>
>>> Agreed.
>>>
>>>> While reviewing the patch, I have found a couple of incorrectly shaped
>>>> sentences, both in the docs and some comments. Attached is a new
>>>> version with this word-smithing. The patch is now switched as ready
>>>> for committer.
>>>
>>> Thanks. I found a typo in v7 patch, so attached latest v8 patch.
>>
>> + qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
>> + qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
>> + qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
>>
>> In quorum commit, we need to calculate the N-th largest LSN from
>> M quorum synchronous standbys' LSN. N would be usually 1 - 3 and
>> M would be 1 - 10, I guess. You used the algorithm using qsort for
>> that calculation. But I'm not sure if that's enough effective algorithm
>> or not.
>>
>> If M (i.e., number of quorum sync standbys) is enough large,
>> your choice would be good. But usually M seems not so large.
>>
>
> Thank you for the comment.
>
> One another possible idea is to use the partial selection sort[1],
> which takes O(MN) time. Since this is more efficient if N is small
> this would be better than qsort for this case. But I'm not sure that
> we can see such a difference by result of performance measurement.
So, isn't it better to compare the performance of some algorithms and
confirm which is the best for quorum commit? Since this code is hot, i.e.,
can be very frequently executed, I'd like to avoid waste of cycle as much
as possible.
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-07 04:26 Michael Paquier <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 2 replies; 267+ messages in thread
From: Michael Paquier @ 2016-12-07 04:26 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Masahiko Sawada <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Wed, Dec 7, 2016 at 12:32 PM, Fujii Masao <[email protected]> wrote:
> So, isn't it better to compare the performance of some algorithms and
> confirm which is the best for quorum commit? Since this code is hot, i.e.,
> can be very frequently executed, I'd like to avoid waste of cycle as much
> as possible.
It seems to me that it would be simple enough to write a script to do
that to avoid any other noise: allocate an array with N random
elements, and fetch the M-th element from it after applying a sort
method. I highly doubt that you'd see much difference with a low
number of elements, now if you scale at a thousand standbys in a
quorum set you may surely see something :*)
Anybody willing to try out?
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-07 05:49 Kyotaro HORIGUCHI <[email protected]>
parent: Michael Paquier <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Kyotaro HORIGUCHI @ 2016-12-07 05:49 UTC (permalink / raw)
To: [email protected]; +Cc: [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; pgsql-hackers
At Wed, 7 Dec 2016 13:26:38 +0900, Michael Paquier <[email protected]> wrote in <CAB7nPqSyfsg=gHeqgXyzP0iGWvdyrXqnG-UENzfueaU=2m5-zg@mail.gmail.com>
> On Wed, Dec 7, 2016 at 12:32 PM, Fujii Masao <[email protected]> wrote:
> > So, isn't it better to compare the performance of some algorithms and
> > confirm which is the best for quorum commit? Since this code is hot, i.e.,
> > can be very frequently executed, I'd like to avoid waste of cycle as much
> > as possible.
>
> It seems to me that it would be simple enough to write a script to do
> that to avoid any other noise: allocate an array with N random
> elements, and fetch the M-th element from it after applying a sort
> method. I highly doubt that you'd see much difference with a low
> number of elements, now if you scale at a thousand standbys in a
> quorum set you may surely see something :*)
> Anybody willing to try out?
Aside from measurement of the two sorting methods, I'd like to
point out that quorum commit basically doesn't need
sorting. Counting comforming santdbys while scanning the
walsender(receiver) LSN list comparing with the target LSN is
O(n). Small refactoring of SyncRerpGetOldestSyncRecPtr would
enough to do that.
regards,
--
Kyotaro Horiguchi
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-07 07:05 Michael Paquier <[email protected]>
parent: Kyotaro HORIGUCHI <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-07 07:05 UTC (permalink / raw)
To: Kyotaro HORIGUCHI <[email protected]>; +Cc: Fujii Masao <[email protected]>; [email protected]; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; [email protected]; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Wed, Dec 7, 2016 at 2:49 PM, Kyotaro HORIGUCHI
<[email protected]> wrote:
> Aside from measurement of the two sorting methods, I'd like to
> point out that quorum commit basically doesn't need
> sorting. Counting conforming santdbys while scanning the
> walsender(receiver) LSN list comparing with the target LSN is
> O(n). Small refactoring of SyncRerpGetOldestSyncRecPtr would
> enough to do that.
Indeed, I haven't thought about that, and that's a no-brainer. That
would remove the need to allocate and sort each array, what is simply
needed is to track the number of times a newest value has been found.
So what this processing would do is updating the write/flush/apply
values for the first k loops if the new value is *older* than the
current one, where k is the quorum number, and between k+1 and N the
value gets updated only if the value compared is newer. No need to
take the mutex lock for a long time as well. By the way, the patch now
conflicts on HEAD, it needs a refresh.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-07 08:17 Masahiko Sawada <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-07 08:17 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Kyotaro HORIGUCHI <[email protected]>; Fujii Masao <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Wed, Dec 7, 2016 at 4:05 PM, Michael Paquier
<[email protected]> wrote:
> On Wed, Dec 7, 2016 at 2:49 PM, Kyotaro HORIGUCHI
> <[email protected]> wrote:
>> Aside from measurement of the two sorting methods, I'd like to
>> point out that quorum commit basically doesn't need
>> sorting. Counting conforming santdbys while scanning the
>> walsender(receiver) LSN list comparing with the target LSN is
>> O(n). Small refactoring of SyncRerpGetOldestSyncRecPtr would
>> enough to do that.
What does the target LSN mean here?
> Indeed, I haven't thought about that, and that's a no-brainer. That
> would remove the need to allocate and sort each array, what is simply
> needed is to track the number of times a newest value has been found.
> So what this processing would do is updating the write/flush/apply
> values for the first k loops if the new value is *older* than the
> current one, where k is the quorum number, and between k+1 and N the
> value gets updated only if the value compared is newer. No need to
> take the mutex lock for a long time as well.
Sorry, I could not understand this algorithm. Could you elaborate
this? It takes only O(n) times?
> By the way, the patch now
> conflicts on HEAD, it needs a refresh.
Thanks, I'll post the latest patch.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-07 10:04 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-07 10:04 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Kyotaro HORIGUCHI <[email protected]>; Fujii Masao <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Wed, Dec 7, 2016 at 5:17 PM, Masahiko Sawada <[email protected]> wrote:
> On Wed, Dec 7, 2016 at 4:05 PM, Michael Paquier
> <[email protected]> wrote:
>> Indeed, I haven't thought about that, and that's a no-brainer. That
>> would remove the need to allocate and sort each array, what is simply
>> needed is to track the number of times a newest value has been found.
>> So what this processing would do is updating the write/flush/apply
>> values for the first k loops if the new value is *older* than the
>> current one, where k is the quorum number, and between k+1 and N the
>> value gets updated only if the value compared is newer. No need to
>> take the mutex lock for a long time as well.
>
> Sorry, I could not understand this algorithm. Could you elaborate
> this? It takes only O(n) times?
Nah, please forget that, that was a random useless thought. There is
no way to be able to select the k-th element without knowing the
hierarchy induced by the others, which is what the partial sort would
help with here.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-08 00:07 Robert Haas <[email protected]>
parent: Michael Paquier <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Robert Haas @ 2016-12-08 00:07 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Fujii Masao <[email protected]>; Masahiko Sawada <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 6, 2016 at 11:26 PM, Michael Paquier
<[email protected]> wrote:
> On Wed, Dec 7, 2016 at 12:32 PM, Fujii Masao <[email protected]> wrote:
>> So, isn't it better to compare the performance of some algorithms and
>> confirm which is the best for quorum commit? Since this code is hot, i.e.,
>> can be very frequently executed, I'd like to avoid waste of cycle as much
>> as possible.
>
> It seems to me that it would be simple enough to write a script to do
> that to avoid any other noise: allocate an array with N random
> elements, and fetch the M-th element from it after applying a sort
> method. I highly doubt that you'd see much difference with a low
> number of elements, now if you scale at a thousand standbys in a
> quorum set you may surely see something :*)
> Anybody willing to try out?
You could do that, but first I would code up the simplest, cleanest
algorithm you can think of and see if it even shows up in a 'perf'
profile. Microbenchmarking is probably overkill here unless a problem
is visible on macrobenchmarks.
--
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-08 00:37 Kyotaro HORIGUCHI <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro HORIGUCHI @ 2016-12-08 00:37 UTC (permalink / raw)
To: [email protected]; +Cc: [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; pgsql-hackers
Hello, context switch was complete that time, sorry.
There's multiple "target LET"s. So we need kth-largest LTEs.
At Wed, 7 Dec 2016 19:04:23 +0900, Michael Paquier <[email protected]> wrote in <CAB7nPqR10OnEL5XxW1DVYvAXmtpEVNCMi=V-6Jb_9owFuY8aSg@mail.gmail.com>
> On Wed, Dec 7, 2016 at 5:17 PM, Masahiko Sawada <[email protected]> wrote:
> > Sorry, I could not understand this algorithm. Could you elaborate
> > this? It takes only O(n) times?
>
> Nah, please forget that, that was a random useless thought. There is
> no way to be able to select the k-th element without knowing the
> hierarchy induced by the others, which is what the partial sort would
> help with here.
So, let's consider for some cases,
- needing 3-quorum among 5 standbys.
There's no problem whatever make kth-largest we choose.
Of course qsorts are fine.
- needing 10 quorums among 100 standbys.
I'm not sure if there's any difference with 3/5.
- needing 10 quorums among 1000 standbys.
Obviously qsorts are doing too much. Any kind of kth-largest
algorithm should be involved. For instance quickselect with O(n
long n) - O(n) seems better in comparison to O(n log n) - O(n^2)
of qsort.
- needing 700 quorums among 1000 standbys.
I don't think this case is worth consider but kth-largest is
better even for this case.
If we don't 700/1000 is out of at least the current scope, I also
recommend to use kth-largest selection.
If not, the quorum calculation is triggered by every standby
reply message and the frequency of the calculation seems near to
the frequency of WAL-insertion for the worst case. (Right?) Even
the kth-largest takes too long time to have 1000 standys.
Maintining kth-largest in shared memory needs less CPU but leads
to more bad contention on the shared memory.
Inversely, we already have waiting LSNs of backends in procarray.
If we have another array in the order of waiting LSNs and having
a condition varialble on the number of comforming
walsenders. Every walsender can individually looking up it and
count it up. It might performs better but I'm not sure.
regards,
--
Kyotaro Horiguchi
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-08 07:39 Michael Paquier <[email protected]>
parent: Robert Haas <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-08 07:39 UTC (permalink / raw)
To: Robert Haas <[email protected]>; +Cc: Fujii Masao <[email protected]>; Masahiko Sawada <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 8, 2016 at 9:07 AM, Robert Haas <[email protected]> wrote:
> You could do that, but first I would code up the simplest, cleanest
> algorithm you can think of and see if it even shows up in a 'perf'
> profile. Microbenchmarking is probably overkill here unless a problem
> is visible on macrobenchmarks.
This is what I would go for! The current code is doing a simple thing:
select the Nth element using qsort() after scanning each WAL sender's
values. And I think that Sawada-san got it right. Even running on my
laptop a pgbench run with 10 sync standbys using a data set that fits
into memory, SyncRepGetOldestSyncRecPtr gets at most 0.04% of overhead
using perf top on a non-assert, non-debug build. Hash tables and
allocations get a far larger share. Using the patch,
SyncRepGetSyncRecPtr is at the same level with a quorum set of 10
nodes. Let's kick the ball for now. An extra patch could make things
better later on if that's worth it.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-08 09:32 Masahiko Sawada <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-08 09:32 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Robert Haas <[email protected]>; Fujii Masao <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 8, 2016 at 4:39 PM, Michael Paquier
<[email protected]> wrote:
> On Thu, Dec 8, 2016 at 9:07 AM, Robert Haas <[email protected]> wrote:
>> You could do that, but first I would code up the simplest, cleanest
>> algorithm you can think of and see if it even shows up in a 'perf'
>> profile. Microbenchmarking is probably overkill here unless a problem
>> is visible on macrobenchmarks.
>
> This is what I would go for! The current code is doing a simple thing:
> select the Nth element using qsort() after scanning each WAL sender's
> values. And I think that Sawada-san got it right. Even running on my
> laptop a pgbench run with 10 sync standbys using a data set that fits
> into memory, SyncRepGetOldestSyncRecPtr gets at most 0.04% of overhead
> using perf top on a non-assert, non-debug build. Hash tables and
> allocations get a far larger share. Using the patch,
> SyncRepGetSyncRecPtr is at the same level with a quorum set of 10
> nodes. Let's kick the ball for now. An extra patch could make things
> better later on if that's worth it.
Yeah, since the both K and N could be not large these algorithm takes
almost the same time. And current patch does simple thing. When we
need over 100 or 1000 replication node the optimization could be
required.
Attached latest v9 patch.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[text/x-diff] 000_quorum_commit_v9.patch (28.8K, ../../CAD21AoCdxaPqRj_qegqm-nb_ZZh=B+EVKqzkkbHg1CcD_44yng@mail.gmail.com/2-000_quorum_commit_v9.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 0fc4e57..bc67a99 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3054,42 +3054,75 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
- <literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ANY] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+FIRST <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servres.
</para>
<para>
- The second syntax was used before <productname>PostgreSQL</>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>, makes
+ transaction commit wait until WAL records are received from the
+ <literal>num_sync</> standbys with higher priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ any three standbys of four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name having these words are must be double-quoted.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
- </para>
+ with <literal>FIRST</> and <replaceable class="parameter">num_sync</replaceable>
+ equal to 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
+ </para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this parameter
+ behaves as if <literal>ANY</> is used. Note that this grammar is incompatible
+ with <productname>PostgresSQL</> 9.6 which is first version supporting multiple
+ standbys with synchronous replication, where no such keyword <literal>FIRST</>
+ or <literal>ANY</> can be used. Note that the grammer behaves as if <literal>FIRST</>
+ is used, which is incompatible with the post-9.6 version behavior.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 6b89507..26e3c4e 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1165,6 +1165,18 @@ synchronous_standby_names = '2 (s1, s2, s3)'
The synchronous states of standby servers can be viewed using
the <structname>pg_stat_replication</structname> view.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys <literal>s1</>,
+ <literal>s2</> and <literal>s3</> will be considered as synchronous standby
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 128ee13..771787d 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1437,6 +1437,11 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<literal>sync</>: This standby server is synchronous.
</para>
</listitem>
+ <listitem>
+ <para>
+ <literal>quorum</>: This standby is considered as a candidate of quorum commit.
+ </para>
+ </listitem>
</itemizedlist>
</entry>
</row>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..bcc1317 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,19 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are specified
+ * in synchronous_standby_names. This parameter also specifies a list
+ * of standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the standbys
+ * whose names appear earlier in the list are given higher priority
+ * and will be considered as synchronous. Other standby servers appearing
+ * later in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, the all standbys appearing in the list are
+ * considered as a candidate for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +76,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +392,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +419,10 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the synced
+ * positions among all sync standbys using method.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +440,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +476,50 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys using according to synchronous method,
+ * or NIL if no sync standby is connected. The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ "invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, we need the oldest these positions among sync
+ * standbys. In quorum method, we need the newest these positions
+ * specified by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -507,29 +545,74 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
return false;
}
- /*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
- */
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else /* SYNC_REP_QUORUM */
+ {
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th newest Write, Flush, Apply positions
+ * specified by SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
list_free(sync_standbys);
@@ -537,17 +620,66 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
+ * standbys except for the standbys which are not active, or connected
+ * as async.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as candidate of sync and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +692,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1018,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..403fd7d 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,14 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index aa42d59..28c3eba 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2862,12 +2862,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are considered as
+ * a candidate of quorum commit standby state is always 'quorum'.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
diff --git a/src/backend/utils/sort/tuplesort.c b/src/backend/utils/sort/tuplesort.c
index 46eecbf..3ad8186 100644
--- a/src/backend/utils/sort/tuplesort.c
+++ b/src/backend/utils/sort/tuplesort.c
@@ -2637,16 +2637,8 @@ mergeruns(Tuplesortstate *state)
}
/*
- * Allocate a new 'memtuples' array, for the heap. It will hold one tuple
- * from each input tape.
- */
- state->memtupsize = numInputTapes;
- state->memtuples = (SortTuple *) palloc(numInputTapes * sizeof(SortTuple));
- USEMEM(state, GetMemoryChunkSpace(state->memtuples));
-
- /*
- * Use all the remaining memory we have available for read buffers among
- * the input tapes.
+ * Use all the spare memory we have available for read buffers among the
+ * input tapes.
*
* We do this only after checking for the case that we produced only one
* initial run, because there is no need to use a large read buffer when
@@ -2669,9 +2661,17 @@ mergeruns(Tuplesortstate *state)
(state->availMem) / 1024, numInputTapes);
#endif
- state->read_buffer_size = Min(state->availMem / numInputTapes, 0);
+ state->read_buffer_size = state->availMem / numInputTapes;
USEMEM(state, state->availMem);
+ /*
+ * Allocate a new 'memtuples' array, for the heap. It will hold one tuple
+ * from each input tape.
+ */
+ state->memtupsize = numInputTapes;
+ state->memtuples = (SortTuple *) palloc(numInputTapes * sizeof(SortTuple));
+ USEMEM(state, GetMemoryChunkSpace(state->memtuples));
+
/* End of step D2: rewind all output tapes to prepare for merging */
for (tapenum = 0; tapenum < state->tapeRange; tapenum++)
LogicalTapeRewindForRead(state->tapeset, tapenum, state->read_buffer_size);
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..8dd74a3 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..c502d20 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'FIRST 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'FIRST 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'FIRST 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'FIRST 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,34 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check that the state of standbys listed as a voter are having
+# same priority when synchronous_standby_names uses quorum method.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'2 quorum and 1 async',
+'ANY 2(standby1, standby2)');
+
+# Check that state of standbys are not the same as the behaviour of that
+# 'ANY' is specified.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'not specify synchronization method',
+'2(standby1, standby2)');
+
+# Start Standby3 which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that set setting of 'ANY 2(*)' chooses all standbys as
+# voter.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+'all standbys are considered as candidates for quorum commit',
+'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-10 08:17 Amit Kapila <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Amit Kapila @ 2016-12-10 08:17 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Fujii Masao <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 8, 2016 at 3:02 PM, Masahiko Sawada <[email protected]> wrote:
> On Thu, Dec 8, 2016 at 4:39 PM, Michael Paquier
> <[email protected]> wrote:
>> On Thu, Dec 8, 2016 at 9:07 AM, Robert Haas <[email protected]> wrote:
>>> You could do that, but first I would code up the simplest, cleanest
>>> algorithm you can think of and see if it even shows up in a 'perf'
>>> profile. Microbenchmarking is probably overkill here unless a problem
>>> is visible on macrobenchmarks.
>>
>> This is what I would go for! The current code is doing a simple thing:
>> select the Nth element using qsort() after scanning each WAL sender's
>> values. And I think that Sawada-san got it right. Even running on my
>> laptop a pgbench run with 10 sync standbys using a data set that fits
>> into memory, SyncRepGetOldestSyncRecPtr gets at most 0.04% of overhead
>> using perf top on a non-assert, non-debug build. Hash tables and
>> allocations get a far larger share. Using the patch,
>> SyncRepGetSyncRecPtr is at the same level with a quorum set of 10
>> nodes. Let's kick the ball for now. An extra patch could make things
>> better later on if that's worth it.
>
> Yeah, since the both K and N could be not large these algorithm takes
> almost the same time. And current patch does simple thing. When we
> need over 100 or 1000 replication node the optimization could be
> required.
> Attached latest v9 patch.
>
Few comments:
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are specified
+ * in synchronous_standby_names. This parameter also specifies a list
+ * of standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the standbys
+ * whose names appear earlier in the list are given higher priority
+ * and will be considered as synchronous. Other standby servers appearing
+ * later in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, the all standbys appearing in the list are
+ * considered as a candidate for quorum commit.
In the above description, is priority method represented by FIRST and
quorum method by ANY in the synchronous_standby_names syntax? If so,
it might be better to write about it explicitly.
2.
--- a/src/backend/utils/sort/tuplesort.c
+++ b/src/backend/utils/sort/tuplesort.c
@@ -2637,16 +2637,8 @@ mergeruns(Tuplesortstate *state)
}
/*
- * Allocate a new 'memtuples' array, for the heap. It will hold one tuple
- * from each input tape.
- */
- state->memtupsize = numInputTapes;
- state->memtuples = (SortTuple *) palloc(numInputTapes * sizeof(SortTuple));
- USEMEM(state, GetMemoryChunkSpace(state->memtuples));
-
- /*
- * Use all the remaining memory we have available for read buffers among
- * the input tapes.
+ * Use all the spare memory we have available for read buffers among the
+ * input tapes.
This doesn't belong to this patch.
3.
+ * Return the list of sync standbys using according to synchronous method,
In above sentence, "using according" seems to either incomplete or wrong usage.
4.
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ "invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method));
Here, the error message doesn't seem to aligned and you might want to
use errmsg for the same.
5.
+ * In priority method, we need the oldest these positions among sync
+ * standbys. In quorum method, we need the newest these positions
+ * specified by SyncRepConfig->num_sync.
/oldest these/oldest of these
/newest these positions specified/newest of these positions as specified
Instead of newest, can we consider to use latest?
6.
+ int sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
Can't we use 1 or 2 bytes to store sync_method information?
--
With Regards,
Amit Kapila.
EnterpriseDB: http://www.enterprisedb.com
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-12 12:31 Masahiko Sawada <[email protected]>
parent: Amit Kapila <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-12 12:31 UTC (permalink / raw)
To: Amit Kapila <[email protected]>; +Cc: Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Fujii Masao <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Sat, Dec 10, 2016 at 5:17 PM, Amit Kapila <[email protected]> wrote:
> On Thu, Dec 8, 2016 at 3:02 PM, Masahiko Sawada <[email protected]> wrote:
>> On Thu, Dec 8, 2016 at 4:39 PM, Michael Paquier
>> <[email protected]> wrote:
>>> On Thu, Dec 8, 2016 at 9:07 AM, Robert Haas <[email protected]> wrote:
>>>> You could do that, but first I would code up the simplest, cleanest
>>>> algorithm you can think of and see if it even shows up in a 'perf'
>>>> profile. Microbenchmarking is probably overkill here unless a problem
>>>> is visible on macrobenchmarks.
>>>
>>> This is what I would go for! The current code is doing a simple thing:
>>> select the Nth element using qsort() after scanning each WAL sender's
>>> values. And I think that Sawada-san got it right. Even running on my
>>> laptop a pgbench run with 10 sync standbys using a data set that fits
>>> into memory, SyncRepGetOldestSyncRecPtr gets at most 0.04% of overhead
>>> using perf top on a non-assert, non-debug build. Hash tables and
>>> allocations get a far larger share. Using the patch,
>>> SyncRepGetSyncRecPtr is at the same level with a quorum set of 10
>>> nodes. Let's kick the ball for now. An extra patch could make things
>>> better later on if that's worth it.
>>
>> Yeah, since the both K and N could be not large these algorithm takes
>> almost the same time. And current patch does simple thing. When we
>> need over 100 or 1000 replication node the optimization could be
>> required.
>> Attached latest v9 patch.
>>
>
> Few comments:
Thank you for reviewing.
> + * In 10.0 we support two synchronization methods, priority and
> + * quorum. The number of synchronous standbys that transactions
> + * must wait for replies from and synchronization method are specified
> + * in synchronous_standby_names. This parameter also specifies a list
> + * of standby names, which determines the priority of each standby for
> + * being chosen as a synchronous standby. In priority method, the standbys
> + * whose names appear earlier in the list are given higher priority
> + * and will be considered as synchronous. Other standby servers appearing
> + * later in this list represent potential synchronous standbys. If any of
> + * the current synchronous standbys disconnects for whatever reason,
> + * it will be replaced immediately with the next-highest-priority standby.
> + * In quorum method, the all standbys appearing in the list are
> + * considered as a candidate for quorum commit.
>
> In the above description, is priority method represented by FIRST and
> quorum method by ANY in the synchronous_standby_names syntax? If so,
> it might be better to write about it explicitly.
Added description.
>
> 2.
> --- a/src/backend/utils/sort/tuplesort.c
> +++ b/src/backend/utils/sort/tuplesort.c
> @@ -2637,16 +2637,8 @@ mergeruns(Tuplesortstate *state)
> }
>
> /*
> - * Allocate a new 'memtuples' array, for the heap. It will hold one tuple
> - * from each input tape.
> - */
> - state->memtupsize = numInputTapes;
> - state->memtuples = (SortTuple *) palloc(numInputTapes * sizeof(SortTuple));
> - USEMEM(state, GetMemoryChunkSpace(state->memtuples));
> -
> - /*
> - * Use all the remaining memory we have available for read buffers among
> - * the input tapes.
> + * Use all the spare memory we have available for read buffers among the
> + * input tapes.
>
> This doesn't belong to this patch.
Oops, fixed.
> 3.
> + * Return the list of sync standbys using according to synchronous method,
>
> In above sentence, "using according" seems to either incomplete or wrong usage.
Fixed.
> 4.
> + else
> + ereport(ERROR,
> + (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
> + "invalid synchronization method is specified \"%d\"",
> + SyncRepConfig->sync_method));
>
> Here, the error message doesn't seem to aligned and you might want to
> use errmsg for the same.
>
Fixed.
> 5.
> + * In priority method, we need the oldest these positions among sync
> + * standbys. In quorum method, we need the newest these positions
> + * specified by SyncRepConfig->num_sync.
>
> /oldest these/oldest of these
> /newest these positions specified/newest of these positions as specified
Fixed.
> Instead of newest, can we consider to use latest?
Yeah, I changed it so.
> 6.
> + int sync_method; /* synchronization method */
> /* member_names contains nmembers consecutive nul-terminated C strings */
> char member_names[FLEXIBLE_ARRAY_MEMBER];
> } SyncRepConfigData;
>
> Can't we use 1 or 2 bytes to store sync_method information?
I changed it to uint8.
Attached latest v10 patch incorporated the review comments so far.
Please review it.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[text/x-diff] 000_quorum_commit_v10.patch (27.2K, ../../CAD21AoD8nibM68vt1XBPFYd5ZU61m5D_Cp1rQqsEbH1kETR75A@mail.gmail.com/2-000_quorum_commit_v10.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 0fc4e57..bc67a99 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3054,42 +3054,75 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
- <literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ANY] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+FIRST <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servres.
</para>
<para>
- The second syntax was used before <productname>PostgreSQL</>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>, makes
+ transaction commit wait until WAL records are received from the
+ <literal>num_sync</> standbys with higher priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ any three standbys of four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name having these words are must be double-quoted.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
- </para>
+ with <literal>FIRST</> and <replaceable class="parameter">num_sync</replaceable>
+ equal to 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
+ </para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this parameter
+ behaves as if <literal>ANY</> is used. Note that this grammar is incompatible
+ with <productname>PostgresSQL</> 9.6 which is first version supporting multiple
+ standbys with synchronous replication, where no such keyword <literal>FIRST</>
+ or <literal>ANY</> can be used. Note that the grammer behaves as if <literal>FIRST</>
+ is used, which is incompatible with the post-9.6 version behavior.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 6b89507..26e3c4e 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1165,6 +1165,18 @@ synchronous_standby_names = '2 (s1, s2, s3)'
The synchronous states of standby servers can be viewed using
the <structname>pg_stat_replication</structname> view.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys <literal>s1</>,
+ <literal>s2</> and <literal>s3</> will be considered as synchronous standby
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 128ee13..771787d 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1437,6 +1437,11 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<literal>sync</>: This standby server is synchronous.
</para>
</listitem>
+ <listitem>
+ <para>
+ <literal>quorum</>: This standby is considered as a candidate of quorum commit.
+ </para>
+ </listitem>
</itemizedlist>
</entry>
</row>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..75649f1 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,21 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are
+ * specified in synchronous_standby_names. The priority method is
+ * represented by FIRST, and the quorum method is represented by ANY
+ * This parameter also specifies a list of standby names, which
+ * determines the priority of each standby for being chosen as a
+ * synchronous standby. In priority method, the standbys whose names
+ * appear earlier in the list are given higher priority and will be
+ * considered as synchronous. Other standby servers appearing later
+ * in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, the all standbys appearing in the list are
+ * considered as a candidate for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +78,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +394,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +421,10 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the synced
+ * positions among all sync standbys using method.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +442,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +478,50 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys according to synchronous method, or
+ * reutrn NIL if no sync standby is connected. The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method)));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, we need the oldest of these positions among sync
+ * standbys. In quorum method, we need the latest of these positions
+ * as specified by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -507,29 +547,74 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
return false;
}
- /*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
- */
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else /* SYNC_REP_QUORUM */
+ {
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th latest Write, Flush, Apply positions
+ * specified by SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
list_free(sync_standbys);
@@ -537,17 +622,66 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or return
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
+ * standbys except for the standbys which are not active, or connected
+ * as async.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as candidate of sync and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +694,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1020,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..403fd7d 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,14 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index aa42d59..28c3eba 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2862,12 +2862,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are considered as
+ * a candidate of quorum commit standby state is always 'quorum'.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..5ceb4b9 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int8 sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..e893ba0 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'FIRST 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'FIRST 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'FIRST 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'FIRST 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,34 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check that the state of standbys listed as a voter when the quroum
+# method is used.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'2 quorum and 1 async',
+'ANY 2(standby1, standby2)');
+
+# Check that state of standbys are not the same as the behaviour of that
+# 'ANY' is specified.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'not specify synchronization method',
+'2(standby1, standby2)');
+
+# Start Standby3 which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that set setting of 'ANY 2(*)' chooses all standbys as
+# voter.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+'all standbys are considered as candidates for quorum commit',
+'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-12 12:52 Fujii Masao <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-12 12:52 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Amit Kapila <[email protected]>; Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Mon, Dec 12, 2016 at 9:31 PM, Masahiko Sawada <[email protected]> wrote:
> On Sat, Dec 10, 2016 at 5:17 PM, Amit Kapila <[email protected]> wrote:
>> On Thu, Dec 8, 2016 at 3:02 PM, Masahiko Sawada <[email protected]> wrote:
>>> On Thu, Dec 8, 2016 at 4:39 PM, Michael Paquier
>>> <[email protected]> wrote:
>>>> On Thu, Dec 8, 2016 at 9:07 AM, Robert Haas <[email protected]> wrote:
>>>>> You could do that, but first I would code up the simplest, cleanest
>>>>> algorithm you can think of and see if it even shows up in a 'perf'
>>>>> profile. Microbenchmarking is probably overkill here unless a problem
>>>>> is visible on macrobenchmarks.
>>>>
>>>> This is what I would go for! The current code is doing a simple thing:
>>>> select the Nth element using qsort() after scanning each WAL sender's
>>>> values. And I think that Sawada-san got it right. Even running on my
>>>> laptop a pgbench run with 10 sync standbys using a data set that fits
>>>> into memory, SyncRepGetOldestSyncRecPtr gets at most 0.04% of overhead
>>>> using perf top on a non-assert, non-debug build. Hash tables and
>>>> allocations get a far larger share. Using the patch,
>>>> SyncRepGetSyncRecPtr is at the same level with a quorum set of 10
>>>> nodes. Let's kick the ball for now. An extra patch could make things
>>>> better later on if that's worth it.
>>>
>>> Yeah, since the both K and N could be not large these algorithm takes
>>> almost the same time. And current patch does simple thing. When we
>>> need over 100 or 1000 replication node the optimization could be
>>> required.
>>> Attached latest v9 patch.
>>>
>>
>> Few comments:
>
> Thank you for reviewing.
>
>> + * In 10.0 we support two synchronization methods, priority and
>> + * quorum. The number of synchronous standbys that transactions
>> + * must wait for replies from and synchronization method are specified
>> + * in synchronous_standby_names. This parameter also specifies a list
>> + * of standby names, which determines the priority of each standby for
>> + * being chosen as a synchronous standby. In priority method, the standbys
>> + * whose names appear earlier in the list are given higher priority
>> + * and will be considered as synchronous. Other standby servers appearing
>> + * later in this list represent potential synchronous standbys. If any of
>> + * the current synchronous standbys disconnects for whatever reason,
>> + * it will be replaced immediately with the next-highest-priority standby.
>> + * In quorum method, the all standbys appearing in the list are
>> + * considered as a candidate for quorum commit.
>>
>> In the above description, is priority method represented by FIRST and
>> quorum method by ANY in the synchronous_standby_names syntax? If so,
>> it might be better to write about it explicitly.
>
> Added description.
>
>>
>> 2.
>> --- a/src/backend/utils/sort/tuplesort.c
>> +++ b/src/backend/utils/sort/tuplesort.c
>> @@ -2637,16 +2637,8 @@ mergeruns(Tuplesortstate *state)
>> }
>>
>> /*
>> - * Allocate a new 'memtuples' array, for the heap. It will hold one tuple
>> - * from each input tape.
>> - */
>> - state->memtupsize = numInputTapes;
>> - state->memtuples = (SortTuple *) palloc(numInputTapes * sizeof(SortTuple));
>> - USEMEM(state, GetMemoryChunkSpace(state->memtuples));
>> -
>> - /*
>> - * Use all the remaining memory we have available for read buffers among
>> - * the input tapes.
>> + * Use all the spare memory we have available for read buffers among the
>> + * input tapes.
>>
>> This doesn't belong to this patch.
>
> Oops, fixed.
>
>> 3.
>> + * Return the list of sync standbys using according to synchronous method,
>>
>> In above sentence, "using according" seems to either incomplete or wrong usage.
>
> Fixed.
>
>> 4.
>> + else
>> + ereport(ERROR,
>> + (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
>> + "invalid synchronization method is specified \"%d\"",
>> + SyncRepConfig->sync_method));
>>
>> Here, the error message doesn't seem to aligned and you might want to
>> use errmsg for the same.
>>
>
> Fixed.
>
>> 5.
>> + * In priority method, we need the oldest these positions among sync
>> + * standbys. In quorum method, we need the newest these positions
>> + * specified by SyncRepConfig->num_sync.
>>
>> /oldest these/oldest of these
>> /newest these positions specified/newest of these positions as specified
>
> Fixed.
>
>> Instead of newest, can we consider to use latest?
>
> Yeah, I changed it so.
>
>
>> 6.
>> + int sync_method; /* synchronization method */
>> /* member_names contains nmembers consecutive nul-terminated C strings */
>> char member_names[FLEXIBLE_ARRAY_MEMBER];
>> } SyncRepConfigData;
>>
>> Can't we use 1 or 2 bytes to store sync_method information?
>
> I changed it to uint8.
>
> Attached latest v10 patch incorporated the review comments so far.
> Please review it.
Thanks for updating the patch!
Do we need to update postgresql.conf.sample?
+{any_ident} {
+ yylval.str = pstrdup(yytext);
+ return ANY;
+ }
+{first_ident} {
+ yylval.str = pstrdup(yytext);
+ return FIRST;
+ }
Why is pstrdup(yytext) necessary here?
+ standby_list { $$ =
create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ =
create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ =
create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ =
create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
Isn't this "partial" backward-compatibility (i.e., "NUM (list)" works
differently from curent version while "list" works in the same way as
current one) very confusing?
I prefer to either of
1. break the backward-compatibility, i.e., treat the first syntax of
"standby_list" as quorum commit
2. keep the backward-compatibility, i.e., treat the second syntax of
"NUM (standby_list)" as sync rep with the priority
+ <literal>pg_stat_replication</></link> view). If the keyword
+ <literal>FIRST</> is specified, other standby servers appearing
+ later in this list represent potential synchronous standbys.
+ If any of the current synchronous standbys disconnects for
+ whatever reason, it will be replaced immediately with the
+ next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
It seems strange to explain the behavior of FIRST before explaining
the syntax of synchronous_standby_names and FIRST.
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-12 16:24 Masahiko Sawada <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-12 16:24 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Amit Kapila <[email protected]>; Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Mon, Dec 12, 2016 at 9:52 PM, Fujii Masao <[email protected]> wrote:
> On Mon, Dec 12, 2016 at 9:31 PM, Masahiko Sawada <[email protected]> wrote:
>> On Sat, Dec 10, 2016 at 5:17 PM, Amit Kapila <[email protected]> wrote:
>>> On Thu, Dec 8, 2016 at 3:02 PM, Masahiko Sawada <[email protected]> wrote:
>>>> On Thu, Dec 8, 2016 at 4:39 PM, Michael Paquier
>>>> <[email protected]> wrote:
>>>>> On Thu, Dec 8, 2016 at 9:07 AM, Robert Haas <[email protected]> wrote:
>>>>>> You could do that, but first I would code up the simplest, cleanest
>>>>>> algorithm you can think of and see if it even shows up in a 'perf'
>>>>>> profile. Microbenchmarking is probably overkill here unless a problem
>>>>>> is visible on macrobenchmarks.
>>>>>
>>>>> This is what I would go for! The current code is doing a simple thing:
>>>>> select the Nth element using qsort() after scanning each WAL sender's
>>>>> values. And I think that Sawada-san got it right. Even running on my
>>>>> laptop a pgbench run with 10 sync standbys using a data set that fits
>>>>> into memory, SyncRepGetOldestSyncRecPtr gets at most 0.04% of overhead
>>>>> using perf top on a non-assert, non-debug build. Hash tables and
>>>>> allocations get a far larger share. Using the patch,
>>>>> SyncRepGetSyncRecPtr is at the same level with a quorum set of 10
>>>>> nodes. Let's kick the ball for now. An extra patch could make things
>>>>> better later on if that's worth it.
>>>>
>>>> Yeah, since the both K and N could be not large these algorithm takes
>>>> almost the same time. And current patch does simple thing. When we
>>>> need over 100 or 1000 replication node the optimization could be
>>>> required.
>>>> Attached latest v9 patch.
>>>>
>>>
>>> Few comments:
>>
>> Thank you for reviewing.
>>
>>> + * In 10.0 we support two synchronization methods, priority and
>>> + * quorum. The number of synchronous standbys that transactions
>>> + * must wait for replies from and synchronization method are specified
>>> + * in synchronous_standby_names. This parameter also specifies a list
>>> + * of standby names, which determines the priority of each standby for
>>> + * being chosen as a synchronous standby. In priority method, the standbys
>>> + * whose names appear earlier in the list are given higher priority
>>> + * and will be considered as synchronous. Other standby servers appearing
>>> + * later in this list represent potential synchronous standbys. If any of
>>> + * the current synchronous standbys disconnects for whatever reason,
>>> + * it will be replaced immediately with the next-highest-priority standby.
>>> + * In quorum method, the all standbys appearing in the list are
>>> + * considered as a candidate for quorum commit.
>>>
>>> In the above description, is priority method represented by FIRST and
>>> quorum method by ANY in the synchronous_standby_names syntax? If so,
>>> it might be better to write about it explicitly.
>>
>> Added description.
>>
>>>
>>> 2.
>>> --- a/src/backend/utils/sort/tuplesort.c
>>> +++ b/src/backend/utils/sort/tuplesort.c
>>> @@ -2637,16 +2637,8 @@ mergeruns(Tuplesortstate *state)
>>> }
>>>
>>> /*
>>> - * Allocate a new 'memtuples' array, for the heap. It will hold one tuple
>>> - * from each input tape.
>>> - */
>>> - state->memtupsize = numInputTapes;
>>> - state->memtuples = (SortTuple *) palloc(numInputTapes * sizeof(SortTuple));
>>> - USEMEM(state, GetMemoryChunkSpace(state->memtuples));
>>> -
>>> - /*
>>> - * Use all the remaining memory we have available for read buffers among
>>> - * the input tapes.
>>> + * Use all the spare memory we have available for read buffers among the
>>> + * input tapes.
>>>
>>> This doesn't belong to this patch.
>>
>> Oops, fixed.
>>
>>> 3.
>>> + * Return the list of sync standbys using according to synchronous method,
>>>
>>> In above sentence, "using according" seems to either incomplete or wrong usage.
>>
>> Fixed.
>>
>>> 4.
>>> + else
>>> + ereport(ERROR,
>>> + (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
>>> + "invalid synchronization method is specified \"%d\"",
>>> + SyncRepConfig->sync_method));
>>>
>>> Here, the error message doesn't seem to aligned and you might want to
>>> use errmsg for the same.
>>>
>>
>> Fixed.
>>
>>> 5.
>>> + * In priority method, we need the oldest these positions among sync
>>> + * standbys. In quorum method, we need the newest these positions
>>> + * specified by SyncRepConfig->num_sync.
>>>
>>> /oldest these/oldest of these
>>> /newest these positions specified/newest of these positions as specified
>>
>> Fixed.
>>
>>> Instead of newest, can we consider to use latest?
>>
>> Yeah, I changed it so.
>>
>>
>>> 6.
>>> + int sync_method; /* synchronization method */
>>> /* member_names contains nmembers consecutive nul-terminated C strings */
>>> char member_names[FLEXIBLE_ARRAY_MEMBER];
>>> } SyncRepConfigData;
>>>
>>> Can't we use 1 or 2 bytes to store sync_method information?
>>
>> I changed it to uint8.
>>
>> Attached latest v10 patch incorporated the review comments so far.
>> Please review it.
>
> Thanks for updating the patch!
>
> Do we need to update postgresql.conf.sample?
Added description to postgresql.conf.sample.
> +{any_ident} {
> + yylval.str = pstrdup(yytext);
> + return ANY;
> + }
> +{first_ident} {
> + yylval.str = pstrdup(yytext);
> + return FIRST;
> + }
>
> Why is pstrdup(yytext) necessary here?
The first whole line was unnecessary actually. Removed.
> + standby_list { $$ =
> create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
> + | NUM '(' standby_list ')' { $$ =
> create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
> + | ANY NUM '(' standby_list ')' { $$ =
> create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
> + | FIRST NUM '(' standby_list ')' { $$ =
> create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
>
> Isn't this "partial" backward-compatibility (i.e., "NUM (list)" works
> differently from curent version while "list" works in the same way as
> current one) very confusing?
>
> I prefer to either of
>
> 1. break the backward-compatibility, i.e., treat the first syntax of
> "standby_list" as quorum commit
> 2. keep the backward-compatibility, i.e., treat the second syntax of
> "NUM (standby_list)" as sync rep with the priority
There were some comments when I proposed the quorum commit. If we do
#1 it breaks the backward-compatibility with 9.5 or before as well. I
don't think it's a good idea. On the other hand, if we do #2 then the
behaviour of s_s_name is 'NUM (standby_list)' == 'FIRST NUM
(standby_list)''. But it would not what most of user will want and
would confuse the users of future version who will want to use the
quorum commit. Since many hackers thought that the sensible default
behaviour is 'NUM (standby_list)' == 'ANY NUM (standby_list)' the
current patch chose to changes the behaviour of s_s_names and document
that changes thoroughly.
> + <literal>pg_stat_replication</></link> view). If the keyword
> + <literal>FIRST</> is specified, other standby servers appearing
> + later in this list represent potential synchronous standbys.
> + If any of the current synchronous standbys disconnects for
> + whatever reason, it will be replaced immediately with the
> + next-highest-priority standby. Specifying more than one standby
> + name can allow very high availability.
>
> It seems strange to explain the behavior of FIRST before explaining
> the syntax of synchronous_standby_names and FIRST.
>
Updated document.
Attached latest v11 patch.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[application/octet-stream] 000_quorum_commit_v11.patch (27.9K, ../../CAD21AoBqgOvUX_mdKu6GNDkB57Ch4E1SBO-b-3YEhErw0iVrug@mail.gmail.com/2-000_quorum_commit_v11.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 0fc4e57..8bc8cd9 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3054,42 +3054,77 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
<literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[ANY] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+FIRST <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
- </para>
- <para>
- The second syntax was used before <productname>PostgreSQL</>
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servres.
+ </para>
+ <para>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>, makes
+ transaction commit wait until WAL records are received from the
+ <literal>num_sync</> standbys with higher priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ The other standby servers appearing later in list represent potential
+ synchronous standbys. If any of the current synchronous standbys
+ disconnects for whatever reason, it will be replaced immediately
+ with the next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ any three standbys of four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>. The transaction
+ can continue to proceed as long as <literal>num_sync</> standbys
+ live. Specifying more than one standby name can allow very high
+ availability.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name having these words are must be double-quoted.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
+ with <literal>FIRST</> and <replaceable class="parameter">num_sync</replaceable>
+ equal to 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
</para>
+ <note>
+ <para>
+ If <literal>FIRST</> or <literal>ANY</> are not specified, this parameter
+ behaves as if <literal>ANY</> is used. Note that this grammar is incompatible
+ with <productname>PostgresSQL</> 9.6 which is first version supporting multiple
+ standbys with synchronous replication, where no such keyword <literal>FIRST</>
+ or <literal>ANY</> can be used. Note that the grammer behaves as if <literal>FIRST</>
+ is used, which is incompatible with the post-9.6 version behavior.
+ </para>
+ </note>
<para>
The name of a standby server for this purpose is the
<varname>application_name</> setting of the standby, as set in the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 6b89507..26e3c4e 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1165,6 +1165,18 @@ synchronous_standby_names = '2 (s1, s2, s3)'
The synchronous states of standby servers can be viewed using
the <structname>pg_stat_replication</structname> view.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys <literal>s1</>,
+ <literal>s2</> and <literal>s3</> will be considered as synchronous standby
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 128ee13..771787d 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1437,6 +1437,11 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<literal>sync</>: This standby server is synchronous.
</para>
</listitem>
+ <listitem>
+ <para>
+ <literal>quorum</>: This standby is considered as a candidate of quorum commit.
+ </para>
+ </listitem>
</itemizedlist>
</entry>
</row>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..75649f1 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,21 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are
+ * specified in synchronous_standby_names. The priority method is
+ * represented by FIRST, and the quorum method is represented by ANY
+ * This parameter also specifies a list of standby names, which
+ * determines the priority of each standby for being chosen as a
+ * synchronous standby. In priority method, the standbys whose names
+ * appear earlier in the list are given higher priority and will be
+ * considered as synchronous. Other standby servers appearing later
+ * in this list represent potential synchronous standbys. If any of
+ * the current synchronous standbys disconnects for whatever reason,
+ * it will be replaced immediately with the next-highest-priority standby.
+ * In quorum method, the all standbys appearing in the list are
+ * considered as a candidate for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +78,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +394,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +421,10 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the synced
+ * positions among all sync standbys using method.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +442,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +478,50 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys according to synchronous method, or
+ * reutrn NIL if no sync standby is connected. The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method)));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, we need the oldest of these positions among sync
+ * standbys. In quorum method, we need the latest of these positions
+ * as specified by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -507,29 +547,74 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
return false;
}
- /*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
- */
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
+ }
+ else /* SYNC_REP_QUORUM */
+ {
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th latest Write, Flush, Apply positions
+ * specified by SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
}
list_free(sync_standbys);
@@ -537,17 +622,66 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or return
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
+ * standbys except for the standbys which are not active, or connected
+ * as async.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as candidate of sync and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +694,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1020,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..e10be8b 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, int sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -77,7 +79,7 @@ standby_name:
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, int sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +100,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..c08e95b 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,8 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} { return ANY; }
+{first_ident} { return FIRST; }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index b14d821..83f4e7c 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2868,12 +2868,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are considered as
+ * a candidate of quorum commit standby state is always 'quorum'.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index 7f9acfd..b332247 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -245,7 +245,8 @@
# These settings are ignored on a standby server.
#synchronous_standby_names = '' # standby servers that provide sync rep
- # number of sync standbys and comma-separated list of application_name
+ # synchronization method, number of sync standbys
+ # and comma-separated list of application_name
# from standby(s); '*' = all
#vacuum_defer_cleanup_age = 0 # number of xacts by which cleanup is delayed
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..5ceb4b9 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ int8 sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..e893ba0 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -107,7 +107,7 @@ test_sync_state(
$node_master, qq(standby2|2|sync
standby3|3|sync),
'2 synchronous standbys',
- '2(standby1,standby2,standby3)');
+ 'FIRST 2(standby1,standby2,standby3)');
# Start standby1
$node_standby_1->start;
@@ -138,7 +138,7 @@ standby2|4|sync
standby3|3|sync
standby4|1|sync),
'num_sync exceeds the num of potential sync standbys',
- '6(standby4,standby0,standby3,standby2)');
+ 'FIRST 6(standby4,standby0,standby3,standby2)');
# The setting that * comes before another standby name is acceptable
# but does not make sense in most cases. Check that sync_state is
@@ -150,7 +150,7 @@ standby2|2|sync
standby3|2|potential
standby4|2|potential),
'asterisk comes before another standby name',
- '2(standby1,*,standby2)');
+ 'FIRST 2(standby1,*,standby2)');
# Check that the setting of '2(*)' chooses standby2 and standby3 that are stored
# earlier in WalSnd array as sync standbys.
@@ -160,7 +160,7 @@ standby2|1|sync
standby3|1|sync
standby4|1|potential),
'multiple standbys having the same priority are chosen as sync',
- '2(*)');
+ 'FIRST 2(*)');
# Stop Standby3 which is considered in 'sync' state.
$node_standby_3->stop;
@@ -172,3 +172,34 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check that the state of standbys listed as a voter when the quroum
+# method is used.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'2 quorum and 1 async',
+'ANY 2(standby1, standby2)');
+
+# Check that state of standbys are not the same as the behaviour of that
+# 'ANY' is specified.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'not specify synchronization method',
+'2(standby1, standby2)');
+
+# Start Standby3 which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that set setting of 'ANY 2(*)' chooses all standbys as
+# voter.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+'all standbys are considered as candidates for quorum commit',
+'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-13 03:16 Amit Kapila <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Amit Kapila @ 2016-12-13 03:16 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Fujii Masao <[email protected]>; Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Mon, Dec 12, 2016 at 9:54 PM, Masahiko Sawada <[email protected]> wrote:
> On Mon, Dec 12, 2016 at 9:52 PM, Fujii Masao <[email protected]> wrote:
>> On Mon, Dec 12, 2016 at 9:31 PM, Masahiko Sawada <[email protected]> wrote:
>>> On Sat, Dec 10, 2016 at 5:17 PM, Amit Kapila <[email protected]> wrote:
>>>>
>>>> Few comments:
>>>
>>> Thank you for reviewing.
>>>
>>>> + * In 10.0 we support two synchronization methods, priority and
>>>> + * quorum. The number of synchronous standbys that transactions
>>>> + * must wait for replies from and synchronization method are specified
>>>> + * in synchronous_standby_names. This parameter also specifies a list
>>>> + * of standby names, which determines the priority of each standby for
>>>> + * being chosen as a synchronous standby. In priority method, the standbys
>>>> + * whose names appear earlier in the list are given higher priority
>>>> + * and will be considered as synchronous. Other standby servers appearing
>>>> + * later in this list represent potential synchronous standbys. If any of
>>>> + * the current synchronous standbys disconnects for whatever reason,
>>>> + * it will be replaced immediately with the next-highest-priority standby.
>>>> + * In quorum method, the all standbys appearing in the list are
>>>> + * considered as a candidate for quorum commit.
>>>>
>>>> In the above description, is priority method represented by FIRST and
>>>> quorum method by ANY in the synchronous_standby_names syntax? If so,
>>>> it might be better to write about it explicitly.
>>>
>>> Added description.
>>>
+ * specified in synchronous_standby_names. The priority method is
+ * represented by FIRST, and the quorum method is represented by ANY
Full stop is missing after "ANY".
>>>
>>>> 6.
>>>> + int sync_method; /* synchronization method */
>>>> /* member_names contains nmembers consecutive nul-terminated C strings */
>>>> char member_names[FLEXIBLE_ARRAY_MEMBER];
>>>> } SyncRepConfigData;
>>>>
>>>> Can't we use 1 or 2 bytes to store sync_method information?
>>>
>>> I changed it to uint8.
>>>
+ int8 sync_method; /* synchronization method */
> I changed it to uint8.
In mail, you have mentioned uint8, but in the code it is int8. I
think you want to update code to use uint8.
>
>> + standby_list { $$ =
>> create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
>> + | NUM '(' standby_list ')' { $$ =
>> create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
>> + | ANY NUM '(' standby_list ')' { $$ =
>> create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
>> + | FIRST NUM '(' standby_list ')' { $$ =
>> create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
>>
>> Isn't this "partial" backward-compatibility (i.e., "NUM (list)" works
>> differently from curent version while "list" works in the same way as
>> current one) very confusing?
>>
>> I prefer to either of
>>
>> 1. break the backward-compatibility, i.e., treat the first syntax of
>> "standby_list" as quorum commit
>> 2. keep the backward-compatibility, i.e., treat the second syntax of
>> "NUM (standby_list)" as sync rep with the priority
>
+1.
> There were some comments when I proposed the quorum commit. If we do
> #1 it breaks the backward-compatibility with 9.5 or before as well. I
> don't think it's a good idea. On the other hand, if we do #2 then the
> behaviour of s_s_name is 'NUM (standby_list)' == 'FIRST NUM
> (standby_list)''. But it would not what most of user will want and
> would confuse the users of future version who will want to use the
> quorum commit. Since many hackers thought that the sensible default
> behaviour is 'NUM (standby_list)' == 'ANY NUM (standby_list)' the
> current patch chose to changes the behaviour of s_s_names and document
> that changes thoroughly.
>
Your arguments are sensible, but I think we should address the point
of confusion raised by Fujii-san. As a developer, I feel breaking
backward compatibility (go with Option-1 mentioned above) here is a
good move as it can avoid confusions in future. However, I know many
a time users are so accustomed to the current usage that they feel
irritated with the change in behavior even it is for their betterment,
so it is advisable to do so only if it is necessary or we have
feedback from a couple of users. So in this case, if we don't want to
go with Option-1, then I think we should go with Option-2. If we go
with Option-2, then we can anyway comeback to change the behavior
which is more sensible for future after feedback from users.
--
With Regards,
Amit Kapila.
EnterpriseDB: http://www.enterprisedb.com
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-13 08:06 Kyotaro HORIGUCHI <[email protected]>
parent: Amit Kapila <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Kyotaro HORIGUCHI @ 2016-12-13 08:06 UTC (permalink / raw)
To: [email protected]; +Cc: [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; pgsql-hackers
At Tue, 13 Dec 2016 08:46:06 +0530, Amit Kapila <[email protected]> wrote in <CAA4eK1JoheFzO1rrKm391wJDepFvZr1geRh4ZJ_9iC4FOX+3Uw@mail.gmail.com>
> On Mon, Dec 12, 2016 at 9:54 PM, Masahiko Sawada <[email protected]> wrote:
> > On Mon, Dec 12, 2016 at 9:52 PM, Fujii Masao <[email protected]> wrote:
> >> On Mon, Dec 12, 2016 at 9:31 PM, Masahiko Sawada <[email protected]> wrote:
> >>> On Sat, Dec 10, 2016 at 5:17 PM, Amit Kapila <[email protected]> wrote:
> >>>>
> >>>> Few comments:
> >>>
> >>> Thank you for reviewing.
> >>>
> >>>> + * In 10.0 we support two synchronization methods, priority and
> >>>> + * quorum. The number of synchronous standbys that transactions
> >>>> + * must wait for replies from and synchronization method are specified
> >>>> + * in synchronous_standby_names. This parameter also specifies a list
> >>>> + * of standby names, which determines the priority of each standby for
> >>>> + * being chosen as a synchronous standby. In priority method, the standbys
> >>>> + * whose names appear earlier in the list are given higher priority
> >>>> + * and will be considered as synchronous. Other standby servers appearing
> >>>> + * later in this list represent potential synchronous standbys. If any of
> >>>> + * the current synchronous standbys disconnects for whatever reason,
> >>>> + * it will be replaced immediately with the next-highest-priority standby.
> >>>> + * In quorum method, the all standbys appearing in the list are
> >>>> + * considered as a candidate for quorum commit.
> >>>>
> >>>> In the above description, is priority method represented by FIRST and
> >>>> quorum method by ANY in the synchronous_standby_names syntax? If so,
> >>>> it might be better to write about it explicitly.
> >>>
> >>> Added description.
> >>>
>
> + * specified in synchronous_standby_names. The priority method is
> + * represented by FIRST, and the quorum method is represented by ANY
>
> Full stop is missing after "ANY".
>
> >>>
> >>>> 6.
> >>>> + int sync_method; /* synchronization method */
> >>>> /* member_names contains nmembers consecutive nul-terminated C strings */
> >>>> char member_names[FLEXIBLE_ARRAY_MEMBER];
> >>>> } SyncRepConfigData;
> >>>>
> >>>> Can't we use 1 or 2 bytes to store sync_method information?
> >>>
> >>> I changed it to uint8.
> >>>
>
> + int8 sync_method; /* synchronization method */
>
> > I changed it to uint8.
>
> In mail, you have mentioned uint8, but in the code it is int8. I
> think you want to update code to use uint8.
>
>
> >
> >> + standby_list { $$ =
> >> create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
> >> + | NUM '(' standby_list ')' { $$ =
> >> create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
> >> + | ANY NUM '(' standby_list ')' { $$ =
> >> create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
> >> + | FIRST NUM '(' standby_list ')' { $$ =
> >> create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
> >>
> >> Isn't this "partial" backward-compatibility (i.e., "NUM (list)" works
> >> differently from curent version while "list" works in the same way as
> >> current one) very confusing?
> >>
> >> I prefer to either of
> >>
> >> 1. break the backward-compatibility, i.e., treat the first syntax of
> >> "standby_list" as quorum commit
> >> 2. keep the backward-compatibility, i.e., treat the second syntax of
> >> "NUM (standby_list)" as sync rep with the priority
> >
>
> +1.
>
> > There were some comments when I proposed the quorum commit. If we do
> > #1 it breaks the backward-compatibility with 9.5 or before as well. I
> > don't think it's a good idea. On the other hand, if we do #2 then the
> > behaviour of s_s_name is 'NUM (standby_list)' == 'FIRST NUM
> > (standby_list)''. But it would not what most of user will want and
> > would confuse the users of future version who will want to use the
> > quorum commit. Since many hackers thought that the sensible default
> > behaviour is 'NUM (standby_list)' == 'ANY NUM (standby_list)' the
> > current patch chose to changes the behaviour of s_s_names and document
> > that changes thoroughly.
> >
>
> Your arguments are sensible, but I think we should address the point
> of confusion raised by Fujii-san. As a developer, I feel breaking
> backward compatibility (go with Option-1 mentioned above) here is a
> good move as it can avoid confusions in future. However, I know many
> a time users are so accustomed to the current usage that they feel
> irritated with the change in behavior even it is for their betterment,
> so it is advisable to do so only if it is necessary or we have
> feedback from a couple of users. So in this case, if we don't want to
> go with Option-1, then I think we should go with Option-2. If we go
> with Option-2, then we can anyway comeback to change the behavior
> which is more sensible for future after feedback from users.
This implicitly put an assumption that replication configuration
is defined by s_s_names. But in the past discussion, some people
suggested that quorum commit should be configured by another GUC
variable and I think it is the time to do this now.
So, we have the third option that would be like the following.
- s_s_names is restored to work in the way as of 9.5. or may
be the same as 9.6. Or immediately remove it! My inclination
is doing this.
- a new GUC varialbe such like "quorum_commit_standbys" (which
is exclusive to s_s_names) is defined for new version of
quorum commit feature. The option-1 except "standby_list"
format is usable in this.
This doesn't puzzle users who don't read release notes carefully
(ME?). Leaving s_s_names can save some of such users but I don't
think it is requried at Pg10.
regards,
--
Kyotaro Horiguchi
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-14 14:34 Fujii Masao <[email protected]>
parent: Kyotaro HORIGUCHI <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-14 14:34 UTC (permalink / raw)
To: Kyotaro HORIGUCHI <[email protected]>; +Cc: Amit Kapila <[email protected]>; Sawada Masahiko <[email protected]>; Michael Paquier <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 13, 2016 at 5:06 PM, Kyotaro HORIGUCHI
<[email protected]> wrote:
> At Tue, 13 Dec 2016 08:46:06 +0530, Amit Kapila <[email protected]> wrote in <CAA4eK1JoheFzO1rrKm391wJDepFvZr1geRh4ZJ_9iC4FOX+3Uw@mail.gmail.com>
>> On Mon, Dec 12, 2016 at 9:54 PM, Masahiko Sawada <[email protected]> wrote:
>> > On Mon, Dec 12, 2016 at 9:52 PM, Fujii Masao <[email protected]> wrote:
>> >> On Mon, Dec 12, 2016 at 9:31 PM, Masahiko Sawada <[email protected]> wrote:
>> >>> On Sat, Dec 10, 2016 at 5:17 PM, Amit Kapila <[email protected]> wrote:
>> >>>>
>> >>>> Few comments:
>> >>>
>> >>> Thank you for reviewing.
>> >>>
>> >>>> + * In 10.0 we support two synchronization methods, priority and
>> >>>> + * quorum. The number of synchronous standbys that transactions
>> >>>> + * must wait for replies from and synchronization method are specified
>> >>>> + * in synchronous_standby_names. This parameter also specifies a list
>> >>>> + * of standby names, which determines the priority of each standby for
>> >>>> + * being chosen as a synchronous standby. In priority method, the standbys
>> >>>> + * whose names appear earlier in the list are given higher priority
>> >>>> + * and will be considered as synchronous. Other standby servers appearing
>> >>>> + * later in this list represent potential synchronous standbys. If any of
>> >>>> + * the current synchronous standbys disconnects for whatever reason,
>> >>>> + * it will be replaced immediately with the next-highest-priority standby.
>> >>>> + * In quorum method, the all standbys appearing in the list are
>> >>>> + * considered as a candidate for quorum commit.
>> >>>>
>> >>>> In the above description, is priority method represented by FIRST and
>> >>>> quorum method by ANY in the synchronous_standby_names syntax? If so,
>> >>>> it might be better to write about it explicitly.
>> >>>
>> >>> Added description.
>> >>>
>>
>> + * specified in synchronous_standby_names. The priority method is
>> + * represented by FIRST, and the quorum method is represented by ANY
>>
>> Full stop is missing after "ANY".
>>
>> >>>
>> >>>> 6.
>> >>>> + int sync_method; /* synchronization method */
>> >>>> /* member_names contains nmembers consecutive nul-terminated C strings */
>> >>>> char member_names[FLEXIBLE_ARRAY_MEMBER];
>> >>>> } SyncRepConfigData;
>> >>>>
>> >>>> Can't we use 1 or 2 bytes to store sync_method information?
>> >>>
>> >>> I changed it to uint8.
>> >>>
>>
>> + int8 sync_method; /* synchronization method */
>>
>> > I changed it to uint8.
>>
>> In mail, you have mentioned uint8, but in the code it is int8. I
>> think you want to update code to use uint8.
>>
>>
>> >
>> >> + standby_list { $$ =
>> >> create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
>> >> + | NUM '(' standby_list ')' { $$ =
>> >> create_syncrep_config($1, $3, SYNC_REP_QUORUM); }
>> >> + | ANY NUM '(' standby_list ')' { $$ =
>> >> create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
>> >> + | FIRST NUM '(' standby_list ')' { $$ =
>> >> create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
>> >>
>> >> Isn't this "partial" backward-compatibility (i.e., "NUM (list)" works
>> >> differently from curent version while "list" works in the same way as
>> >> current one) very confusing?
>> >>
>> >> I prefer to either of
>> >>
>> >> 1. break the backward-compatibility, i.e., treat the first syntax of
>> >> "standby_list" as quorum commit
>> >> 2. keep the backward-compatibility, i.e., treat the second syntax of
>> >> "NUM (standby_list)" as sync rep with the priority
>> >
>>
>> +1.
>>
>> > There were some comments when I proposed the quorum commit. If we do
>> > #1 it breaks the backward-compatibility with 9.5 or before as well. I
>> > don't think it's a good idea. On the other hand, if we do #2 then the
>> > behaviour of s_s_name is 'NUM (standby_list)' == 'FIRST NUM
>> > (standby_list)''. But it would not what most of user will want and
>> > would confuse the users of future version who will want to use the
>> > quorum commit. Since many hackers thought that the sensible default
>> > behaviour is 'NUM (standby_list)' == 'ANY NUM (standby_list)' the
>> > current patch chose to changes the behaviour of s_s_names and document
>> > that changes thoroughly.
>> >
>>
>> Your arguments are sensible, but I think we should address the point
>> of confusion raised by Fujii-san. As a developer, I feel breaking
>> backward compatibility (go with Option-1 mentioned above) here is a
>> good move as it can avoid confusions in future. However, I know many
>> a time users are so accustomed to the current usage that they feel
>> irritated with the change in behavior even it is for their betterment,
>> so it is advisable to do so only if it is necessary or we have
>> feedback from a couple of users. So in this case, if we don't want to
>> go with Option-1, then I think we should go with Option-2. If we go
>> with Option-2, then we can anyway comeback to change the behavior
>> which is more sensible for future after feedback from users.
>
> This implicitly put an assumption that replication configuration
> is defined by s_s_names. But in the past discussion, some people
> suggested that quorum commit should be configured by another GUC
> variable and I think it is the time to do this now.
>
> So, we have the third option that would be like the following.
>
> - s_s_names is restored to work in the way as of 9.5. or may
> be the same as 9.6. Or immediately remove it! My inclination
> is doing this.
>
> - a new GUC varialbe such like "quorum_commit_standbys" (which
> is exclusive to s_s_names) is defined for new version of
> quorum commit feature. The option-1 except "standby_list"
> format is usable in this.
If we drop the "standby_list" syntax, I don't think that new parameter is
necessary. We can keep s_s_names and just drop the support for that syntax
from s_s_names. This may be ok if we're really in "break all the things" mode
for PostgreSQL 10.
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-14 21:47 Michael Paquier <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-14 21:47 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Sawada Masahiko <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Wed, Dec 14, 2016 at 11:34 PM, Fujii Masao <[email protected]> wrote:
> If we drop the "standby_list" syntax, I don't think that new parameter is
> necessary. We can keep s_s_names and just drop the support for that syntax
> from s_s_names. This may be ok if we're really in "break all the things" mode
> for PostgreSQL 10.
Please let's not raise that as an argument again... And not break the
s_list argument. Many users depend on that for just single sync
standbys. FWIW, I'd be in favor of backward compatibility and say that
a standby list is a priority list if we can maintain that. Upthread
agreement was to break that, I did not insist further, and won't if
that's still the feeling.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-15 02:04 Fujii Masao <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-15 02:04 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Sawada Masahiko <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 15, 2016 at 6:47 AM, Michael Paquier
<[email protected]> wrote:
> On Wed, Dec 14, 2016 at 11:34 PM, Fujii Masao <[email protected]> wrote:
>> If we drop the "standby_list" syntax, I don't think that new parameter is
>> necessary. We can keep s_s_names and just drop the support for that syntax
>> from s_s_names. This may be ok if we're really in "break all the things" mode
>> for PostgreSQL 10.
>
> Please let's not raise that as an argument again... And not break the
> s_list argument. Many users depend on that for just single sync
> standbys. FWIW, I'd be in favor of backward compatibility and say that
> a standby list is a priority list if we can maintain that. Upthread
> agreement was to break that, I did not insist further, and won't if
> that's still the feeling.
I wonder why you think that the backward-compatibility for standby_list is
so "special". We renamed pg_xlog directory to pg_wal and are planning to
change recovery.conf API at all, though they have bigger impacts on
the existing users in terms of the backward compatibility. OTOH, so far,
changing GUC between major releases happened several times.
But I'm not against keeping the backward compatibility for standby_list,
to be honest. My concern is that the latest patch tries to support
the backward compatibility "partially" and which would be confusing to users,
as I told upthread.
So I'd like to propose to keep the backward compatibility fully for s_s_names
(i.e., both "standby_list" and "N (standby_list)" mean the priority method)
at the first commit, then continue discussing this and change it if we reach
the consensus until PostgreSQL 10 is actually released. Thought?
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-15 02:23 Michael Paquier <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 2 replies; 267+ messages in thread
From: Michael Paquier @ 2016-12-15 02:23 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Sawada Masahiko <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 15, 2016 at 11:04 AM, Fujii Masao <[email protected]> wrote:
> On Thu, Dec 15, 2016 at 6:47 AM, Michael Paquier
> <[email protected]> wrote:
>> On Wed, Dec 14, 2016 at 11:34 PM, Fujii Masao <[email protected]> wrote:
>>> If we drop the "standby_list" syntax, I don't think that new parameter is
>>> necessary. We can keep s_s_names and just drop the support for that syntax
>>> from s_s_names. This may be ok if we're really in "break all the things" mode
>>> for PostgreSQL 10.
>>
>> Please let's not raise that as an argument again... And not break the
>> s_list argument. Many users depend on that for just single sync
>> standbys. FWIW, I'd be in favor of backward compatibility and say that
>> a standby list is a priority list if we can maintain that. Upthread
>> agreement was to break that, I did not insist further, and won't if
>> that's still the feeling.
>
> I wonder why you think that the backward-compatibility for standby_list is
> so "special". We renamed pg_xlog directory to pg_wal and are planning to
> change recovery.conf API at all, though they have bigger impacts on
> the existing users in terms of the backward compatibility. OTOH, so far,
> changing GUC between major releases happened several times.
Silent failures for existing failover deployments is a pain to solve
after doing upgrades. That's my only concern. Changing pg_wal would
result in a hard failure when upgrading. And changing the meaning of
the standby list (without keyword ANY or FIRST!) does not fall into
that category... So yes just removing support for standby list would
result in a hard failure, which would be fine for the
let-s-break-all-things move.
> But I'm not against keeping the backward compatibility for standby_list,
> to be honest. My concern is that the latest patch tries to support
> the backward compatibility "partially" and which would be confusing to users,
> as I told upthread.
If we try to support backward compatibility, I'd personally do it
fully, and have a list of standby names specified meaning a priority
list.
> So I'd like to propose to keep the backward compatibility fully for s_s_names
> (i.e., both "standby_list" and "N (standby_list)" mean the priority method)
> at the first commit, then continue discussing this and change it if we reach
> the consensus until PostgreSQL 10 is actually released. Thought?
+1 on that.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-15 05:13 Amit Kapila <[email protected]>
parent: Michael Paquier <[email protected]>
1 sibling, 0 replies; 267+ messages in thread
From: Amit Kapila @ 2016-12-15 05:13 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Fujii Masao <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Sawada Masahiko <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 15, 2016 at 7:53 AM, Michael Paquier
<[email protected]> wrote:
> On Thu, Dec 15, 2016 at 11:04 AM, Fujii Masao <[email protected]> wrote:
>> On Thu, Dec 15, 2016 at 6:47 AM, Michael Paquier
>> <[email protected]> wrote:
>
>> So I'd like to propose to keep the backward compatibility fully for s_s_names
>> (i.e., both "standby_list" and "N (standby_list)" mean the priority method)
>> at the first commit, then continue discussing this and change it if we reach
>> the consensus until PostgreSQL 10 is actually released. Thought?
>
> +1 on that.
>
+1. That is the safest option to proceed.
--
With Regards,
Amit Kapila.
EnterpriseDB: http://www.enterprisedb.com
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-15 05:20 Masahiko Sawada <[email protected]>
parent: Michael Paquier <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-15 05:20 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Fujii Masao <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 15, 2016 at 11:23 AM, Michael Paquier
<[email protected]> wrote:
> On Thu, Dec 15, 2016 at 11:04 AM, Fujii Masao <[email protected]> wrote:
>> On Thu, Dec 15, 2016 at 6:47 AM, Michael Paquier
>> <[email protected]> wrote:
>>> On Wed, Dec 14, 2016 at 11:34 PM, Fujii Masao <[email protected]> wrote:
>>>> If we drop the "standby_list" syntax, I don't think that new parameter is
>>>> necessary. We can keep s_s_names and just drop the support for that syntax
>>>> from s_s_names. This may be ok if we're really in "break all the things" mode
>>>> for PostgreSQL 10.
>>>
>>> Please let's not raise that as an argument again... And not break the
>>> s_list argument. Many users depend on that for just single sync
>>> standbys. FWIW, I'd be in favor of backward compatibility and say that
>>> a standby list is a priority list if we can maintain that. Upthread
>>> agreement was to break that, I did not insist further, and won't if
>>> that's still the feeling.
>>
>> I wonder why you think that the backward-compatibility for standby_list is
>> so "special". We renamed pg_xlog directory to pg_wal and are planning to
>> change recovery.conf API at all, though they have bigger impacts on
>> the existing users in terms of the backward compatibility. OTOH, so far,
>> changing GUC between major releases happened several times.
>
> Silent failures for existing failover deployments is a pain to solve
> after doing upgrades. That's my only concern. Changing pg_wal would
> result in a hard failure when upgrading. And changing the meaning of
> the standby list (without keyword ANY or FIRST!) does not fall into
> that category... So yes just removing support for standby list would
> result in a hard failure, which would be fine for the
> let-s-break-all-things move.
>
>> But I'm not against keeping the backward compatibility for standby_list,
>> to be honest. My concern is that the latest patch tries to support
>> the backward compatibility "partially" and which would be confusing to users,
>> as I told upthread.
> If we try to support backward compatibility, I'd personally do it
> fully, and have a list of standby names specified meaning a priority
> list.
>
>> So I'd like to propose to keep the backward compatibility fully for s_s_names
>> (i.e., both "standby_list" and "N (standby_list)" mean the priority method)
>> at the first commit, then continue discussing this and change it if we reach
>> the consensus until PostgreSQL 10 is actually released. Thought?
>
> +1 on that.
+1.
I'll update the patch.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-15 06:06 Kyotaro HORIGUCHI <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Kyotaro HORIGUCHI @ 2016-12-15 06:06 UTC (permalink / raw)
To: [email protected]; +Cc: [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; pgsql-hackers
At Thu, 15 Dec 2016 14:20:53 +0900, Masahiko Sawada <[email protected]> wrote in <CAD21AoDn73aC+o0mrWCs800LeOsMYP4oV7xVb0T0_4V5VCQzhQ@mail.gmail.com>
> On Thu, Dec 15, 2016 at 11:23 AM, Michael Paquier
> <[email protected]> wrote:
> > On Thu, Dec 15, 2016 at 11:04 AM, Fujii Masao <[email protected]> wrote:
> >> On Thu, Dec 15, 2016 at 6:47 AM, Michael Paquier
> >> <[email protected]> wrote:
> >>> On Wed, Dec 14, 2016 at 11:34 PM, Fujii Masao <[email protected]> wrote:
> >>>> If we drop the "standby_list" syntax, I don't think that new parameter is
> >>>> necessary. We can keep s_s_names and just drop the support for that syntax
> >>>> from s_s_names. This may be ok if we're really in "break all the things" mode
> >>>> for PostgreSQL 10.
> >>>
> >>> Please let's not raise that as an argument again... And not break the
> >>> s_list argument. Many users depend on that for just single sync
> >>> standbys. FWIW, I'd be in favor of backward compatibility and say that
> >>> a standby list is a priority list if we can maintain that. Upthread
> >>> agreement was to break that, I did not insist further, and won't if
> >>> that's still the feeling.
> >>
> >> I wonder why you think that the backward-compatibility for standby_list is
> >> so "special". We renamed pg_xlog directory to pg_wal and are planning to
> >> change recovery.conf API at all, though they have bigger impacts on
> >> the existing users in terms of the backward compatibility. OTOH, so far,
> >> changing GUC between major releases happened several times.
> >
> > Silent failures for existing failover deployments is a pain to solve
> > after doing upgrades. That's my only concern. Changing pg_wal would
> > result in a hard failure when upgrading. And changing the meaning of
> > the standby list (without keyword ANY or FIRST!) does not fall into
> > that category... So yes just removing support for standby list would
> > result in a hard failure, which would be fine for the
> > let-s-break-all-things move.
> >
> >> But I'm not against keeping the backward compatibility for standby_list,
> >> to be honest. My concern is that the latest patch tries to support
> >> the backward compatibility "partially" and which would be confusing to users,
> >> as I told upthread.
> > If we try to support backward compatibility, I'd personally do it
> > fully, and have a list of standby names specified meaning a priority
> > list.
> >
> >> So I'd like to propose to keep the backward compatibility fully for s_s_names
> >> (i.e., both "standby_list" and "N (standby_list)" mean the priority method)
> >> at the first commit, then continue discussing this and change it if we reach
> >> the consensus until PostgreSQL 10 is actually released. Thought?
> >
> > +1 on that.
>
> +1.
FWIW, +1 from me.
> I'll update the patch.
--
Kyotaro Horiguchi
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-15 09:08 Masahiko Sawada <[email protected]>
parent: Kyotaro HORIGUCHI <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-15 09:08 UTC (permalink / raw)
To: Kyotaro HORIGUCHI <[email protected]>; +Cc: Michael Paquier <[email protected]>; Fujii Masao <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 15, 2016 at 3:06 PM, Kyotaro HORIGUCHI
<[email protected]> wrote:
> At Thu, 15 Dec 2016 14:20:53 +0900, Masahiko Sawada <[email protected]> wrote in <CAD21AoDn73aC+o0mrWCs800LeOsMYP4oV7xVb0T0_4V5VCQzhQ@mail.gmail.com>
>> On Thu, Dec 15, 2016 at 11:23 AM, Michael Paquier
>> <[email protected]> wrote:
>> > On Thu, Dec 15, 2016 at 11:04 AM, Fujii Masao <[email protected]> wrote:
>> >> On Thu, Dec 15, 2016 at 6:47 AM, Michael Paquier
>> >> <[email protected]> wrote:
>> >>> On Wed, Dec 14, 2016 at 11:34 PM, Fujii Masao <[email protected]> wrote:
>> >>>> If we drop the "standby_list" syntax, I don't think that new parameter is
>> >>>> necessary. We can keep s_s_names and just drop the support for that syntax
>> >>>> from s_s_names. This may be ok if we're really in "break all the things" mode
>> >>>> for PostgreSQL 10.
>> >>>
>> >>> Please let's not raise that as an argument again... And not break the
>> >>> s_list argument. Many users depend on that for just single sync
>> >>> standbys. FWIW, I'd be in favor of backward compatibility and say that
>> >>> a standby list is a priority list if we can maintain that. Upthread
>> >>> agreement was to break that, I did not insist further, and won't if
>> >>> that's still the feeling.
>> >>
>> >> I wonder why you think that the backward-compatibility for standby_list is
>> >> so "special". We renamed pg_xlog directory to pg_wal and are planning to
>> >> change recovery.conf API at all, though they have bigger impacts on
>> >> the existing users in terms of the backward compatibility. OTOH, so far,
>> >> changing GUC between major releases happened several times.
>> >
>> > Silent failures for existing failover deployments is a pain to solve
>> > after doing upgrades. That's my only concern. Changing pg_wal would
>> > result in a hard failure when upgrading. And changing the meaning of
>> > the standby list (without keyword ANY or FIRST!) does not fall into
>> > that category... So yes just removing support for standby list would
>> > result in a hard failure, which would be fine for the
>> > let-s-break-all-things move.
>> >
>> >> But I'm not against keeping the backward compatibility for standby_list,
>> >> to be honest. My concern is that the latest patch tries to support
>> >> the backward compatibility "partially" and which would be confusing to users,
>> >> as I told upthread.
>> > If we try to support backward compatibility, I'd personally do it
>> > fully, and have a list of standby names specified meaning a priority
>> > list.
>> >
>> >> So I'd like to propose to keep the backward compatibility fully for s_s_names
>> >> (i.e., both "standby_list" and "N (standby_list)" mean the priority method)
>> >> at the first commit, then continue discussing this and change it if we reach
>> >> the consensus until PostgreSQL 10 is actually released. Thought?
>> >
>> > +1 on that.
>>
>> +1.
>
> FWIW, +1 from me.
>
>> I'll update the patch.
>
Attached latest v12 patch.
I changed behavior of "N (standby_list)" to use the priority method
and incorporated some review comments so far. Please review it.
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[text/x-diff] 000_quorum_commit_v12.patch (26.3K, ../../CAD21AoBBFkH3MXsZ25ROHXuLZTQnwvbGc1qjO7uqkC59v-_P8w@mail.gmail.com/2-000_quorum_commit_v12.patch)
download | inline diff:
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 0fc4e57..91eb888 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -3054,41 +3054,67 @@ include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
- earlier in this list, and
+ in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
<literal>pg_stat_replication</></link> view).
- Other standby servers appearing later in this list represent potential
- synchronous standbys. If any of the current synchronous
- standbys disconnects for whatever reason,
- it will be replaced immediately with the next-highest-priority standby.
- Specifying more than one standby name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
-<replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+[FIRST] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
+ANY <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
- is the name of a standby server. For example, a setting of
- <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
- until their WAL records are received by three higher-priority standbys
- chosen from standby servers <literal>s1</>, <literal>s2</>,
- <literal>s3</> and <literal>s4</>.
- </para>
- <para>
- The second syntax was used before <productname>PostgreSQL</>
+ is the name of a standby server.
+ <literal>FIRST</> and <literal>ANY</> specify the method used by
+ the master to control the standby servres.
+ </para>
+ <para>
+ The keyword <literal>FIRST</>, coupled with <literal>num_sync</>, makes
+ transaction commit wait until WAL records are received from the
+ <literal>num_sync</> standbys with higher priority number.
+ For example, a setting of <literal>FIRST 3 (s1, s2, s3, s4)</>
+ makes transaction commits wait until their WAL records are received
+ by three higher-priority standbys chosen from standby servers
+ <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
+ The other standby servers appearing later in list represent potential
+ synchronous standbys. If any of the current synchronous standbys
+ disconnects for whatever reason, it will be replaced immediately
+ with the next-highest-priority standby. Specifying more than one standby
+ name can allow very high availability. The keyword <literal>FIRST</>
+ is optional.
+ </para>
+ <para>
+ The keyword <literal>ANY</>, coupled with <literal>num_sync</>,
+ makes transaction commits wait until WAL records are received
+ from at least <literal>num_sync</> connected standbys among those
+ defined in the list of <varname>synchronous_standby_names</>. For
+ example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> makes
+ transaction commits wait until receiving WAL records from at least
+ any three standbys of four listed servers <literal>s1</>,
+ <literal>s2</>, <literal>s3</>, <literal>s4</>. The transaction
+ can continue to proceed as long as <literal>num_sync</> standbys
+ live. Specifying more than one standby name can allow very high
+ availability.
+ </para>
+ <para>
+ <literal>FIRST</> and <literal>ANY</> are case-insensitive words
+ and the standby name having these words are must be double-quoted.
+ </para>
+ <para>
+ The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
- with <replaceable class="parameter">num_sync</replaceable> equal to 1.
- For example, <literal>1 (s1, s2)</> and
- <literal>s1, s2</> have the same meaning: either <literal>s1</>
- or <literal>s2</> is chosen as a synchronous standby.
+ with <literal>FIRST</> and <replaceable class="parameter">num_sync</replaceable>
+ equal to 1. For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</>
+ have the same meaning: either <literal>s1</> or <literal>s2</> is
+ chosen as a synchronous standby.
</para>
<para>
The name of a standby server for this purpose is the
diff --git a/doc/src/sgml/high-availability.sgml b/doc/src/sgml/high-availability.sgml
index 6b89507..26e3c4e 100644
--- a/doc/src/sgml/high-availability.sgml
+++ b/doc/src/sgml/high-availability.sgml
@@ -1150,7 +1150,7 @@ primary_slot_name = 'node_a_slot'
An example of <varname>synchronous_standby_names</> for multiple
synchronous standbys is:
<programlisting>
-synchronous_standby_names = '2 (s1, s2, s3)'
+synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
@@ -1165,6 +1165,18 @@ synchronous_standby_names = '2 (s1, s2, s3)'
The synchronous states of standby servers can be viewed using
the <structname>pg_stat_replication</structname> view.
</para>
+ <para>
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
+<programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+</programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, the three standbys <literal>s1</>,
+ <literal>s2</> and <literal>s3</> will be considered as synchronous standby
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
</sect3>
<sect3 id="synchronous-replication-performance">
diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index 128ee13..771787d 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -1437,6 +1437,11 @@ SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<literal>sync</>: This standby server is synchronous.
</para>
</listitem>
+ <listitem>
+ <para>
+ <literal>quorum</>: This standby is considered as a candidate of quorum commit.
+ </para>
+ </listitem>
</itemizedlist>
</entry>
</row>
diff --git a/src/backend/replication/Makefile b/src/backend/replication/Makefile
index c99717e..da8bcf0 100644
--- a/src/backend/replication/Makefile
+++ b/src/backend/replication/Makefile
@@ -26,7 +26,7 @@ repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
-syncrep_scanner.c: FLEXFLAGS = -CF -p
+syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
diff --git a/src/backend/replication/syncrep.c b/src/backend/replication/syncrep.c
index ac29f56..1de796c 100644
--- a/src/backend/replication/syncrep.c
+++ b/src/backend/replication/syncrep.c
@@ -31,16 +31,21 @@
*
* In 9.5 or before only a single standby could be considered as
* synchronous. In 9.6 we support multiple synchronous standbys.
- * The number of synchronous standbys that transactions must wait for
- * replies from is specified in synchronous_standby_names.
- * This parameter also specifies a list of standby names,
- * which determines the priority of each standby for being chosen as
- * a synchronous standby. The standbys whose names appear earlier
- * in the list are given higher priority and will be considered as
- * synchronous. Other standby servers appearing later in this list
- * represent potential synchronous standbys. If any of the current
- * synchronous standbys disconnects for whatever reason, it will be
- * replaced immediately with the next-highest-priority standby.
+ * In 10.0 we support two synchronization methods, priority and
+ * quorum. The number of synchronous standbys that transactions
+ * must wait for replies from and synchronization method are
+ * specified in synchronous_standby_names. The priority method is
+ * represented by FIRST or nothing specified, and the quorum method
+ * is represented by ANY. This parameter also specifies a list of
+ * standby names, which determines the priority of each standby for
+ * being chosen as a synchronous standby. In priority method, the
+ * standbys whose names appear earlier in the list are given higher
+ * priority and will be considered as synchronous. Other standby
+ * servers appearing later in this list represent potential synchronous
+ * standbys. If any of the current synchronous standbys disconnects
+ * for whatever reason, it will be replaced immediately with the
+ * next-highest-priority standby. In quorum method, the all standbys
+ * appearing in the list are considered as a candidate for quorum commit.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
@@ -73,24 +78,27 @@
/* User-settable parameters for sync rep */
char *SyncRepStandbyNames;
+SyncRepConfigData *SyncRepConfig = NULL;
#define SyncStandbysDefined() \
(SyncRepStandbyNames != NULL && SyncRepStandbyNames[0] != '\0')
static bool announce_next_takeover = true;
-static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
-static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
- XLogRecPtr *flushPtr,
- XLogRecPtr *applyPtr,
- bool *am_sync);
+static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
+ XLogRecPtr *flushPtr,
+ XLogRecPtr *applyPtr,
+ bool *am_sync);
static int SyncRepGetStandbyPriority(void);
+static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
@@ -386,7 +394,7 @@ SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
- bool got_oldest;
+ bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
@@ -413,11 +421,10 @@ SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
- * Check whether we are a sync standby or not, and calculate the oldest
- * positions among all sync standbys.
+ * Check whether we are a sync standby or not, and calculate the synced
+ * positions among all sync standbys using method.
*/
- got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
- &applyPtr, &am_sync);
+ got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
@@ -435,7 +442,7 @@ SyncRepReleaseWaiters(void)
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
- if (!got_oldest || !am_sync)
+ if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
@@ -471,17 +478,50 @@ SyncRepReleaseWaiters(void)
}
/*
- * Calculate the oldest Write, Flush and Apply positions among sync standbys.
+ * Return the list of sync standbys according to synchronous method, or
+ * reutrn NIL if no sync standby is connected. The caller must hold SyncRepLock.
+ *
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+List *
+SyncRepGetSyncStandbys(bool *am_sync)
+{
+ /* Set default result */
+ if (am_sync != NULL)
+ *am_sync = false;
+
+ /* Quick exit if sync replication is not requested */
+ if (SyncRepConfig == NULL)
+ return NIL;
+
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
+ return SyncRepGetSyncStandbysPriority(am_sync);
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ return SyncRepGetSyncStandbysQuorum(am_sync);
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method)));
+}
+
+/*
+ * Calculate the Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
- * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
+ * store the positions into *writePtr, *flushPtr and *applyPtr.
+ *
+ * In priority method, we need the oldest of these positions among sync
+ * standbys. In quorum method, we need the latest of these positions
+ * as specified by SyncRepConfig->num_sync.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
-SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
+SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
@@ -507,47 +547,146 @@ SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
return false;
}
- /*
- * Scan through all sync standbys and calculate the oldest Write, Flush
- * and Apply positions.
- */
- foreach(cell, sync_standbys)
+ if (SyncRepConfig->sync_method == SYNC_REP_PRIORITY)
{
- WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
- XLogRecPtr write;
- XLogRecPtr flush;
- XLogRecPtr apply;
-
- SpinLockAcquire(&walsnd->mutex);
- write = walsnd->write;
- flush = walsnd->flush;
- apply = walsnd->apply;
- SpinLockRelease(&walsnd->mutex);
-
- if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
- *writePtr = write;
- if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
- *flushPtr = flush;
- if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
- *applyPtr = apply;
+ /*
+ * Scan through all sync standbys and calculate the oldest
+ * Write, Flush and Apply positions.
+ */
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+ XLogRecPtr write;
+ XLogRecPtr flush;
+ XLogRecPtr apply;
+
+ SpinLockAcquire(&walsnd->mutex);
+ write = walsnd->write;
+ flush = walsnd->flush;
+ apply = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ if (XLogRecPtrIsInvalid(*writePtr) || *writePtr > write)
+ *writePtr = write;
+ if (XLogRecPtrIsInvalid(*flushPtr) || *flushPtr > flush)
+ *flushPtr = flush;
+ if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
+ *applyPtr = apply;
+ }
}
+ else if (SyncRepConfig->sync_method == SYNC_REP_QUORUM)
+ {
+ XLogRecPtr *write_array;
+ XLogRecPtr *flush_array;
+ XLogRecPtr *apply_array;
+ int len;
+ int i = 0;
+
+ len = list_length(sync_standbys);
+ write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+ apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
+
+ foreach (cell, sync_standbys)
+ {
+ WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
+
+ SpinLockAcquire(&walsnd->mutex);
+ write_array[i] = walsnd->write;
+ flush_array[i] = walsnd->flush;
+ apply_array[i] = walsnd->apply;
+ SpinLockRelease(&walsnd->mutex);
+
+ i++;
+ }
+
+ qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
+ qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
+
+ /*
+ * Get N-th latest Write, Flush, Apply positions
+ * specified by SyncRepConfig->num_sync.
+ */
+ *writePtr = write_array[SyncRepConfig->num_sync - 1];
+ *flushPtr = flush_array[SyncRepConfig->num_sync - 1];
+ *applyPtr = apply_array[SyncRepConfig->num_sync - 1];
+
+ pfree(write_array);
+ pfree(flush_array);
+ pfree(apply_array);
+ }
+ else
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("invalid synchronization method is specified \"%d\"",
+ SyncRepConfig->sync_method)));
list_free(sync_standbys);
return true;
}
/*
- * Return the list of sync standbys, or NIL if no sync standby is connected.
+ * Return the list of sync standbys using quorum method, or return
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
+ * standbys except for the standbys which are not active, or connected
+ * as async.
*
- * If there are multiple standbys with the same priority,
+ * On return, *am_sync is set to true if this walsender is connecting to
+ * sync standby. Otherwise it's set to false.
+ */
+static List *
+SyncRepGetSyncStandbysQuorum(bool *am_sync)
+{
+ List *result = NIL;
+ int i;
+
+ Assert(SyncRepConfig->sync_method == SYNC_REP_QUORUM);
+
+ for (i = 0; i < max_wal_senders; i++)
+ {
+ volatile WalSnd *walsnd = &WalSndCtl->walsnds[i];
+
+ /* Must be active */
+ if (walsnd->pid == 0)
+ continue;
+
+ /* Must be streaming */
+ if (walsnd->state != WALSNDSTATE_STREAMING)
+ continue;
+
+ /* Must be synchronous */
+ if (walsnd->sync_standby_priority == 0)
+ continue;
+
+ /* Must have a valid flush position */
+ if (XLogRecPtrIsInvalid(walsnd->flush))
+ continue;
+
+ /*
+ * Consider this standby as candidate of sync and append
+ * it to the result.
+ */
+ result = lappend_int(result, i);
+ if (am_sync != NULL && walsnd == MyWalSnd)
+ *am_sync = true;
+ }
+
+ return result;
+}
+
+/*
+ * Return the list of sync standbys using priority method, or return
+ * NIL if no sync standby is connected. In priority method,
+ * if there are multiple standbys with the same priority,
* the first one found is selected preferentially.
- * The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
-List *
-SyncRepGetSyncStandbys(bool *am_sync)
+static List *
+SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
@@ -560,13 +699,7 @@ SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
- /* Set default result */
- if (am_sync != NULL)
- *am_sync = false;
-
- /* Quick exit if sync replication is not requested */
- if (SyncRepConfig == NULL)
- return NIL;
+ Assert(SyncRepConfig->sync_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
@@ -892,6 +1025,23 @@ SyncRepQueueIsOrderedByLSN(int mode)
#endif
/*
+ * Compare lsn in order to sort array in descending order.
+ */
+static int
+cmp_lsn(const void *a, const void *b)
+{
+ XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
+ XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
+
+ if (lsn1 > lsn2)
+ return -1;
+ else if (lsn1 == lsn2)
+ return 0;
+ else
+ return 1;
+}
+
+/*
* ===========================================================
* Synchronous Replication functions executed by any process
* ===========================================================
diff --git a/src/backend/replication/syncrep_gram.y b/src/backend/replication/syncrep_gram.y
index 35c2776..0ba7c4e 100644
--- a/src/backend/replication/syncrep_gram.y
+++ b/src/backend/replication/syncrep_gram.y
@@ -21,7 +21,7 @@ SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
- List *members);
+ List *members, uint8 sync_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
@@ -46,7 +46,7 @@ static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
-%token <str> NAME NUM JUNK
+%token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
@@ -60,8 +60,10 @@ result:
;
standby_config:
- standby_list { $$ = create_syncrep_config("1", $1); }
- | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
+ standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
+ | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_PRIORITY); }
+ | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
+ | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
@@ -75,9 +77,8 @@ standby_name:
;
%%
-
static SyncRepConfigData *
-create_syncrep_config(const char *num_sync, List *members)
+create_syncrep_config(const char *num_sync, List *members, uint8 sync_method)
{
SyncRepConfigData *config;
int size;
@@ -98,6 +99,7 @@ create_syncrep_config(const char *num_sync, List *members)
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->sync_method = sync_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
diff --git a/src/backend/replication/syncrep_scanner.l b/src/backend/replication/syncrep_scanner.l
index d20662e..c08e95b 100644
--- a/src/backend/replication/syncrep_scanner.l
+++ b/src/backend/replication/syncrep_scanner.l
@@ -54,6 +54,8 @@ digit [0-9]
ident_start [A-Za-z\200-\377_]
ident_cont [A-Za-z\200-\377_0-9\$]
identifier {ident_start}{ident_cont}*
+any_ident any
+first_ident first
dquote \"
xdstart {dquote}
@@ -64,6 +66,8 @@ xdinside [^"]+
%%
{space}+ { /* ignore */ }
+{any_ident} { return ANY; }
+{first_ident} { return FIRST; }
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c
index b14d821..fe396a8 100644
--- a/src/backend/replication/walsender.c
+++ b/src/backend/replication/walsender.c
@@ -2868,12 +2868,14 @@ pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
- * informational, not different from priority.
+ * informational. In quorum method, since all standbys are considered as
+ * a candidate of quorum commit standby state is always 'quorum'.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
- values[7] = CStringGetTextDatum("sync");
+ values[7] = SyncRepConfig->sync_method == SYNC_REP_PRIORITY ?
+ CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index 7f9acfd..b332247 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -245,7 +245,8 @@
# These settings are ignored on a standby server.
#synchronous_standby_names = '' # standby servers that provide sync rep
- # number of sync standbys and comma-separated list of application_name
+ # synchronization method, number of sync standbys
+ # and comma-separated list of application_name
# from standby(s); '*' = all
#vacuum_defer_cleanup_age = 0 # number of xacts by which cleanup is delayed
diff --git a/src/include/replication/syncrep.h b/src/include/replication/syncrep.h
index e4e0e27..29c35e4 100644
--- a/src/include/replication/syncrep.h
+++ b/src/include/replication/syncrep.h
@@ -32,6 +32,10 @@
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+/* sync_method of SyncRepConfigData */
+#define SYNC_REP_PRIORITY 0
+#define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
@@ -45,10 +49,13 @@ typedef struct SyncRepConfigData
int num_sync; /* number of sync standbys that we need to
* wait for */
int nmembers; /* number of members in the following list */
+ uint8 sync_method; /* synchronization method */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
diff --git a/src/test/recovery/t/007_sync_rep.pl b/src/test/recovery/t/007_sync_rep.pl
index 0c87226..00e1ea0 100644
--- a/src/test/recovery/t/007_sync_rep.pl
+++ b/src/test/recovery/t/007_sync_rep.pl
@@ -3,7 +3,7 @@ use strict;
use warnings;
use PostgresNode;
use TestLib;
-use Test::More tests => 8;
+use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
@@ -172,3 +172,34 @@ test_sync_state(
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+# Check that priority method is used and standby1 and standby2 are considered
+# as synchronous standby.
+test_sync_state(
+$node_master, qq(standby1|1|sync
+standby2|2|sync
+standby4|0|async),
+'specify priority method by FIRST',
+'FIRST 2(standby1, standby2)');
+
+# Check that the state of standbys listed as a voter when the quorum
+# method is used.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|2|quorum
+standby4|0|async),
+'2 quorum and 1 async',
+'ANY 2(standby1, standby2)');
+
+# Start Standby3 which will be considered in 'quorum' state.
+$node_standby_3->start;
+
+# Check that set setting of 'ANY 2(*)' chooses all standbys as
+# voter.
+test_sync_state(
+$node_master, qq(standby1|1|quorum
+standby2|1|quorum
+standby3|1|quorum
+standby4|1|quorum),
+'all standbys are considered as candidates for quorum commit',
+'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-16 05:38 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-16 05:38 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Kyotaro HORIGUCHI <[email protected]>; Fujii Masao <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Thu, Dec 15, 2016 at 6:08 PM, Masahiko Sawada <[email protected]> wrote:
> Attached latest v12 patch.
> I changed behavior of "N (standby_list)" to use the priority method
> and incorporated some review comments so far. Please review it.
Some comments...
+ Another example of <varname>synchronous_standby_names</> for multiple
+ synchronous standby is:
Here standby takes an 's'.
+ candidates. The master server will wait for at least 2 replies from them.
+ <literal>s4</> is an asynchronous standby since its name is not in the list.
+ </para>
"will wait for replies from at least two of them".
+ * next-highest-priority standby. In quorum method, the all standbys
+ * appearing in the list are considered as a candidate for quorum commit.
"the all" is incorrect. I think you mean "all the" instead.
+ * NIL if no sync standby is connected. In quorum method, all standby
+ * priorities are same, that is 1. So this function returns the list of
This is not true. Standys have a priority number assigned. Though it does
not matter much for quorum groups, it gives an indication of their position
in the defined list.
#synchronous_standby_names = '' # standby servers that provide sync rep
- # number of sync standbys and comma-separated list of application_name
+ # synchronization method, number of sync standbys
+ # and comma-separated list of application_name
# from standby(s); '*' = all
The formulation is funny here: "sync rep synchronization method".
I think that Fujii-san has also some doc changes in his box. For anybody
picking up this patch next, it would be good to incorporate the things
I have noticed here.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-16 08:04 Fujii Masao <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-16 08:04 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Fri, Dec 16, 2016 at 2:38 PM, Michael Paquier
<[email protected]> wrote:
> On Thu, Dec 15, 2016 at 6:08 PM, Masahiko Sawada <[email protected]> wrote:
>> Attached latest v12 patch.
>> I changed behavior of "N (standby_list)" to use the priority method
>> and incorporated some review comments so far. Please review it.
>
> Some comments...
>
> + Another example of <varname>synchronous_standby_names</> for multiple
> + synchronous standby is:
> Here standby takes an 's'.
>
> + candidates. The master server will wait for at least 2 replies from them.
> + <literal>s4</> is an asynchronous standby since its name is not in the list.
> + </para>
> "will wait for replies from at least two of them".
>
> + * next-highest-priority standby. In quorum method, the all standbys
> + * appearing in the list are considered as a candidate for quorum commit.
> "the all" is incorrect. I think you mean "all the" instead.
>
> + * NIL if no sync standby is connected. In quorum method, all standby
> + * priorities are same, that is 1. So this function returns the list of
> This is not true. Standys have a priority number assigned. Though it does
> not matter much for quorum groups, it gives an indication of their position
> in the defined list.
>
> #synchronous_standby_names = '' # standby servers that provide sync rep
> - # number of sync standbys and comma-separated list of application_name
> + # synchronization method, number of sync standbys
> + # and comma-separated list of application_name
> # from standby(s); '*' = all
> The formulation is funny here: "sync rep synchronization method".
>
> I think that Fujii-san has also some doc changes in his box. For anybody
> picking up this patch next, it would be good to incorporate the things
> I have noticed here.
Yes, I will. Thanks!
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-16 13:42 Fujii Masao <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-16 13:42 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Fri, Dec 16, 2016 at 5:04 PM, Fujii Masao <[email protected]> wrote:
> On Fri, Dec 16, 2016 at 2:38 PM, Michael Paquier
> <[email protected]> wrote:
>> On Thu, Dec 15, 2016 at 6:08 PM, Masahiko Sawada <[email protected]> wrote:
>>> Attached latest v12 patch.
>>> I changed behavior of "N (standby_list)" to use the priority method
>>> and incorporated some review comments so far. Please review it.
>>
>> Some comments...
>>
>> + Another example of <varname>synchronous_standby_names</> for multiple
>> + synchronous standby is:
>> Here standby takes an 's'.
>>
>> + candidates. The master server will wait for at least 2 replies from them.
>> + <literal>s4</> is an asynchronous standby since its name is not in the list.
>> + </para>
>> "will wait for replies from at least two of them".
>>
>> + * next-highest-priority standby. In quorum method, the all standbys
>> + * appearing in the list are considered as a candidate for quorum commit.
>> "the all" is incorrect. I think you mean "all the" instead.
>>
>> + * NIL if no sync standby is connected. In quorum method, all standby
>> + * priorities are same, that is 1. So this function returns the list of
>> This is not true. Standys have a priority number assigned. Though it does
>> not matter much for quorum groups, it gives an indication of their position
>> in the defined list.
>>
>> #synchronous_standby_names = '' # standby servers that provide sync rep
>> - # number of sync standbys and comma-separated list of application_name
>> + # synchronization method, number of sync standbys
>> + # and comma-separated list of application_name
>> # from standby(s); '*' = all
>> The formulation is funny here: "sync rep synchronization method".
>>
>> I think that Fujii-san has also some doc changes in his box. For anybody
>> picking up this patch next, it would be good to incorporate the things
>> I have noticed here.
>
> Yes, I will. Thanks!
Attached is the modified version of the patch. Barring objections, I will
commit this version.
Even after committing the patch, there will be still many source comments
and documentations that we need to update, for example,
in high-availability.sgml. We need to check and update them throughly later.
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
Attachments:
[text/x-patch] quorum_commit_v13.patch (36.1K, ../../CAHGQGwFGzT27pd3s7ffEEXJGwxLSyUe=Bq7RPK+_1HpubBk2_g@mail.gmail.com/2-quorum_commit_v13.patch)
download | inline diff:
*** a/doc/src/sgml/config.sgml
--- b/doc/src/sgml/config.sgml
***************
*** 3054,3094 **** include_dir 'conf.d'
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
! earlier in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
<literal>pg_stat_replication</></link> view).
! Other standby servers appearing later in this list represent potential
! synchronous standbys. If any of the current synchronous
! standbys disconnects for whatever reason,
! it will be replaced immediately with the next-highest-priority standby.
! Specifying more than one standby name can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
! <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
! is the name of a standby server. For example, a setting of
! <literal>3 (s1, s2, s3, s4)</> makes transaction commits wait
! until their WAL records are received by three higher-priority standbys
! chosen from standby servers <literal>s1</>, <literal>s2</>,
! <literal>s3</> and <literal>s4</>.
! </para>
! <para>
! The second syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
! with <replaceable class="parameter">num_sync</replaceable> equal to 1.
! For example, <literal>1 (s1, s2)</> and
! <literal>s1, s2</> have the same meaning: either <literal>s1</>
! or <literal>s2</> is chosen as a synchronous standby.
</para>
<para>
The name of a standby server for this purpose is the
--- 3054,3124 ----
transactions waiting for commit will be allowed to proceed after
these standby servers confirm receipt of their data.
The synchronous standbys will be those whose names appear
! in this list, and
that are both currently connected and streaming data in real-time
(as shown by a state of <literal>streaming</literal> in the
<link linkend="monitoring-stats-views-table">
<literal>pg_stat_replication</></link> view).
! Specifying more than one standby names can allow very high availability.
</para>
<para>
This parameter specifies a list of standby servers using
either of the following syntaxes:
<synopsis>
! [FIRST] <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
! ANY <replaceable class="parameter">num_sync</replaceable> ( <replaceable class="parameter">standby_name</replaceable> [, ...] )
<replaceable class="parameter">standby_name</replaceable> [, ...]
</synopsis>
where <replaceable class="parameter">num_sync</replaceable> is
the number of synchronous standbys that transactions need to
wait for replies from,
and <replaceable class="parameter">standby_name</replaceable>
! is the name of a standby server.
! <literal>FIRST</> and <literal>ANY</> specify the method to choose
! synchronous standbys from the listed servers.
! </para>
! <para>
! The keyword <literal>FIRST</>, coupled with
! <replaceable class="parameter">num_sync</replaceable>, specifies a
! priority-based synchronous replication and makes transaction commits
! wait until their WAL records are replicated to
! <replaceable class="parameter">num_sync</replaceable> synchronous
! standbys chosen based on their priorities. For example, a setting of
! <literal>FIRST 3 (s1, s2, s3, s4)</> will cause each commit to wait for
! replies from three higher-priority standbys chosen from standby servers
! <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>.
! The standbys whose names appear earlier in the list are given higher
! priority and will be considered as synchronous. Other standby servers
! appearing later in this list represent potential synchronous standbys.
! If any of the current synchronous standbys disconnects for whatever
! reason, it will be replaced immediately with the next-highest-priority
! standby. The keyword <literal>FIRST</> is optional.
! </para>
! <para>
! The keyword <literal>ANY</>, coupled with
! <replaceable class="parameter">num_sync</replaceable>, specifies a
! quorum-based synchronous replication and makes transaction commits
! wait until their WAL records are replicated to <emphasis>at least</>
! <replaceable class="parameter">num_sync</replaceable> listed standbys.
! For example, a setting of <literal>ANY 3 (s1, s2, s3, s4)</> will cause
! each commit to proceed as soon as at least any three standbys of
! <literal>s1</>, <literal>s2</>, <literal>s3</> and <literal>s4</>
! reply.
! </para>
! <para>
! <literal>FIRST</> and <literal>ANY</> are case-insensitive. If these
! keywords are used as the name of a standby server,
! its <replaceable class="parameter">standby_name</replaceable> must
! be double-quoted.
! </para>
! <para>
! The third syntax was used before <productname>PostgreSQL</>
version 9.6 and is still supported. It's the same as the first syntax
! with <literal>FIRST</> and
! <replaceable class="parameter">num_sync</replaceable> equal to 1.
! For example, <literal>FIRST 1 (s1, s2)</> and <literal>s1, s2</> have
! the same meaning: either <literal>s1</> or <literal>s2</> is chosen
! as a synchronous standby.
</para>
<para>
The name of a standby server for this purpose is the
*** a/doc/src/sgml/high-availability.sgml
--- b/doc/src/sgml/high-availability.sgml
***************
*** 1138,1156 **** primary_slot_name = 'node_a_slot'
as synchronous confirm receipt of their data. The number of synchronous
standbys that transactions must wait for replies from is specified in
<varname>synchronous_standby_names</>. This parameter also specifies
! a list of standby names, which determines the priority of each standby
! for being chosen as a synchronous standby. The standbys whose names
! appear earlier in the list are given higher priority and will be considered
! as synchronous. Other standby servers appearing later in this list
! represent potential synchronous standbys. If any of the current
! synchronous standbys disconnects for whatever reason, it will be replaced
! immediately with the next-highest-priority standby.
</para>
<para>
! An example of <varname>synchronous_standby_names</> for multiple
! synchronous standbys is:
<programlisting>
! synchronous_standby_names = '2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
--- 1138,1162 ----
as synchronous confirm receipt of their data. The number of synchronous
standbys that transactions must wait for replies from is specified in
<varname>synchronous_standby_names</>. This parameter also specifies
! a list of standby names and the method (<literal>FIRST</> and
! <literal>ANY</>) to choose synchronous standbys from the listed ones.
</para>
<para>
! The method <literal>FIRST</> specifies a priority-based synchronous
! replication and makes transaction commits wait until their WAL records are
! replicated to the requested number of synchronous standbys chosen based on
! their priorities. The standbys whose names appear earlier in the list are
! given higher priority and will be considered as synchronous. Other standby
! servers appearing later in this list represent potential synchronous
! standbys. If any of the current synchronous standbys disconnects for
! whatever reason, it will be replaced immediately with the
! next-highest-priority standby.
! </para>
! <para>
! An example of <varname>synchronous_standby_names</> for
! a priority-based multiple synchronous standbys is:
<programlisting>
! synchronous_standby_names = 'FIRST 2 (s1, s2, s3)'
</programlisting>
In this example, if four standby servers <literal>s1</>, <literal>s2</>,
<literal>s3</> and <literal>s4</> are running, the two standbys
***************
*** 1162,1167 **** synchronous_standby_names = '2 (s1, s2, s3)'
--- 1168,1191 ----
its name is not in the list.
</para>
<para>
+ The method <literal>ANY</> specifies a quorum-based synchronous
+ replication and makes transaction commits wait until their WAL records
+ are replicated to <emphasis>at least</> the requested number of
+ synchronous standbys in the list.
+ </para>
+ <para>
+ An example of <varname>synchronous_standby_names</> for
+ a quorum-based multiple synchronous standbys is:
+ <programlisting>
+ synchronous_standby_names = 'ANY 2 (s1, s2, s3)'
+ </programlisting>
+ In this example, if four standby servers <literal>s1</>, <literal>s2</>,
+ <literal>s3</> and <literal>s4</> are running, transaction commits will
+ wait for replies from at least any two standbys of <literal>s1</>,
+ <literal>s2</> and <literal>s3</>. <literal>s4</> is an asynchronous
+ standby since its name is not in the list.
+ </para>
+ <para>
The synchronous states of standby servers can be viewed using
the <structname>pg_stat_replication</structname> view.
</para>
*** a/doc/src/sgml/monitoring.sgml
--- b/doc/src/sgml/monitoring.sgml
***************
*** 1412,1418 **** SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
<entry><structfield>sync_priority</></entry>
<entry><type>integer</></entry>
<entry>Priority of this standby server for being chosen as the
! synchronous standby</entry>
</row>
<row>
<entry><structfield>sync_state</></entry>
--- 1412,1419 ----
<entry><structfield>sync_priority</></entry>
<entry><type>integer</></entry>
<entry>Priority of this standby server for being chosen as the
! synchronous standby in a priority-based synchronous replication.
! This has no effect in a quorum-based synchronous replication.</entry>
</row>
<row>
<entry><structfield>sync_state</></entry>
***************
*** 1437,1442 **** SELECT pid, wait_event_type, wait_event FROM pg_stat_activity WHERE wait_event i
--- 1438,1449 ----
<literal>sync</>: This standby server is synchronous.
</para>
</listitem>
+ <listitem>
+ <para>
+ <literal>quorum</>: This standby server is considered as a candidate
+ for quorum standbys.
+ </para>
+ </listitem>
</itemizedlist>
</entry>
</row>
*** a/src/backend/replication/Makefile
--- b/src/backend/replication/Makefile
***************
*** 26,32 **** repl_gram.o: repl_scanner.c
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
! syncrep_scanner.c: FLEXFLAGS = -CF -p
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
--- 26,32 ----
# syncrep_scanner is complied as part of syncrep_gram
syncrep_gram.o: syncrep_scanner.c
! syncrep_scanner.c: FLEXFLAGS = -CF -p -i
syncrep_scanner.c: FLEX_NO_BACKUP=yes
# repl_gram.c, repl_scanner.c, syncrep_gram.c and syncrep_scanner.c
*** a/src/backend/replication/syncrep.c
--- b/src/backend/replication/syncrep.c
***************
*** 30,52 ****
* searching the through all waiters each time we receive a reply.
*
* In 9.5 or before only a single standby could be considered as
! * synchronous. In 9.6 we support multiple synchronous standbys.
! * The number of synchronous standbys that transactions must wait for
! * replies from is specified in synchronous_standby_names.
! * This parameter also specifies a list of standby names,
! * which determines the priority of each standby for being chosen as
! * a synchronous standby. The standbys whose names appear earlier
! * in the list are given higher priority and will be considered as
! * synchronous. Other standby servers appearing later in this list
! * represent potential synchronous standbys. If any of the current
! * synchronous standbys disconnects for whatever reason, it will be
! * replaced immediately with the next-highest-priority standby.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
* the primary; that may take some time. Once caught up,
! * the current higher priority standbys which are considered as
! * synchronous at that moment will release waiters from the queue.
*
* Portions Copyright (c) 2010-2016, PostgreSQL Global Development Group
*
--- 30,63 ----
* searching the through all waiters each time we receive a reply.
*
* In 9.5 or before only a single standby could be considered as
! * synchronous. In 9.6 we support a priority-based multiple synchronous
! * standbys. In 10.0 a quorum-based multiple synchronous standbys is also
! * supported. The number of synchronous standbys that transactions
! * must wait for replies from is specified in synchronous_standby_names.
! * This parameter also specifies a list of standby names and the method
! * (FIRST and ANY) to choose synchronous standbys from the listed ones.
! *
! * The method FIRST specifies a priority-based synchronous replication
! * and makes transaction commits wait until their WAL records are
! * replicated to the requested number of synchronous standbys chosen based
! * on their priorities. The standbys whose names appear earlier in the list
! * are given higher priority and will be considered as synchronous.
! * Other standby servers appearing later in this list represent potential
! * synchronous standbys. If any of the current synchronous standbys
! * disconnects for whatever reason, it will be replaced immediately with
! * the next-highest-priority standby.
! *
! * The method ANY specifies a quorum-based synchronous replication
! * and makes transaction commits wait until their WAL records are
! * replicated to at least the requested number of synchronous standbys
! * in the list. All the standbys appearing in the list are considered as
! * candidates for quorum synchronous standbys.
*
* Before the standbys chosen from synchronous_standby_names can
* become the synchronous standbys they must have caught up with
* the primary; that may take some time. Once caught up,
! * the standbys which are considered as synchronous at that moment
! * will release waiters from the queue.
*
* Portions Copyright (c) 2010-2016, PostgreSQL Global Development Group
*
***************
*** 79,96 **** char *SyncRepStandbyNames;
static bool announce_next_takeover = true;
! static SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
! static bool SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
! XLogRecPtr *flushPtr,
! XLogRecPtr *applyPtr,
! bool *am_sync);
static int SyncRepGetStandbyPriority(void);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
--- 90,118 ----
static bool announce_next_takeover = true;
! SyncRepConfigData *SyncRepConfig = NULL;
static int SyncRepWaitMode = SYNC_REP_NO_WAIT;
static void SyncRepQueueInsert(int mode);
static void SyncRepCancelWait(void);
static int SyncRepWakeQueue(bool all, int mode);
! static bool SyncRepGetSyncRecPtr(XLogRecPtr *writePtr,
! XLogRecPtr *flushPtr,
! XLogRecPtr *applyPtr,
! bool *am_sync);
! static void SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr,
! XLogRecPtr *flushPtr,
! XLogRecPtr *applyPtr,
! List *sync_standbys);
! static void SyncRepGetNthLatestSyncRecPtr(XLogRecPtr *writePtr,
! XLogRecPtr *flushPtr,
! XLogRecPtr *applyPtr,
! List *sync_standbys, uint8 nth);
static int SyncRepGetStandbyPriority(void);
+ static List *SyncRepGetSyncStandbysPriority(bool *am_sync);
+ static List *SyncRepGetSyncStandbysQuorum(bool *am_sync);
+ static int cmp_lsn(const void *a, const void *b);
#ifdef USE_ASSERT_CHECKING
static bool SyncRepQueueIsOrderedByLSN(int mode);
***************
*** 386,392 **** SyncRepReleaseWaiters(void)
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
! bool got_oldest;
bool am_sync;
int numwrite = 0;
int numflush = 0;
--- 408,414 ----
XLogRecPtr writePtr;
XLogRecPtr flushPtr;
XLogRecPtr applyPtr;
! bool got_recptr;
bool am_sync;
int numwrite = 0;
int numflush = 0;
***************
*** 413,423 **** SyncRepReleaseWaiters(void)
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
! * Check whether we are a sync standby or not, and calculate the oldest
* positions among all sync standbys.
*/
! got_oldest = SyncRepGetOldestSyncRecPtr(&writePtr, &flushPtr,
! &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
--- 435,444 ----
LWLockAcquire(SyncRepLock, LW_EXCLUSIVE);
/*
! * Check whether we are a sync standby or not, and calculate the synced
* positions among all sync standbys.
*/
! got_recptr = SyncRepGetSyncRecPtr(&writePtr, &flushPtr, &applyPtr, &am_sync);
/*
* If we are managing a sync standby, though we weren't prior to this,
***************
*** 426,441 **** SyncRepReleaseWaiters(void)
if (announce_next_takeover && am_sync)
{
announce_next_takeover = false;
! ereport(LOG,
! (errmsg("standby \"%s\" is now a synchronous standby with priority %u",
! application_name, MyWalSnd->sync_standby_priority)));
}
/*
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
! if (!got_oldest || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
--- 447,468 ----
if (announce_next_takeover && am_sync)
{
announce_next_takeover = false;
!
! if (SyncRepConfig->syncrep_method == SYNC_REP_PRIORITY)
! ereport(LOG,
! (errmsg("standby \"%s\" is now a synchronous standby with priority %u",
! application_name, MyWalSnd->sync_standby_priority)));
! else
! ereport(LOG,
! (errmsg("standby \"%s\" is now a candidate for quorum synchronous standby",
! application_name)));
}
/*
* If the number of sync standbys is less than requested or we aren't
* managing a sync standby then just leave.
*/
! if (!got_recptr || !am_sync)
{
LWLockRelease(SyncRepLock);
announce_next_takeover = !am_sync;
***************
*** 471,491 **** SyncRepReleaseWaiters(void)
}
/*
! * Calculate the oldest Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
! * store the oldest positions into *writePtr, *flushPtr and *applyPtr.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
! SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
- ListCell *cell;
*writePtr = InvalidXLogRecPtr;
*flushPtr = InvalidXLogRecPtr;
--- 498,517 ----
}
/*
! * Calculate the synced Write, Flush and Apply positions among sync standbys.
*
* Return false if the number of sync standbys is less than
* synchronous_standby_names specifies. Otherwise return true and
! * store the positions into *writePtr, *flushPtr and *applyPtr.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
static bool
! SyncRepGetSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
XLogRecPtr *applyPtr, bool *am_sync)
{
List *sync_standbys;
*writePtr = InvalidXLogRecPtr;
*flushPtr = InvalidXLogRecPtr;
***************
*** 508,519 **** SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
}
/*
! * Scan through all sync standbys and calculate the oldest Write, Flush
! * and Apply positions.
*/
! foreach(cell, sync_standbys)
{
! WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
XLogRecPtr write;
XLogRecPtr flush;
XLogRecPtr apply;
--- 534,582 ----
}
/*
! * In a priority-based sync replication, the synced positions are the
! * oldest ones among sync standbys. In a quorum-based, they are the Nth
! * latest ones.
! *
! * SyncRepGetNthLatestSyncRecPtr() also can calculate the oldest positions.
! * But we use SyncRepGetOldestSyncRecPtr() for that calculation because
! * it's a bit more efficient.
! *
! * XXX If the numbers of current and requested sync standbys are the same,
! * we can use SyncRepGetOldestSyncRecPtr() to calculate the synced
! * positions even in a quorum-based sync replication.
! */
! if (SyncRepConfig->syncrep_method == SYNC_REP_PRIORITY)
! {
! SyncRepGetOldestSyncRecPtr(writePtr, flushPtr, applyPtr,
! sync_standbys);
! }
! else
! {
! SyncRepGetNthLatestSyncRecPtr(writePtr, flushPtr, applyPtr,
! sync_standbys, SyncRepConfig->num_sync);
! }
!
! list_free(sync_standbys);
! return true;
! }
!
! /*
! * Calculate the oldest Write, Flush and Apply positions among sync standbys.
! */
! static void
! SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
! XLogRecPtr *applyPtr, List *sync_standbys)
! {
! ListCell *cell;
!
! /*
! * Scan through all sync standbys and calculate the oldest
! * Write, Flush and Apply positions.
*/
! foreach (cell, sync_standbys)
{
! WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
XLogRecPtr write;
XLogRecPtr flush;
XLogRecPtr apply;
***************
*** 531,553 **** SyncRepGetOldestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
*applyPtr = apply;
}
! list_free(sync_standbys);
! return true;
}
/*
* Return the list of sync standbys, or NIL if no sync standby is connected.
*
- * If there are multiple standbys with the same priority,
- * the first one found is selected preferentially.
* The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
List *
! SyncRepGetSyncStandbys(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
--- 594,756 ----
if (XLogRecPtrIsInvalid(*applyPtr) || *applyPtr > apply)
*applyPtr = apply;
}
+ }
! /*
! * Calculate the Nth latest Write, Flush and Apply positions among sync
! * standbys.
! */
! static void
! SyncRepGetNthLatestSyncRecPtr(XLogRecPtr *writePtr, XLogRecPtr *flushPtr,
! XLogRecPtr *applyPtr, List *sync_standbys, uint8 nth)
! {
! ListCell *cell;
! XLogRecPtr *write_array;
! XLogRecPtr *flush_array;
! XLogRecPtr *apply_array;
! int len;
! int i = 0;
!
! len = list_length(sync_standbys);
! write_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
! flush_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
! apply_array = (XLogRecPtr *) palloc(sizeof(XLogRecPtr) * len);
!
! foreach (cell, sync_standbys)
! {
! WalSnd *walsnd = &WalSndCtl->walsnds[lfirst_int(cell)];
!
! SpinLockAcquire(&walsnd->mutex);
! write_array[i] = walsnd->write;
! flush_array[i] = walsnd->flush;
! apply_array[i] = walsnd->apply;
! SpinLockRelease(&walsnd->mutex);
!
! i++;
! }
!
! qsort(write_array, len, sizeof(XLogRecPtr), cmp_lsn);
! qsort(flush_array, len, sizeof(XLogRecPtr), cmp_lsn);
! qsort(apply_array, len, sizeof(XLogRecPtr), cmp_lsn);
!
! /* Get Nth latest Write, Flush, Apply positions */
! *writePtr = write_array[nth - 1];
! *flushPtr = flush_array[nth - 1];
! *applyPtr = apply_array[nth - 1];
!
! pfree(write_array);
! pfree(flush_array);
! pfree(apply_array);
! }
!
! /*
! * Compare lsn in order to sort array in descending order.
! */
! static int
! cmp_lsn(const void *a, const void *b)
! {
! XLogRecPtr lsn1 = *((const XLogRecPtr *) a);
! XLogRecPtr lsn2 = *((const XLogRecPtr *) b);
!
! if (lsn1 > lsn2)
! return -1;
! else if (lsn1 == lsn2)
! return 0;
! else
! return 1;
}
/*
* Return the list of sync standbys, or NIL if no sync standby is connected.
*
* The caller must hold SyncRepLock.
*
* On return, *am_sync is set to true if this walsender is connecting to
* sync standby. Otherwise it's set to false.
*/
List *
! SyncRepGetSyncStandbys(bool *am_sync)
! {
! /* Set default result */
! if (am_sync != NULL)
! *am_sync = false;
!
! /* Quick exit if sync replication is not requested */
! if (SyncRepConfig == NULL)
! return NIL;
!
! return (SyncRepConfig->syncrep_method == SYNC_REP_PRIORITY) ?
! SyncRepGetSyncStandbysPriority(am_sync) :
! SyncRepGetSyncStandbysQuorum(am_sync);
! }
!
! /*
! * Return the list of all the candidates for quorum sync standbys,
! * or NIL if no such standby is connected.
! *
! * The caller must hold SyncRepLock. This function must be called only in
! * a quorum-based sync replication.
! *
! * On return, *am_sync is set to true if this walsender is connecting to
! * sync standby. Otherwise it's set to false.
! */
! static List *
! SyncRepGetSyncStandbysQuorum(bool *am_sync)
! {
! List *result = NIL;
! int i;
! volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
! * rearrangement */
!
! Assert(SyncRepConfig->syncrep_method == SYNC_REP_QUORUM);
!
! for (i = 0; i < max_wal_senders; i++)
! {
! walsnd = &WalSndCtl->walsnds[i];
!
! /* Must be active */
! if (walsnd->pid == 0)
! continue;
!
! /* Must be streaming */
! if (walsnd->state != WALSNDSTATE_STREAMING)
! continue;
!
! /* Must be synchronous */
! if (walsnd->sync_standby_priority == 0)
! continue;
!
! /* Must have a valid flush position */
! if (XLogRecPtrIsInvalid(walsnd->flush))
! continue;
!
! /*
! * Consider this standby as a candidate for quorum sync standbys
! * and append it to the result.
! */
! result = lappend_int(result, i);
! if (am_sync != NULL && walsnd == MyWalSnd)
! *am_sync = true;
! }
!
! return result;
! }
!
! /*
! * Return the list of sync standbys chosen based on their priorities,
! * or NIL if no sync standby is connected.
! *
! * If there are multiple standbys with the same priority,
! * the first one found is selected preferentially.
! *
! * The caller must hold SyncRepLock. This function must be called only in
! * a priority-based sync replication.
! *
! * On return, *am_sync is set to true if this walsender is connecting to
! * sync standby. Otherwise it's set to false.
! */
! static List *
! SyncRepGetSyncStandbysPriority(bool *am_sync)
{
List *result = NIL;
List *pending = NIL;
***************
*** 560,572 **** SyncRepGetSyncStandbys(bool *am_sync)
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
! /* Set default result */
! if (am_sync != NULL)
! *am_sync = false;
!
! /* Quick exit if sync replication is not requested */
! if (SyncRepConfig == NULL)
! return NIL;
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
--- 763,769 ----
volatile WalSnd *walsnd; /* Use volatile pointer to prevent code
* rearrangement */
! Assert(SyncRepConfig->syncrep_method == SYNC_REP_PRIORITY);
lowest_priority = SyncRepConfig->nmembers;
next_highest_priority = lowest_priority + 1;
*** a/src/backend/replication/syncrep_gram.y
--- b/src/backend/replication/syncrep_gram.y
***************
*** 21,27 **** SyncRepConfigData *syncrep_parse_result;
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
! List *members);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
--- 21,27 ----
char *syncrep_parse_error_msg;
static SyncRepConfigData *create_syncrep_config(const char *num_sync,
! List *members, uint8 syncrep_method);
/*
* Bison doesn't allocate anything that needs to live across parser calls,
***************
*** 46,52 **** static SyncRepConfigData *create_syncrep_config(const char *num_sync,
SyncRepConfigData *config;
}
! %token <str> NAME NUM JUNK
%type <config> result standby_config
%type <list> standby_list
--- 46,52 ----
SyncRepConfigData *config;
}
! %token <str> NAME NUM JUNK ANY FIRST
%type <config> result standby_config
%type <list> standby_list
***************
*** 60,67 **** result:
;
standby_config:
! standby_list { $$ = create_syncrep_config("1", $1); }
! | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3); }
;
standby_list:
--- 60,69 ----
;
standby_config:
! standby_list { $$ = create_syncrep_config("1", $1, SYNC_REP_PRIORITY); }
! | NUM '(' standby_list ')' { $$ = create_syncrep_config($1, $3, SYNC_REP_PRIORITY); }
! | ANY NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_QUORUM); }
! | FIRST NUM '(' standby_list ')' { $$ = create_syncrep_config($2, $4, SYNC_REP_PRIORITY); }
;
standby_list:
***************
*** 75,83 **** standby_name:
;
%%
-
static SyncRepConfigData *
! create_syncrep_config(const char *num_sync, List *members)
{
SyncRepConfigData *config;
int size;
--- 77,84 ----
;
%%
static SyncRepConfigData *
! create_syncrep_config(const char *num_sync, List *members, uint8 syncrep_method)
{
SyncRepConfigData *config;
int size;
***************
*** 98,103 **** create_syncrep_config(const char *num_sync, List *members)
--- 99,105 ----
config->config_size = size;
config->num_sync = atoi(num_sync);
+ config->syncrep_method = syncrep_method;
config->nmembers = list_length(members);
ptr = config->member_names;
foreach(lc, members)
*** a/src/backend/replication/syncrep_scanner.l
--- b/src/backend/replication/syncrep_scanner.l
***************
*** 64,69 **** xdinside [^"]+
--- 64,72 ----
%%
{space}+ { /* ignore */ }
+ ANY { return ANY; }
+ FIRST { return FIRST; }
+
{xdstart} {
initStringInfo(&xdbuf);
BEGIN(xd);
*** a/src/backend/replication/walsender.c
--- b/src/backend/replication/walsender.c
***************
*** 2868,2879 **** pg_stat_get_wal_senders(PG_FUNCTION_ARGS)
/*
* More easily understood version of standby state. This is purely
! * informational, not different from priority.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
! values[7] = CStringGetTextDatum("sync");
else
values[7] = CStringGetTextDatum("potential");
}
--- 2868,2887 ----
/*
* More easily understood version of standby state. This is purely
! * informational.
! *
! * In quorum-based sync replication, the role of each standby
! * listed in synchronous_standby_names can be changing very
! * frequently. Any standbys considered as "sync" at one moment can
! * be switched to "potential" ones at the next moment. So, it's
! * basically useless to report "sync" or "potential" as their sync
! * states. We report just "quorum" for them.
*/
if (priority == 0)
values[7] = CStringGetTextDatum("async");
else if (list_member_int(sync_standbys, i))
! values[7] = SyncRepConfig->syncrep_method == SYNC_REP_PRIORITY ?
! CStringGetTextDatum("sync") : CStringGetTextDatum("quorum");
else
values[7] = CStringGetTextDatum("potential");
}
*** a/src/backend/utils/misc/postgresql.conf.sample
--- b/src/backend/utils/misc/postgresql.conf.sample
***************
*** 245,251 ****
# These settings are ignored on a standby server.
#synchronous_standby_names = '' # standby servers that provide sync rep
! # number of sync standbys and comma-separated list of application_name
# from standby(s); '*' = all
#vacuum_defer_cleanup_age = 0 # number of xacts by which cleanup is delayed
--- 245,252 ----
# These settings are ignored on a standby server.
#synchronous_standby_names = '' # standby servers that provide sync rep
! # method to choose sync standbys, number of sync standbys
! # and comma-separated list of application_name
# from standby(s); '*' = all
#vacuum_defer_cleanup_age = 0 # number of xacts by which cleanup is delayed
*** a/src/include/replication/syncrep.h
--- b/src/include/replication/syncrep.h
***************
*** 32,37 ****
--- 32,41 ----
#define SYNC_REP_WAITING 1
#define SYNC_REP_WAIT_COMPLETE 2
+ /* syncrep_method of SyncRepConfigData */
+ #define SYNC_REP_PRIORITY 0
+ #define SYNC_REP_QUORUM 1
+
/*
* Struct for the configuration of synchronous replication.
*
***************
*** 44,54 **** typedef struct SyncRepConfigData
--- 48,61 ----
int config_size; /* total size of this struct, in bytes */
int num_sync; /* number of sync standbys that we need to
* wait for */
+ uint8 syncrep_method; /* method to choose sync standbys */
int nmembers; /* number of members in the following list */
/* member_names contains nmembers consecutive nul-terminated C strings */
char member_names[FLEXIBLE_ARRAY_MEMBER];
} SyncRepConfigData;
+ extern SyncRepConfigData *SyncRepConfig;
+
/* communication variables for parsing synchronous_standby_names GUC */
extern SyncRepConfigData *syncrep_parse_result;
extern char *syncrep_parse_error_msg;
*** a/src/test/recovery/t/007_sync_rep.pl
--- b/src/test/recovery/t/007_sync_rep.pl
***************
*** 3,9 **** use strict;
use warnings;
use PostgresNode;
use TestLib;
! use Test::More tests => 8;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
--- 3,9 ----
use warnings;
use PostgresNode;
use TestLib;
! use Test::More tests => 11;
# Query checking sync_priority and sync_state of each standby
my $check_sql =
***************
*** 172,174 **** test_sync_state(
--- 172,205 ----
standby2|1|sync
standby4|1|potential),
'potential standby found earlier in array is promoted to sync');
+
+ # Check that standby1 and standby2 are chosen as sync standbys
+ # based on their priorities.
+ test_sync_state(
+ $node_master, qq(standby1|1|sync
+ standby2|2|sync
+ standby4|0|async),
+ 'priority-based sync replication specified by FIRST keyword',
+ 'FIRST 2(standby1, standby2)');
+
+ # Check that all the listed standbys are considered as candidates
+ # for sync standbys in a quorum-based sync replication.
+ test_sync_state(
+ $node_master, qq(standby1|1|quorum
+ standby2|2|quorum
+ standby4|0|async),
+ '2 quorum and 1 async',
+ 'ANY 2(standby1, standby2)');
+
+ # Start Standby3 which will be considered in 'quorum' state.
+ $node_standby_3->start;
+
+ # Check that the setting of 'ANY 2(*)' chooses all standbys as
+ # candidates for quorum sync standbys.
+ test_sync_state(
+ $node_master, qq(standby1|1|quorum
+ standby2|1|quorum
+ standby3|1|quorum
+ standby4|1|quorum),
+ 'all standbys are considered as candidates for quorum sync standbys',
+ 'ANY 2(*)');
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-18 12:36 Michael Paquier <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-18 12:36 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Fri, Dec 16, 2016 at 10:42 PM, Fujii Masao <[email protected]> wrote:
> Attached is the modified version of the patch. Barring objections, I will
> commit this version.
There is a whitespace:
$ git diff master --check
src/backend/replication/syncrep.c:39: trailing whitespace.
+ *
> Even after committing the patch, there will be still many source comments
> and documentations that we need to update, for example,
> in high-availability.sgml. We need to check and update them throughly later.
The current patch is complicated enough, so that's fine for me. I
checked the patch one last time and that looks good.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-19 12:49 Fujii Masao <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 2 replies; 267+ messages in thread
From: Fujii Masao @ 2016-12-19 12:49 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Sun, Dec 18, 2016 at 9:36 PM, Michael Paquier
<[email protected]> wrote:
> On Fri, Dec 16, 2016 at 10:42 PM, Fujii Masao <[email protected]> wrote:
>> Attached is the modified version of the patch. Barring objections, I will
>> commit this version.
>
> There is a whitespace:
> $ git diff master --check
> src/backend/replication/syncrep.c:39: trailing whitespace.
> + *
Okey, pushed the patch with this fix. Thanks!
Regarding this feature, there are some loose ends. We should work on
and complete them until the release.
(1)
Which synchronous replication method, priority or quorum, should be
chosen when neither FIRST nor ANY is specified in s_s_names? Right now,
a priority-based sync replication is chosen for keeping backward
compatibility. However some hackers argued to change this decision
so that a quorum commit is chosen because they think that most users
prefer to a quorum.
(2)
There will be still many source comments and documentations that
we need to update, for example, in high-availability.sgml. We need to
check and update them throughly.
(3)
The priority value is assigned to each standby listed in s_s_names
even in quorum commit though those priority values are not used at all.
Users can see those priority values in pg_stat_replication.
Isn't this confusing? If yes, it might be better to always assign 1 as
the priority, for example.
Any other?
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-19 16:44 Alvaro Herrera <[email protected]>
parent: Fujii Masao <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Alvaro Herrera @ 2016-12-19 16:44 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Michael Paquier <[email protected]>; Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
Fujii Masao wrote:
> Regarding this feature, there are some loose ends. We should work on
> and complete them until the release.
Please list these in https://wiki.postgresql.org/wiki/Open_Items so that we
don't forget.
--
Álvaro Herrera https://www.2ndQuadrant.com/
PostgreSQL Development, 24x7 Support, Remote DBA, Training & Services
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-20 05:31 Masahiko Sawada <[email protected]>
parent: Fujii Masao <[email protected]>
1 sibling, 1 reply; 267+ messages in thread
From: Masahiko Sawada @ 2016-12-20 05:31 UTC (permalink / raw)
To: Fujii Masao <[email protected]>; +Cc: Michael Paquier <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Mon, Dec 19, 2016 at 9:49 PM, Fujii Masao <[email protected]> wrote:
> On Sun, Dec 18, 2016 at 9:36 PM, Michael Paquier
> <[email protected]> wrote:
>> On Fri, Dec 16, 2016 at 10:42 PM, Fujii Masao <[email protected]> wrote:
>>> Attached is the modified version of the patch. Barring objections, I will
>>> commit this version.
>>
>> There is a whitespace:
>> $ git diff master --check
>> src/backend/replication/syncrep.c:39: trailing whitespace.
>> + *
>
> Okey, pushed the patch with this fix. Thanks!
Thank you for reviewing and commit!
> Regarding this feature, there are some loose ends. We should work on
> and complete them until the release.
>
> (1)
> Which synchronous replication method, priority or quorum, should be
> chosen when neither FIRST nor ANY is specified in s_s_names? Right now,
> a priority-based sync replication is chosen for keeping backward
> compatibility. However some hackers argued to change this decision
> so that a quorum commit is chosen because they think that most users
> prefer to a quorum.
>
> (2)
> There will be still many source comments and documentations that
> we need to update, for example, in high-availability.sgml. We need to
> check and update them throughly.
Will try to update them.
> (3)
> The priority value is assigned to each standby listed in s_s_names
> even in quorum commit though those priority values are not used at all.
> Users can see those priority values in pg_stat_replication.
> Isn't this confusing? If yes, it might be better to always assign 1 as
> the priority, for example.
>
>
> Any other?
>
Do we need to consider the sorting method and the selecting k-th
latest LSN method?
Regards,
--
Masahiko Sawada
NIPPON TELEGRAPH AND TELEPHONE CORPORATION
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-20 05:46 Michael Paquier <[email protected]>
parent: Masahiko Sawada <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Michael Paquier @ 2016-12-20 05:46 UTC (permalink / raw)
To: Masahiko Sawada <[email protected]>; +Cc: Fujii Masao <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 20, 2016 at 2:31 PM, Masahiko Sawada <[email protected]> wrote:
> Do we need to consider the sorting method and the selecting k-th
> latest LSN method?
Honestly, nah. Tests are showing that there are many more bottlenecks
before that with just memory allocation and parsing.
--
Michael
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-20 14:28 Fujii Masao <[email protected]>
parent: Alvaro Herrera <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Fujii Masao @ 2016-12-20 14:28 UTC (permalink / raw)
To: Alvaro Herrera <[email protected]>; +Cc: Michael Paquier <[email protected]>; Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 20, 2016 at 1:44 AM, Alvaro Herrera
<[email protected]> wrote:
> Fujii Masao wrote:
>
>> Regarding this feature, there are some loose ends. We should work on
>> and complete them until the release.
>
> Please list these in https://wiki.postgresql.org/wiki/Open_Items so that we
> don't forget.
Yep, added!
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-20 14:47 Fujii Masao <[email protected]>
parent: Michael Paquier <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Fujii Masao @ 2016-12-20 14:47 UTC (permalink / raw)
To: Michael Paquier <[email protected]>; +Cc: Masahiko Sawada <[email protected]>; Kyotaro HORIGUCHI <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Tue, Dec 20, 2016 at 2:46 PM, Michael Paquier
<[email protected]> wrote:
> On Tue, Dec 20, 2016 at 2:31 PM, Masahiko Sawada <[email protected]> wrote:
>> Do we need to consider the sorting method and the selecting k-th
>> latest LSN method?
>
> Honestly, nah. Tests are showing that there are many more bottlenecks
> before that with just memory allocation and parsing.
I think that it's worth prototyping alternative algorithm, and
measuring the performances of those alternative and current
algorithms. This measurement should check not only the bottleneck
but also how much each algorithm increases the time that backends
need to wait for before they receive ack from walsender.
If it's reported that current algorithm is enough "effecient",
we can just leave the code as it is. OTOH, if not, let's adopt
the alternative one.
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-21 01:39 Kyotaro HORIGUCHI <[email protected]>
parent: Fujii Masao <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Kyotaro HORIGUCHI @ 2016-12-21 01:39 UTC (permalink / raw)
To: [email protected]; +Cc: [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; pgsql-hackers
At Tue, 20 Dec 2016 23:47:22 +0900, Fujii Masao <[email protected]> wrote in <CAHGQGwFcEhv8BPP0HV2VQ8kXaHQmfN7PFAgkKsPyVip0frizpg@mail.gmail.com>
> On Tue, Dec 20, 2016 at 2:46 PM, Michael Paquier
> <[email protected]> wrote:
> > On Tue, Dec 20, 2016 at 2:31 PM, Masahiko Sawada <[email protected]> wrote:
> >> Do we need to consider the sorting method and the selecting k-th
> >> latest LSN method?
> >
> > Honestly, nah. Tests are showing that there are many more bottlenecks
> > before that with just memory allocation and parsing.
>
> I think that it's worth prototyping alternative algorithm, and
> measuring the performances of those alternative and current
> algorithms. This measurement should check not only the bottleneck
> but also how much each algorithm increases the time that backends
> need to wait for before they receive ack from walsender.
>
> If it's reported that current algorithm is enough "effecient",
> we can just leave the code as it is. OTOH, if not, let's adopt
> the alternative one.
I'm personally interested in the difference of them but it
doesn't seem urgently required. If we have nothing particular to
do with this, considering other ordering method would be
valuable.
By a not-well-grounded thought though, maintaining top-kth list
by insertion sort would be promising rather than running top-kth
sorting on the whole list. Sorting on all walsenders is needed
for the first time and some other situation though.
By the way, do we continue dispu^h^hcussing on the format of
s_s_names and/or a successor right now?
regards,
--
Kyotaro Horiguchi
NTT Open Source Software Center
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: Quorum commit for multiple synchronous replication.
@ 2016-12-21 10:27 Fujii Masao <[email protected]>
parent: Kyotaro HORIGUCHI <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Fujii Masao @ 2016-12-21 10:27 UTC (permalink / raw)
To: Kyotaro HORIGUCHI <[email protected]>; +Cc: Michael Paquier <[email protected]>; Sawada Masahiko <[email protected]>; Amit Kapila <[email protected]>; Robert Haas <[email protected]>; Petr Jelinek <[email protected]>; Vik Fearing <[email protected]>; Simon Riggs <[email protected]>; Josh Berkus <[email protected]>; pgsql-hackers
On Wed, Dec 21, 2016 at 10:39 AM, Kyotaro HORIGUCHI
<[email protected]> wrote:
> At Tue, 20 Dec 2016 23:47:22 +0900, Fujii Masao <[email protected]> wrote in <CAHGQGwFcEhv8BPP0HV2VQ8kXaHQmfN7PFAgkKsPyVip0frizpg@mail.gmail.com>
>> On Tue, Dec 20, 2016 at 2:46 PM, Michael Paquier
>> <[email protected]> wrote:
>> > On Tue, Dec 20, 2016 at 2:31 PM, Masahiko Sawada <[email protected]> wrote:
>> >> Do we need to consider the sorting method and the selecting k-th
>> >> latest LSN method?
>> >
>> > Honestly, nah. Tests are showing that there are many more bottlenecks
>> > before that with just memory allocation and parsing.
>>
>> I think that it's worth prototyping alternative algorithm, and
>> measuring the performances of those alternative and current
>> algorithms. This measurement should check not only the bottleneck
>> but also how much each algorithm increases the time that backends
>> need to wait for before they receive ack from walsender.
>>
>> If it's reported that current algorithm is enough "effecient",
>> we can just leave the code as it is. OTOH, if not, let's adopt
>> the alternative one.
>
> I'm personally interested in the difference of them but it
> doesn't seem urgently required.
Yes, it's not urgent task.
> If we have nothing particular to
> do with this, considering other ordering method would be
> valuable.
>
> By a not-well-grounded thought though, maintaining top-kth list
> by insertion sort would be promising rather than running top-kth
> sorting on the whole list. Sorting on all walsenders is needed
> for the first time and some other situation though.
>
>
> By the way, do we continue dispu^h^hcussing on the format of
> s_s_names and/or a successor right now?
Yes. If there is better approach, we should discuss that.
Regards,
--
Fujii Masao
--
Sent via pgsql-hackers mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers
^ permalink raw reply [nested|flat] 267+ messages in thread
* Question on compatibility of Postgres with Open JDK
@ 2019-01-30 06:28 Pratheej Chandrika <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Pratheej Chandrika @ 2019-01-30 06:28 UTC (permalink / raw)
To: [email protected]; pgsql-hackers
Hello,
We are using Postgresql (postgresql-bdr94).
Please let us know whether Postgresql supports Open JDK?
Thanks
Pratheej
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: [BDR] Question on compatibility of Postgres with Open JDK
@ 2019-01-30 06:33 Craig Ringer <[email protected]>
parent: Pratheej Chandrika <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Craig Ringer @ 2019-01-30 06:33 UTC (permalink / raw)
To: Pratheej Chandrika <[email protected]>; +Cc: Postgres-BDR and pglogical Mailing List <[email protected]>; pgsql-hackers
I don't understand the question.
If you want to use PgJDBC, then yes, PgJDBC works on OpenJDK. You do not
need to use pgjdbc 9.4 with PostgreSQL 9.4, you may use the latest version.
If you want to use pl/java, then I don't know if it's been tested with
postgres-bdr 9.4. But it should work fine if it works with normal community
postgres 9.4.
On Wed, 30 Jan 2019 at 14:28, Pratheej Chandrika <
[email protected]> wrote:
> Hello,
> We are using Postgresql (postgresql-bdr94).
>
> Please let us know whether Postgresql supports Open JDK?
>
> Thanks
> Pratheej
>
> --
> You received this message because you are subscribed to the Google Groups
> "Postgres-BDR and pglogical Mailing List" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to [email protected].
> Visit this group at
> https://groups.google.com/a/2ndquadrant.com/group/bdr-list/.
> To view this discussion on the web visit
> https://groups.google.com/a/2ndquadrant.com/d/msgid/bdr-list/CA%2BOir%3DMAc9OU4iNm%3DRBr%2BF2fLOSjJT...
> <https://groups.google.com/a/2ndquadrant.com/d/msgid/bdr-list/CA%2BOir%3DMAc9OU4iNm%3DRBr%2BF2fLOSjJT...;
> .
>
--
Craig Ringer http://www.2ndQuadrant.com/
2ndQuadrant - PostgreSQL Solutions for the Enterprise
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: [BDR] Question on compatibility of Postgres with Open JDK
@ 2019-01-30 07:28 Pratheej Chandrika <[email protected]>
parent: Craig Ringer <[email protected]>
0 siblings, 1 reply; 267+ messages in thread
From: Pratheej Chandrika @ 2019-01-30 07:28 UTC (permalink / raw)
To: Craig Ringer <[email protected]>; +Cc: Postgres-BDR and pglogical Mailing List <[email protected]>; pgsql-hackers
--00000000000040e9470580a7da42
Content-Type: text/plain; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable
Criag,
Thanks a lot for the prompt reply.
^ permalink raw reply [nested|flat] 267+ messages in thread
* Re: [BDR] Question on compatibility of Postgres with Open JDK
@ 2019-01-30 08:27 Craig Ringer <[email protected]>
parent: Pratheej Chandrika <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Craig Ringer @ 2019-01-30 08:27 UTC (permalink / raw)
To: Pratheej Chandrika <[email protected]>; +Cc: Postgres-BDR and pglogical Mailing List <[email protected]>; pgsql-hackers
On Wed, 30 Jan 2019 at 15:28, Pratheej Chandrika <
[email protected]> wrote:
> Criag,
> Thanks a lot for the prompt reply.
>
> From what you mentioned, I assume that other the client side jdbc there
> is no Java dependency from Server side. What I mean is I assume there is no
> jdk/java dependency for Postgres server to work. Request your input.
>
Correct.
Please see the PostgreSQL and PgJDBC manuals for more details.
--
Craig Ringer http://www.2ndQuadrant.com/
2ndQuadrant - PostgreSQL Solutions for the Enterprise
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v57 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 84b22f4ac9..a2c88bd3a4 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Mar_18_16_56_02_2021_947)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v57 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 84b22f4ac9..a2c88bd3a4 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Mar_18_16_56_02_2021_947)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v43 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 2b2761a588..eaf4448943 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Dec_11_16_50_03_2020_915)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v44 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 2b2761a588..eaf4448943 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Mon_Dec_21_17_16_20_2020_608)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v38 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 25eabbb1ad..dd35920e82 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.18.4
----Next_Part(Thu_Oct__1_09_07_22_2020_252)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v39 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 25eabbb1ad..dd35920e82 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.18.4
----Next_Part(Tue_Oct__6_10_06_44_2020_382)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v40 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 25eabbb1ad..dd35920e82 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.18.4
----Next_Part(Wed_Nov__4_17_39_10_2020_208)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v41 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 25eabbb1ad..dd35920e82 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.18.4
----Next_Part(Fri_Nov__6_09_27_56_2020_738)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v42 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index 25eabbb1ad..dd35920e82 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.18.4
----Next_Part(Wed_Nov_11_10_07_22_2020_796)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v45 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Jan__8_10_24_34_2021_185)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v46 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_14_15_14_25_2021_903)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v47 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index d2c3064678..25677c5c6e 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Thu_Jan_21_12_03_48_2021_284)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v48 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Fri_Mar__5_17_18_56_2021_497)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v49 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_16_53_11_2021_575)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v50 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar__9_18_29_34_2021_806)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v51 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_12_10_39_2021_432)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v52 7/7] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Wed_Mar_10_17_51_37_2021_192)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* [PATCH v56 6/6] Exclude pg_stat directory from base backup
@ 2020-09-29 14:19 Kyotaro Horiguchi <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Kyotaro Horiguchi @ 2020-09-29 14:19 UTC (permalink / raw)
basebackup sends the content of pg_stat directory, which is doomed to
be removed at startup from the backup. Now that pg_stat_statements
saves a temporary file into the directory, let exclude pg_stat
directory from a base backup.
---
src/backend/replication/basebackup.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/backend/replication/basebackup.c b/src/backend/replication/basebackup.c
index f0d75f55bd..f54fcec70a 100644
--- a/src/backend/replication/basebackup.c
+++ b/src/backend/replication/basebackup.c
@@ -149,6 +149,13 @@ struct exclude_list_item
*/
static const char *const excludeDirContents[] =
{
+ /*
+ * Skip statistics files. PGSTAT_STAT_PERMANENT_DIRECTORY must be skipped
+ * because the files in the directory will be removed at startup from the
+ * backup.
+ */
+ PGSTAT_STAT_PERMANENT_DIRECTORY,
+
/*
* It is generally not useful to backup the contents of this directory
* even if the intention is to restore to another primary. See backup.sgml
--
2.27.0
----Next_Part(Tue_Mar_16_10_27_55_2021_500)----
^ permalink raw reply [nested|flat] 267+ messages in thread
* cfbot failures
@ 2023-02-20 01:08 Justin Pryzby <[email protected]>
0 siblings, 0 replies; 267+ messages in thread
From: Justin Pryzby @ 2023-02-20 01:08 UTC (permalink / raw)
To: Andres Freund <[email protected]>; +Cc: [email protected]; Thomas Munro <[email protected]>
On 2023-02-11, Andres Freund wrote [email protected]:
> The windows test failure is a transient issue independent of the patch
> (something went wrong with image permissions).
That's happening again since 3h ago.
https://cirrus-ci.com/github/postgresql-cfbot/postgresql
I suggested in the past that cfbot should delay if (say) the last 5 or
10 consecutive runs all failed (or maybe all failed on the same "task").
Maybe that should only apply to re-tests but not to new patches. It
could inject 15min delays until the condition is resolved. Or it could
run retests on a longer interval like 96h instead of 24. And add a
warning or start beeping about the issue.
That would mitigate not only issues in the master branch but also issues
with CI infrastructure (cirrus/google/images).
--
Justin
^ permalink raw reply [nested|flat] 267+ messages in thread
end of thread, other threads:[~2023-02-20 01:08 UTC | newest]
Thread overview: 267+ messages (download: mbox mbox.gz follow: Atom feed)
-- links below jump to the message on this page --
2016-11-07 15:25 Re: Quorum commit for multiple synchronous replication. Masahiko Sawada <[email protected]>
2016-11-08 13:12 ` Michael Paquier <[email protected]>
2016-11-14 08:39 ` Masahiko Sawada <[email protected]>
2016-11-16 03:08 ` Masahiko Sawada <[email protected]>
2016-11-26 13:27 ` Michael Paquier <[email protected]>
2016-11-28 11:03 ` Masahiko Sawada <[email protected]>
2016-11-29 04:32 ` Michael Paquier <[email protected]>
2016-12-06 04:11 ` Fujii Masao <[email protected]>
2016-12-06 09:57 ` Masahiko Sawada <[email protected]>
2016-12-06 10:14 ` Michael Paquier <[email protected]>
2016-12-07 03:32 ` Fujii Masao <[email protected]>
2016-12-07 04:26 ` Michael Paquier <[email protected]>
2016-12-07 05:49 ` Kyotaro HORIGUCHI <[email protected]>
2016-12-07 07:05 ` Michael Paquier <[email protected]>
2016-12-07 08:17 ` Masahiko Sawada <[email protected]>
2016-12-07 10:04 ` Michael Paquier <[email protected]>
2016-12-08 00:37 ` Kyotaro HORIGUCHI <[email protected]>
2016-12-08 00:07 ` Robert Haas <[email protected]>
2016-12-08 07:39 ` Michael Paquier <[email protected]>
2016-12-08 09:32 ` Masahiko Sawada <[email protected]>
2016-12-10 08:17 ` Amit Kapila <[email protected]>
2016-12-12 12:31 ` Masahiko Sawada <[email protected]>
2016-12-12 12:52 ` Fujii Masao <[email protected]>
2016-12-12 16:24 ` Masahiko Sawada <[email protected]>
2016-12-13 03:16 ` Amit Kapila <[email protected]>
2016-12-13 08:06 ` Kyotaro HORIGUCHI <[email protected]>
2016-12-14 14:34 ` Fujii Masao <[email protected]>
2016-12-14 21:47 ` Michael Paquier <[email protected]>
2016-12-15 02:04 ` Fujii Masao <[email protected]>
2016-12-15 02:23 ` Michael Paquier <[email protected]>
2016-12-15 05:13 ` Amit Kapila <[email protected]>
2016-12-15 05:20 ` Masahiko Sawada <[email protected]>
2016-12-15 06:06 ` Kyotaro HORIGUCHI <[email protected]>
2016-12-15 09:08 ` Masahiko Sawada <[email protected]>
2016-12-16 05:38 ` Michael Paquier <[email protected]>
2016-12-16 08:04 ` Fujii Masao <[email protected]>
2016-12-16 13:42 ` Fujii Masao <[email protected]>
2016-12-18 12:36 ` Michael Paquier <[email protected]>
2016-12-19 12:49 ` Fujii Masao <[email protected]>
2016-12-19 16:44 ` Alvaro Herrera <[email protected]>
2016-12-20 14:28 ` Fujii Masao <[email protected]>
2016-12-20 05:31 ` Masahiko Sawada <[email protected]>
2016-12-20 05:46 ` Michael Paquier <[email protected]>
2016-12-20 14:47 ` Fujii Masao <[email protected]>
2016-12-21 01:39 ` Kyotaro HORIGUCHI <[email protected]>
2016-12-21 10:27 ` Fujii Masao <[email protected]>
2019-01-30 06:28 Question on compatibility of Postgres with Open JDK Pratheej Chandrika <[email protected]>
2019-01-30 06:33 ` Re: [BDR] Question on compatibility of Postgres with Open JDK Craig Ringer <[email protected]>
2019-01-30 07:28 ` Re: [BDR] Question on compatibility of Postgres with Open JDK Pratheej Chandrika <[email protected]>
2019-01-30 08:27 ` Re: [BDR] Question on compatibility of Postgres with Open JDK Craig Ringer <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v57 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v40 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v57 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v38 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v43 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v44 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v41 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v42 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v48 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v39 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v52 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v56 6/6] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v50 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v49 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v47 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v45 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v51 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2020-09-29 14:19 [PATCH v46 7/7] Exclude pg_stat directory from base backup Kyotaro Horiguchi <[email protected]>
2023-02-20 01:08 cfbot failures Justin Pryzby <[email protected]>
This inbox is served by agora; see mirroring instructions
for how to clone and mirror all data and code used for this inbox