Add log_autovacuum_{vacuum|analyze}_min_duration
Hi hackers,
I am proposing the introduction of two new GUC parameters,
log_autovacuum_{vacuum|analyze}_min_duration, to replace the existing
log_autovacuum_min_duration.
Motivation:
Currently, log_autovacuum_min_duration controls the logging threshold
for both autovacuum and autoanalyze activities. However, autoanalyze
operations typically have a much shorter duration than autovacuum
operations. Consequently, if log_autovacuum_min_duration is set to a
value appropriate for capturing longer-running autovacuum tasks,
shorter autoanalyze activities are often not logged. This can make it
difficult to monitor and troubleshoot autoanalyze behavior
effectively.
By providing separate GUCs, administrators can set distinct logging
thresholds for autovacuum and autoanalyze, ensuring that both types of
activities can be logged appropriately based on their typical
execution times.
Example Usage:
The following SQL demonstrates how these new parameters would allow
for more granular logging. In this example, autoanalyze is configured
to always log (duration set to 0), while autovacuum is set to log only
if it runs for a very long time.
```
=# CREATE TABLE t (i int, d text) WITH (
-- autoanalyze settings
autovacuum_analyze_threshold = 1,
autovacuum_analyze_scale_factor = 0,
log_autovacuum_analyze_min_duration = 0,
-- autovacuum settings
autovacuum_vacuum_threshold = 1,
autovacuum_vacuum_scale_factor = 0,
log_autovacuum_vacuum_min_duration = 100_000_000
);
=# INSERT INTO t VALUES (1, 'a');
=# DELETE FROM t WHERE i = 1;
2025-06-03 15:15:39.608 JST [401368] LOG: automatic analyze of table
"postgres.public.t"
avg read rate: 18.229 MB/s, avg write rate: 0.000 MB/s
buffer usage: 155 hits, 7 reads, 0 dirtied
WAL usage: 1 records, 0 full page images, 530 bytes, 0 buffers full
system usage: CPU: user: 0.00 s, system: 0.00 s, elapsed: 0.00 s
```
Two patches are attached.
In v1-0001-Rename-log_autovacuum_min_duration.patch, just renamed
log_autovacuum_min_duration to log_autovacuum_vacuum_min_duration.
In v1-0002-Add-log_autovacuum_analyze_min_duration.patch, add the new
GUC parameter log_autovacuum_analyze_min_duration.
Do you think?
Best regards,
Shinya Kato
NTT OSS Center
Attachments:
v1-0002-Add-log_autovacuum_analyze_min_duration.patchapplication/octet-stream; name=v1-0002-Add-log_autovacuum_analyze_min_duration.patchDownload
From 8026447a175a0c80ed4fc7e85550c07b3ab84834 Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Fri, 2 May 2025 10:28:50 +0900
Subject: [PATCH v1 2/2] Add log_autovacuum_analyze_min_duration
The log output functionality of log_autovacuum_min_duration applies to
both VACUUM and ANALYZE, so it is not possible to separate the VACUUM
and ANALYZE log output thresholds. Logs are likely to be output only for
VACUUM and not for ANALYZE.
Therefore, we decided to separate the threshold for log output of
VACUUM by autovacuum (log_autovacuum_vacuum_min_duration) and the
threshold for log output of ANALYZE by autovacuum
(log_autovacuum_analyze_min_duration).
---
doc/src/sgml/config.sgml | 27 +++++++++++++++++++
doc/src/sgml/maintenance.sgml | 1 +
doc/src/sgml/ref/create_table.sgml | 15 +++++++++++
src/backend/access/common/reloptions.c | 11 ++++++++
src/backend/commands/analyze.c | 8 +++---
src/backend/commands/vacuum.c | 6 ++++-
src/backend/postmaster/autovacuum.c | 8 ++++++
src/backend/utils/misc/guc_tables.c | 12 +++++++++
src/backend/utils/misc/postgresql.conf.sample | 5 ++++
src/bin/psql/tab-complete.in.c | 2 ++
src/include/commands/vacuum.h | 3 +++
src/include/postmaster/autovacuum.h | 1 +
src/include/utils/rel.h | 1 +
.../xid_wraparound/t/001_emergency_vacuum.pl | 1 +
.../modules/xid_wraparound/t/002_limits.pl | 1 +
.../xid_wraparound/t/003_wraparounds.pl | 1 +
src/test/regress/pg_regress.c | 1 +
src/tools/ci/pg_ci_base.conf | 1 +
18 files changed, 100 insertions(+), 5 deletions(-)
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 1ae8dfd7137..e1544fcda73 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -7424,6 +7424,33 @@ local0.* /var/log/postgresql
</listitem>
</varlistentry>
+ <varlistentry id="guc-log-autovacuum-analyze-min-duration" xreflabel="log_autovacuum_analyze_min_duration">
+ <term><varname>log_autovacuum_analyze_min_duration</varname> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autovacuum_analyze_min_duration</varname></primary>
+ <secondary>configuration parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Causes analyze action executed by autovacuum to be logged if it ran for at
+ least the specified amount of time. Setting this to zero logs
+ all analyze actions by autovacuum. <literal>-1</literal> disables logging
+ analyze actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic analyzes that run
+ 250ms or longer will be logged. In addition, when this parameter is
+ set to any value other than <literal>-1</literal>, a message will be
+ logged if an analyze action by autovacuum is skipped due to a conflicting lock or a
+ concurrently dropped relation. The default is <literal>10min</literal>.
+ Enabling this parameter can be helpful in tracking analyze activity by autovacuum.
+ This parameter can only be set in the <filename>postgresql.conf</filename>
+ file or on the server command line; but the setting can be overridden for
+ individual tables by changing table storage parameters.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry id="guc-log-autovacuum-vacuum-min-duration" xreflabel="log_autovacuum_vacuum_min_duration">
<term><varname>log_autovacuum_vacuum_min_duration</varname> (<type>integer</type>)
<indexterm>
diff --git a/doc/src/sgml/maintenance.sgml b/doc/src/sgml/maintenance.sgml
index 84df5215580..066164a700a 100644
--- a/doc/src/sgml/maintenance.sgml
+++ b/doc/src/sgml/maintenance.sgml
@@ -889,6 +889,7 @@ HINT: Execute a database-wide VACUUM in that database.
the next database will be processed as soon as the first worker finishes.
Each worker process will check each table within its database and
execute <command>VACUUM</command> and/or <command>ANALYZE</command> as needed.
+ <xref linkend="guc-log-autovacuum-analyze-min-duration"/> and
<xref linkend="guc-log-autovacuum-vacuum-min-duration"/> can be set to monitor
autovacuum workers' activity.
</para>
diff --git a/doc/src/sgml/ref/create_table.sgml b/doc/src/sgml/ref/create_table.sgml
index 66954c66ba6..20a7909477e 100644
--- a/doc/src/sgml/ref/create_table.sgml
+++ b/doc/src/sgml/ref/create_table.sgml
@@ -1934,6 +1934,21 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</listitem>
</varlistentry>
+ <varlistentry id="reloption-log-autovacuum-analyze-min-duration" xreflabel="log_autovacuum_analyze_min_duration">
+ <term><literal>log_autovacuum_analyze_min_duration</literal>, <literal>toast.log_autovacuum_analyze_min_duration</literal> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autovacuum_analyze_min_duration</varname></primary>
+ <secondary>storage parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Per-table value for <xref linkend="guc-log-autovacuum-analyze-min-duration"/>
+ parameter.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry id="reloption-log-autovacuum-vacuum-min-duration" xreflabel="log_autovacuum_vacuum_min_duration">
<term><literal>log_autovacuum_vacuum_min_duration</literal>, <literal>toast.log_autovacuum_vacuum_min_duration</literal> (<type>integer</type>)
<indexterm>
diff --git a/src/backend/access/common/reloptions.c b/src/backend/access/common/reloptions.c
index 4bc618a34f0..f44d57556b6 100644
--- a/src/backend/access/common/reloptions.c
+++ b/src/backend/access/common/reloptions.c
@@ -319,6 +319,15 @@ static relopt_int intRelOpts[] =
ShareUpdateExclusiveLock
}, -1, 0, 2000000000
},
+ {
+ {
+ "log_autovacuum_analyze_min_duration",
+ "Sets the minimum execution time above which analyze actions by autovacuum will be logged",
+ RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
+ ShareUpdateExclusiveLock
+ },
+ -1, -1, INT_MAX
+ },
{
{
"log_autovacuum_vacuum_min_duration",
@@ -1894,6 +1903,8 @@ default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_max_age)},
{"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
+ {"log_autovacuum_analyze_min_duration", RELOPT_TYPE_INT,
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_analyze_min_duration)},
{"log_autovacuum_vacuum_min_duration", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_vacuum_min_duration)},
{"toast_tuple_target", RELOPT_TYPE_INT,
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index ba26b00cfb1..287ac50a71a 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -139,7 +139,7 @@ analyze_rel(Oid relid, RangeVar *relation,
* Make sure to generate only logs for ANALYZE in this case.
*/
onerel = vacuum_open_relation(relid, relation, params->options & ~(VACOPT_VACUUM),
- params->log_vacuum_min_duration >= 0,
+ params->log_analyze_min_duration >= 0,
ShareUpdateExclusiveLock);
/* leave if relation could not be opened or locked */
@@ -311,7 +311,7 @@ do_analyze_rel(Relation onerel, VacuumParams *params,
verbose = (params->options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params->log_vacuum_min_duration >= 0));
+ params->log_analyze_min_duration >= 0));
if (inh)
ereport(elevel,
(errmsg("analyzing \"%s.%s\" inheritance tree",
@@ -736,9 +736,9 @@ do_analyze_rel(Relation onerel, VacuumParams *params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params->log_vacuum_min_duration == 0 ||
+ if (verbose || params->log_analyze_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params->log_vacuum_min_duration))
+ params->log_analyze_min_duration))
{
long delay_in_ms;
WalUsage walusage;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 7e8d02d7a86..5494b58cb34 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -415,7 +415,11 @@ ExecVacuum(ParseState *pstate, VacuumStmt *vacstmt, bool isTopLevel)
/* user-invoked vacuum is never "for wraparound" */
params.is_wraparound = false;
- /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_vacuum_min_duration */
+ /*
+ * user-invoked vacuum uses VACOPT_VERBOSE instead of
+ * log_analyze_min_duration and log_vacuum_min_duration
+ */
+ params.log_analyze_min_duration = -1;
params.log_vacuum_min_duration = -1;
/*
diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c
index cc77bbd8f11..498159eb46a 100644
--- a/src/backend/postmaster/autovacuum.c
+++ b/src/backend/postmaster/autovacuum.c
@@ -133,6 +133,7 @@ int autovacuum_multixact_freeze_max_age;
double autovacuum_vac_cost_delay;
int autovacuum_vac_cost_limit;
+int Log_autovacuum_anl_min_duration = 600000;
int Log_autovacuum_vac_min_duration = 600000;
/* the minimum allowed time between two awakenings of the launcher */
@@ -2791,6 +2792,7 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
int freeze_table_age;
int multixact_freeze_min_age;
int multixact_freeze_table_age;
+ int log_analyze_min_duration;
int log_vacuum_min_duration;
/*
@@ -2800,6 +2802,11 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
* defaults, autovacuum's own first and plain vacuum second.
*/
+ /* -1 in autovac setting means use log_autovacuum_analyze_min_duration */
+ log_analyze_min_duration = (avopts && avopts->log_analyze_min_duration >= 0)
+ ? avopts->log_analyze_min_duration
+ : Log_autovacuum_anl_min_duration;
+
/* -1 in autovac setting means use log_autovacuum_vacuum_min_duration */
log_vacuum_min_duration = (avopts && avopts->log_vacuum_min_duration >= 0)
? avopts->log_vacuum_min_duration
@@ -2854,6 +2861,7 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
tab->at_params.multixact_freeze_min_age = multixact_freeze_min_age;
tab->at_params.multixact_freeze_table_age = multixact_freeze_table_age;
tab->at_params.is_wraparound = wraparound;
+ tab->at_params.log_analyze_min_duration = log_analyze_min_duration;
tab->at_params.log_vacuum_min_duration = log_vacuum_min_duration;
tab->at_params.toast_parent = InvalidOid;
diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c
index 7ba26ebff5b..b74c7abebea 100644
--- a/src/backend/utils/misc/guc_tables.c
+++ b/src/backend/utils/misc/guc_tables.c
@@ -3168,6 +3168,18 @@ struct config_int ConfigureNamesInt[] =
NULL, NULL, NULL
},
+ {
+ {"log_autovacuum_analyze_min_duration", PGC_SIGHUP, LOGGING_WHAT,
+ gettext_noop("Sets the minimum execution time above which "
+ "analyze actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging analyze actions by autovacuum. 0 means log all analyze actions by autovacuum."),
+ GUC_UNIT_MS
+ },
+ &Log_autovacuum_anl_min_duration,
+ 600000, -1, INT_MAX,
+ NULL, NULL, NULL
+ },
+
{
{"log_autovacuum_vacuum_min_duration", PGC_SIGHUP, LOGGING_WHAT,
gettext_noop("Sets the minimum execution time above which "
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index 90e02054acd..0f97ae1492e 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -585,6 +585,11 @@
#debug_print_rewritten = off
#debug_print_plan = off
#debug_pretty_print = on
+#log_autovacuum_analyze_min_duration = 10min # log analyze activity by autovacuum;
+ # -1 disables, 0 logs all actions and
+ # their durations, > 0 logs only
+ # actions running at least this number
+ # of milliseconds.
#log_autovacuum_vacuum_min_duration = 10min # log vacuum activity by autovacuum;
# -1 disables, 0 logs all actions and
# their durations, > 0 logs only
diff --git a/src/bin/psql/tab-complete.in.c b/src/bin/psql/tab-complete.in.c
index 27f63159e43..8ddda6be2f8 100644
--- a/src/bin/psql/tab-complete.in.c
+++ b/src/bin/psql/tab-complete.in.c
@@ -1386,6 +1386,7 @@ static const char *const table_storage_parameters[] = {
"autovacuum_vacuum_scale_factor",
"autovacuum_vacuum_threshold",
"fillfactor",
+ "log_autovacuum_analyze_min_duration",
"log_autovacuum_vacuum_min_duration",
"parallel_workers",
"toast.autovacuum_enabled",
@@ -1402,6 +1403,7 @@ static const char *const table_storage_parameters[] = {
"toast.autovacuum_vacuum_max_threshold",
"toast.autovacuum_vacuum_scale_factor",
"toast.autovacuum_vacuum_threshold",
+ "toast.log_autovacuum_analyze_min_duration",
"toast.log_autovacuum_vacuum_min_duration",
"toast.vacuum_index_cleanup",
"toast.vacuum_max_eager_freeze_failure_rate",
diff --git a/src/include/commands/vacuum.h b/src/include/commands/vacuum.h
index 5a90b84e099..6c39deb722f 100644
--- a/src/include/commands/vacuum.h
+++ b/src/include/commands/vacuum.h
@@ -224,6 +224,9 @@ typedef struct VacuumParams
int multixact_freeze_table_age; /* multixact age at which to scan
* whole table */
bool is_wraparound; /* force a for-wraparound vacuum */
+ int log_analyze_min_duration; /* minimum execution threshold in ms
+ * at which analyze by autovacuum is
+ * logged, -1 to use default */
int log_vacuum_min_duration; /* minimum execution threshold in ms
* at which vacuum by autovacuum is
* logged, -1 to use default */
diff --git a/src/include/postmaster/autovacuum.h b/src/include/postmaster/autovacuum.h
index 4d0b44a4f7a..59887c4d91f 100644
--- a/src/include/postmaster/autovacuum.h
+++ b/src/include/postmaster/autovacuum.h
@@ -47,6 +47,7 @@ extern PGDLLIMPORT int autovacuum_vac_cost_limit;
/* autovacuum launcher PID, only valid when worker is shutting down */
extern PGDLLIMPORT int AutovacuumLauncherPid;
+extern PGDLLIMPORT int Log_autovacuum_anl_min_duration;
extern PGDLLIMPORT int Log_autovacuum_vac_min_duration;
/* Status inquiry functions */
diff --git a/src/include/utils/rel.h b/src/include/utils/rel.h
index 23e47af9112..b8810bedf90 100644
--- a/src/include/utils/rel.h
+++ b/src/include/utils/rel.h
@@ -322,6 +322,7 @@ typedef struct AutoVacOpts
int multixact_freeze_min_age;
int multixact_freeze_max_age;
int multixact_freeze_table_age;
+ int log_analyze_min_duration;
int log_vacuum_min_duration;
float8 vacuum_cost_delay;
float8 vacuum_scale_factor;
diff --git a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
index 9d64bee10eb..166c2fa571b 100644
--- a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
+++ b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
@@ -21,6 +21,7 @@ $node->append_conf(
autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
+log_autovacuum_analyze_min_duration = 0
log_autovacuum_vacuum_min_duration = 0
]);
$node->start;
diff --git a/src/test/modules/xid_wraparound/t/002_limits.pl b/src/test/modules/xid_wraparound/t/002_limits.pl
index db87477ae5d..462791f3898 100644
--- a/src/test/modules/xid_wraparound/t/002_limits.pl
+++ b/src/test/modules/xid_wraparound/t/002_limits.pl
@@ -28,6 +28,7 @@ $node->init;
$node->append_conf(
'postgresql.conf', qq[
autovacuum_naptime = 1s
+log_autovacuum_analyze_min_duration = 0
log_autovacuum_vacuum_min_duration = 0
]);
$node->start;
diff --git a/src/test/modules/xid_wraparound/t/003_wraparounds.pl b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
index 59c04a1d781..37769399c2c 100644
--- a/src/test/modules/xid_wraparound/t/003_wraparounds.pl
+++ b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
@@ -24,6 +24,7 @@ $node->append_conf(
autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
+log_autovacuum_analyze_min_duration = 0
log_autovacuum_vacuum_min_duration = 0
]);
$node->start;
diff --git a/src/test/regress/pg_regress.c b/src/test/regress/pg_regress.c
index e2001acd4aa..40de7a83b68 100644
--- a/src/test/regress/pg_regress.c
+++ b/src/test/regress/pg_regress.c
@@ -2400,6 +2400,7 @@ regression_main(int argc, char *argv[],
bail("could not open \"%s\" for adding extra config: %m", buf);
fputs("\n# Configuration added by pg_regress\n\n", pg_conf);
+ fputs("log_autovacuum_analyze_min_duration = 0\n", pg_conf);
fputs("log_autovacuum_vacuum_min_duration = 0\n", pg_conf);
fputs("log_checkpoints = on\n", pg_conf);
fputs("log_line_prefix = '%m %b[%p] %q%a '\n", pg_conf);
diff --git a/src/tools/ci/pg_ci_base.conf b/src/tools/ci/pg_ci_base.conf
index d9bb408aab4..1ff32e5c549 100644
--- a/src/tools/ci/pg_ci_base.conf
+++ b/src/tools/ci/pg_ci_base.conf
@@ -6,6 +6,7 @@ restart_after_crash = false
max_prepared_transactions = 10
# Settings that make logs more useful
+log_autovacuum_analyze_min_duration = 0
log_autovacuum_vacuum_min_duration = 0
log_checkpoints = true
log_connections = all
--
2.39.3
v1-0001-Rename-log_autovacuum_min_duration.patchapplication/octet-stream; name=v1-0001-Rename-log_autovacuum_min_duration.patchDownload
From 176d511a9d9ef6d59751d1e57a8e0bab028e7140 Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Thu, 1 May 2025 18:42:28 +0900
Subject: [PATCH v1 1/2] Rename log_autovacuum_min_duration
To introduce log_autovacuum_analyze_min_duration, first rename
log_autovacuum_min_duration to log_autovacuum_vacuum_min_duration.
---
doc/src/sgml/config.sgml | 24 +++++++++----------
doc/src/sgml/maintenance.sgml | 4 ++--
doc/src/sgml/ref/create_table.sgml | 8 +++----
src/backend/access/common/reloptions.c | 8 +++----
src/backend/access/heap/vacuumlazy.c | 6 ++---
src/backend/commands/analyze.c | 8 +++----
src/backend/commands/vacuum.c | 6 ++---
src/backend/postmaster/autovacuum.c | 14 +++++------
src/backend/utils/misc/guc_tables.c | 9 +++----
src/backend/utils/misc/postgresql.conf.sample | 10 ++++----
src/bin/psql/tab-complete.in.c | 4 ++--
src/include/commands/vacuum.h | 6 ++---
src/include/postmaster/autovacuum.h | 2 +-
src/include/utils/rel.h | 2 +-
.../xid_wraparound/t/001_emergency_vacuum.pl | 2 +-
.../modules/xid_wraparound/t/002_limits.pl | 2 +-
.../xid_wraparound/t/003_wraparounds.pl | 2 +-
src/test/regress/pg_regress.c | 2 +-
src/tools/ci/pg_ci_base.conf | 2 +-
19 files changed, 61 insertions(+), 60 deletions(-)
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 021153b2a5f..1ae8dfd7137 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -7424,26 +7424,26 @@ local0.* /var/log/postgresql
</listitem>
</varlistentry>
- <varlistentry id="guc-log-autovacuum-min-duration" xreflabel="log_autovacuum_min_duration">
- <term><varname>log_autovacuum_min_duration</varname> (<type>integer</type>)
+ <varlistentry id="guc-log-autovacuum-vacuum-min-duration" xreflabel="log_autovacuum_vacuum_min_duration">
+ <term><varname>log_autovacuum_vacuum_min_duration</varname> (<type>integer</type>)
<indexterm>
- <primary><varname>log_autovacuum_min_duration</varname></primary>
+ <primary><varname>log_autovacuum_vacuum_min_duration</varname></primary>
<secondary>configuration parameter</secondary>
</indexterm>
</term>
<listitem>
<para>
- Causes each action executed by autovacuum to be logged if it ran for at
+ Causes vacuum action executed by autovacuum to be logged if it ran for at
least the specified amount of time. Setting this to zero logs
- all autovacuum actions. <literal>-1</literal> disables logging autovacuum
- actions. If this value is specified without units, it is taken as milliseconds.
- For example, if you set this to
- <literal>250ms</literal> then all automatic vacuums and analyzes that run
+ all vacuum actions by autovacuum. <literal>-1</literal> disables logging
+ vacuum actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic vacuums that run
250ms or longer will be logged. In addition, when this parameter is
set to any value other than <literal>-1</literal>, a message will be
- logged if an autovacuum action is skipped due to a conflicting lock or a
+ logged if a vacuum action by autovacuum is skipped due to a conflicting lock or a
concurrently dropped relation. The default is <literal>10min</literal>.
- Enabling this parameter can be helpful in tracking autovacuum activity.
+ Enabling this parameter can be helpful in tracking vacuum activity by autovacuum.
This parameter can only be set in the <filename>postgresql.conf</filename>
file or on the server command line; but the setting can be overridden for
individual tables by changing table storage parameters.
@@ -8603,7 +8603,7 @@ COPY postgres_log FROM '/full/path/to/logfile.csv' WITH csv;
in the output of <xref linkend="sql-vacuum"/> when the
<literal>VERBOSE</literal> option is used, and by autovacuum for
auto-vacuums and auto-analyzes when
- <xref linkend="guc-log-autovacuum-min-duration"/> is set.
+ <xref linkend="guc-log-autovacuum-vacuum-min-duration"/> is set.
Only superusers and users with the appropriate <literal>SET</literal>
privilege can change this setting.
</para>
@@ -8636,7 +8636,7 @@ COPY postgres_log FROM '/full/path/to/logfile.csv' WITH csv;
option is used, in the output of <xref linkend="sql-vacuum"/> when
the <literal>VERBOSE</literal> option is used, by autovacuum
for auto-vacuums and auto-analyzes, when <xref
- linkend="guc-log-autovacuum-min-duration"/> is set and by
+ linkend="guc-log-autovacuum-vacuum-min-duration"/> is set and by
<xref linkend="pgstatstatements"/>.
Only superusers and users with the appropriate <literal>SET</literal>
privilege can change this setting.
diff --git a/doc/src/sgml/maintenance.sgml b/doc/src/sgml/maintenance.sgml
index 600e4b3f2f3..84df5215580 100644
--- a/doc/src/sgml/maintenance.sgml
+++ b/doc/src/sgml/maintenance.sgml
@@ -636,7 +636,7 @@ SELECT datname, age(datfrozenxid) FROM pg_database;
<structfield>relminmxid</structfield> advanced, and the number of
newly frozen pages. The same details appear in the server log when
autovacuum logging (controlled by <xref
- linkend="guc-log-autovacuum-min-duration"/>) reports on a
+ linkend="guc-log-autovacuum-vacuum-min-duration"/>) reports on a
<command>VACUUM</command> operation executed by autovacuum.
</para>
</tip>
@@ -889,7 +889,7 @@ HINT: Execute a database-wide VACUUM in that database.
the next database will be processed as soon as the first worker finishes.
Each worker process will check each table within its database and
execute <command>VACUUM</command> and/or <command>ANALYZE</command> as needed.
- <xref linkend="guc-log-autovacuum-min-duration"/> can be set to monitor
+ <xref linkend="guc-log-autovacuum-vacuum-min-duration"/> can be set to monitor
autovacuum workers' activity.
</para>
diff --git a/doc/src/sgml/ref/create_table.sgml b/doc/src/sgml/ref/create_table.sgml
index 4a41b2f5530..66954c66ba6 100644
--- a/doc/src/sgml/ref/create_table.sgml
+++ b/doc/src/sgml/ref/create_table.sgml
@@ -1934,16 +1934,16 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</listitem>
</varlistentry>
- <varlistentry id="reloption-log-autovacuum-min-duration" xreflabel="log_autovacuum_min_duration">
- <term><literal>log_autovacuum_min_duration</literal>, <literal>toast.log_autovacuum_min_duration</literal> (<type>integer</type>)
+ <varlistentry id="reloption-log-autovacuum-vacuum-min-duration" xreflabel="log_autovacuum_vacuum_min_duration">
+ <term><literal>log_autovacuum_vacuum_min_duration</literal>, <literal>toast.log_autovacuum_vacuum_min_duration</literal> (<type>integer</type>)
<indexterm>
- <primary><varname>log_autovacuum_min_duration</varname></primary>
+ <primary><varname>log_autovacuum_vacuum_min_duration</varname></primary>
<secondary>storage parameter</secondary>
</indexterm>
</term>
<listitem>
<para>
- Per-table value for <xref linkend="guc-log-autovacuum-min-duration"/>
+ Per-table value for <xref linkend="guc-log-autovacuum-vacuum-min-duration"/>
parameter.
</para>
</listitem>
diff --git a/src/backend/access/common/reloptions.c b/src/backend/access/common/reloptions.c
index 50747c16396..4bc618a34f0 100644
--- a/src/backend/access/common/reloptions.c
+++ b/src/backend/access/common/reloptions.c
@@ -321,8 +321,8 @@ static relopt_int intRelOpts[] =
},
{
{
- "log_autovacuum_min_duration",
- "Sets the minimum execution time above which autovacuum actions will be logged",
+ "log_autovacuum_vacuum_min_duration",
+ "Sets the minimum execution time above which vacuum actions by autovacuum will be logged",
RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
ShareUpdateExclusiveLock
},
@@ -1894,8 +1894,8 @@ default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_max_age)},
{"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
- {"log_autovacuum_min_duration", RELOPT_TYPE_INT,
- offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_min_duration)},
+ {"log_autovacuum_vacuum_min_duration", RELOPT_TYPE_INT,
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_vacuum_min_duration)},
{"toast_tuple_target", RELOPT_TYPE_INT,
offsetof(StdRdOptions, toast_tuple_target)},
{"autovacuum_vacuum_cost_delay", RELOPT_TYPE_REAL,
diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index 09416450af9..86bb8083c46 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -636,7 +636,7 @@ heap_vacuum_rel(Relation rel, VacuumParams *params,
verbose = (params->options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params->log_min_duration >= 0));
+ params->log_vacuum_min_duration >= 0));
if (instrument)
{
pg_rusage_init(&ru0);
@@ -947,9 +947,9 @@ heap_vacuum_rel(Relation rel, VacuumParams *params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params->log_min_duration == 0 ||
+ if (verbose || params->log_vacuum_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params->log_min_duration))
+ params->log_vacuum_min_duration))
{
long secs_dur;
int usecs_dur;
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index 4fffb76e557..ba26b00cfb1 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -139,7 +139,7 @@ analyze_rel(Oid relid, RangeVar *relation,
* Make sure to generate only logs for ANALYZE in this case.
*/
onerel = vacuum_open_relation(relid, relation, params->options & ~(VACOPT_VACUUM),
- params->log_min_duration >= 0,
+ params->log_vacuum_min_duration >= 0,
ShareUpdateExclusiveLock);
/* leave if relation could not be opened or locked */
@@ -311,7 +311,7 @@ do_analyze_rel(Relation onerel, VacuumParams *params,
verbose = (params->options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params->log_min_duration >= 0));
+ params->log_vacuum_min_duration >= 0));
if (inh)
ereport(elevel,
(errmsg("analyzing \"%s.%s\" inheritance tree",
@@ -736,9 +736,9 @@ do_analyze_rel(Relation onerel, VacuumParams *params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params->log_min_duration == 0 ||
+ if (verbose || params->log_vacuum_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params->log_min_duration))
+ params->log_vacuum_min_duration))
{
long delay_in_ms;
WalUsage walusage;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 33a33bf6b1c..7e8d02d7a86 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -415,8 +415,8 @@ ExecVacuum(ParseState *pstate, VacuumStmt *vacstmt, bool isTopLevel)
/* user-invoked vacuum is never "for wraparound" */
params.is_wraparound = false;
- /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_min_duration */
- params.log_min_duration = -1;
+ /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_vacuum_min_duration */
+ params.log_vacuum_min_duration = -1;
/*
* Later, in vacuum_rel(), we check if a reloption override was specified.
@@ -2069,7 +2069,7 @@ vacuum_rel(Oid relid, RangeVar *relation, VacuumParams *params,
/* open the relation and get the appropriate lock on it */
rel = vacuum_open_relation(relid, relation, params->options,
- params->log_min_duration >= 0, lmode);
+ params->log_vacuum_min_duration >= 0, lmode);
/* leave if relation could not be opened or locked */
if (!rel)
diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c
index 451fb90a610..cc77bbd8f11 100644
--- a/src/backend/postmaster/autovacuum.c
+++ b/src/backend/postmaster/autovacuum.c
@@ -133,7 +133,7 @@ int autovacuum_multixact_freeze_max_age;
double autovacuum_vac_cost_delay;
int autovacuum_vac_cost_limit;
-int Log_autovacuum_min_duration = 600000;
+int Log_autovacuum_vac_min_duration = 600000;
/* the minimum allowed time between two awakenings of the launcher */
#define MIN_AUTOVAC_SLEEPTIME 100.0 /* milliseconds */
@@ -2791,7 +2791,7 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
int freeze_table_age;
int multixact_freeze_min_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
/*
* Calculate the vacuum cost parameters and the freeze ages. If there
@@ -2800,10 +2800,10 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
* defaults, autovacuum's own first and plain vacuum second.
*/
- /* -1 in autovac setting means use log_autovacuum_min_duration */
- log_min_duration = (avopts && avopts->log_min_duration >= 0)
- ? avopts->log_min_duration
- : Log_autovacuum_min_duration;
+ /* -1 in autovac setting means use log_autovacuum_vacuum_min_duration */
+ log_vacuum_min_duration = (avopts && avopts->log_vacuum_min_duration >= 0)
+ ? avopts->log_vacuum_min_duration
+ : Log_autovacuum_vac_min_duration;
/* these do not have autovacuum-specific settings */
freeze_min_age = (avopts && avopts->freeze_min_age >= 0)
@@ -2854,7 +2854,7 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
tab->at_params.multixact_freeze_min_age = multixact_freeze_min_age;
tab->at_params.multixact_freeze_table_age = multixact_freeze_table_age;
tab->at_params.is_wraparound = wraparound;
- tab->at_params.log_min_duration = log_min_duration;
+ tab->at_params.log_vacuum_min_duration = log_vacuum_min_duration;
tab->at_params.toast_parent = InvalidOid;
/*
diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c
index f04bfedb2fd..7ba26ebff5b 100644
--- a/src/backend/utils/misc/guc_tables.c
+++ b/src/backend/utils/misc/guc_tables.c
@@ -3169,13 +3169,14 @@ struct config_int ConfigureNamesInt[] =
},
{
- {"log_autovacuum_min_duration", PGC_SIGHUP, LOGGING_WHAT,
+ {"log_autovacuum_vacuum_min_duration", PGC_SIGHUP, LOGGING_WHAT,
gettext_noop("Sets the minimum execution time above which "
- "autovacuum actions will be logged."),
- gettext_noop("-1 disables logging autovacuum actions. 0 means log all autovacuum actions."),
+ "vacuum actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging vacuum actions by autovacuum. "
+ "0 means log all vacuum actions by autovacuum."),
GUC_UNIT_MS
},
- &Log_autovacuum_min_duration,
+ &Log_autovacuum_vac_min_duration,
600000, -1, INT_MAX,
NULL, NULL, NULL
},
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index 341f88adc87..90e02054acd 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -585,11 +585,11 @@
#debug_print_rewritten = off
#debug_print_plan = off
#debug_pretty_print = on
-#log_autovacuum_min_duration = 10min # log autovacuum activity;
- # -1 disables, 0 logs all actions and
- # their durations, > 0 logs only
- # actions running at least this number
- # of milliseconds.
+#log_autovacuum_vacuum_min_duration = 10min # log vacuum activity by autovacuum;
+ # -1 disables, 0 logs all actions and
+ # their durations, > 0 logs only
+ # actions running at least this number
+ # of milliseconds.
#log_checkpoints = on
#log_connections = '' # log aspects of connection setup
# options include receipt, authentication, authorization,
diff --git a/src/bin/psql/tab-complete.in.c b/src/bin/psql/tab-complete.in.c
index ec65ab79fec..27f63159e43 100644
--- a/src/bin/psql/tab-complete.in.c
+++ b/src/bin/psql/tab-complete.in.c
@@ -1386,7 +1386,7 @@ static const char *const table_storage_parameters[] = {
"autovacuum_vacuum_scale_factor",
"autovacuum_vacuum_threshold",
"fillfactor",
- "log_autovacuum_min_duration",
+ "log_autovacuum_vacuum_min_duration",
"parallel_workers",
"toast.autovacuum_enabled",
"toast.autovacuum_freeze_max_age",
@@ -1402,7 +1402,7 @@ static const char *const table_storage_parameters[] = {
"toast.autovacuum_vacuum_max_threshold",
"toast.autovacuum_vacuum_scale_factor",
"toast.autovacuum_vacuum_threshold",
- "toast.log_autovacuum_min_duration",
+ "toast.log_autovacuum_vacuum_min_duration",
"toast.vacuum_index_cleanup",
"toast.vacuum_max_eager_freeze_failure_rate",
"toast.vacuum_truncate",
diff --git a/src/include/commands/vacuum.h b/src/include/commands/vacuum.h
index bc37a80dc74..5a90b84e099 100644
--- a/src/include/commands/vacuum.h
+++ b/src/include/commands/vacuum.h
@@ -224,9 +224,9 @@ typedef struct VacuumParams
int multixact_freeze_table_age; /* multixact age at which to scan
* whole table */
bool is_wraparound; /* force a for-wraparound vacuum */
- int log_min_duration; /* minimum execution threshold in ms at
- * which autovacuum is logged, -1 to use
- * default */
+ int log_vacuum_min_duration; /* minimum execution threshold in ms
+ * at which vacuum by autovacuum is
+ * logged, -1 to use default */
VacOptValue index_cleanup; /* Do index vacuum and cleanup */
VacOptValue truncate; /* Truncate empty pages at the end */
Oid toast_parent; /* for privilege checks when recursing */
diff --git a/src/include/postmaster/autovacuum.h b/src/include/postmaster/autovacuum.h
index e8135f41a1c..4d0b44a4f7a 100644
--- a/src/include/postmaster/autovacuum.h
+++ b/src/include/postmaster/autovacuum.h
@@ -47,7 +47,7 @@ extern PGDLLIMPORT int autovacuum_vac_cost_limit;
/* autovacuum launcher PID, only valid when worker is shutting down */
extern PGDLLIMPORT int AutovacuumLauncherPid;
-extern PGDLLIMPORT int Log_autovacuum_min_duration;
+extern PGDLLIMPORT int Log_autovacuum_vac_min_duration;
/* Status inquiry functions */
extern bool AutoVacuumingActive(void);
diff --git a/src/include/utils/rel.h b/src/include/utils/rel.h
index b552359915f..23e47af9112 100644
--- a/src/include/utils/rel.h
+++ b/src/include/utils/rel.h
@@ -322,7 +322,7 @@ typedef struct AutoVacOpts
int multixact_freeze_min_age;
int multixact_freeze_max_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
float8 vacuum_cost_delay;
float8 vacuum_scale_factor;
float8 vacuum_ins_scale_factor;
diff --git a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
index 73d1ec4af19..9d64bee10eb 100644
--- a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
+++ b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
@@ -21,7 +21,7 @@ $node->append_conf(
autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
-log_autovacuum_min_duration = 0
+log_autovacuum_vacuum_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/modules/xid_wraparound/t/002_limits.pl b/src/test/modules/xid_wraparound/t/002_limits.pl
index aa1d8765d3a..db87477ae5d 100644
--- a/src/test/modules/xid_wraparound/t/002_limits.pl
+++ b/src/test/modules/xid_wraparound/t/002_limits.pl
@@ -28,7 +28,7 @@ $node->init;
$node->append_conf(
'postgresql.conf', qq[
autovacuum_naptime = 1s
-log_autovacuum_min_duration = 0
+log_autovacuum_vacuum_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/modules/xid_wraparound/t/003_wraparounds.pl b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
index 2aeaee8769c..59c04a1d781 100644
--- a/src/test/modules/xid_wraparound/t/003_wraparounds.pl
+++ b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
@@ -24,7 +24,7 @@ $node->append_conf(
autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
-log_autovacuum_min_duration = 0
+log_autovacuum_vacuum_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/regress/pg_regress.c b/src/test/regress/pg_regress.c
index 5d85dcc62f0..e2001acd4aa 100644
--- a/src/test/regress/pg_regress.c
+++ b/src/test/regress/pg_regress.c
@@ -2400,7 +2400,7 @@ regression_main(int argc, char *argv[],
bail("could not open \"%s\" for adding extra config: %m", buf);
fputs("\n# Configuration added by pg_regress\n\n", pg_conf);
- fputs("log_autovacuum_min_duration = 0\n", pg_conf);
+ fputs("log_autovacuum_vacuum_min_duration = 0\n", pg_conf);
fputs("log_checkpoints = on\n", pg_conf);
fputs("log_line_prefix = '%m %b[%p] %q%a '\n", pg_conf);
fputs("log_lock_waits = on\n", pg_conf);
diff --git a/src/tools/ci/pg_ci_base.conf b/src/tools/ci/pg_ci_base.conf
index 9cec5c2910d..d9bb408aab4 100644
--- a/src/tools/ci/pg_ci_base.conf
+++ b/src/tools/ci/pg_ci_base.conf
@@ -6,7 +6,7 @@ restart_after_crash = false
max_prepared_transactions = 10
# Settings that make logs more useful
-log_autovacuum_min_duration = 0
+log_autovacuum_vacuum_min_duration = 0
log_checkpoints = true
log_connections = all
log_disconnections = true
--
2.39.3
Hi,
On Tue, Jun 03, 2025 at 03:35:20PM +0900, Shinya Kato wrote:
I am proposing the introduction of two new GUC parameters,
log_autovacuum_{vacuum|analyze}_min_duration, to replace the existing
log_autovacuum_min_duration.
How about adding log_autoanalyze_min_duration instead? That would still
slightly retcon the log_autovacuum_min_duration meaning/semantics by no
longer logging autoanalyze unless the new GUC is set, but at least not
rename the GUC and make both shorter while still being comprehensible
IMO. Not sure what others think?
Michael
Thank you for the comment!
On Tue, Jun 3, 2025 at 4:42 PM Michael Banck <mbanck@gmx.net> wrote:
Hi,
On Tue, Jun 03, 2025 at 03:35:20PM +0900, Shinya Kato wrote:
I am proposing the introduction of two new GUC parameters,
log_autovacuum_{vacuum|analyze}_min_duration, to replace the existing
log_autovacuum_min_duration.How about adding log_autoanalyze_min_duration instead? That would still
slightly retcon the log_autovacuum_min_duration meaning/semantics by no
longer logging autoanalyze unless the new GUC is set, but at least not
rename the GUC and make both shorter while still being comprehensible
IMO. Not sure what others think?
I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.
https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUM
Shinya Kato
NTT OSS Center
Hi,
On Tue, Jun 03, 2025 at 05:25:40PM +0900, Shinya Kato wrote:
On Tue, Jun 3, 2025 at 4:42 PM Michael Banck <mbanck@gmx.net> wrote:
On Tue, Jun 03, 2025 at 03:35:20PM +0900, Shinya Kato wrote:
I am proposing the introduction of two new GUC parameters,
log_autovacuum_{vacuum|analyze}_min_duration, to replace the existing
log_autovacuum_min_duration.How about adding log_autoanalyze_min_duration instead? That would still
slightly retcon the log_autovacuum_min_duration meaning/semantics by no
longer logging autoanalyze unless the new GUC is set, but at least not
rename the GUC and make both shorter while still being comprehensible
IMO. Not sure what others think?I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.
https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUM
Right, but the GUCs that directly affect either vacuum or autovacuum
behaviour need the qualification (and then vacuum/analyze on top of it).
I think we have less constraints with the logging GUC and do not need to
mirror the behaviorial GUCs at all costs. But again, that is just my two
cents.
Unless we want to have 4 logging GUCs
(log_{auto,}vacuum_{vacuum,analyze}_min_duration) which I think would
be overkill?
Michael
On Tue, Jun 03, 2025 at 10:57:11AM +0200, Michael Banck wrote:
On Tue, Jun 03, 2025 at 05:25:40PM +0900, Shinya Kato wrote:
I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.
https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUMRight, but the GUCs that directly affect either vacuum or autovacuum
behaviour need the qualification (and then vacuum/analyze on top of it).
I think we have less constraints with the logging GUC and do not need to
mirror the behaviorial GUCs at all costs. But again, that is just my two
cents.
I lean towards log_autovacuum_{vacuum|analyze}_min_duration. If
log_autovacuum_min_duration didn't exist, that's probably the naming scheme
we'd go with. However, I'm not sure we can get away with renaming
log_autovacuum_min_duration. Presumably we'd need to at least keep it
around as a backward-compatibility GUC, and its behavior would probably
change, too (e.g., to only logging vacuums). Maybe that's acceptable if we
buy the assertion that autoanalyze is typically much faster than autovacuum
(and so autoanalyzes weren't getting logged, anyway).
--
nathan
On Tue, Jun 03, 2025 at 10:57:11AM +0200, Michael Banck wrote:
On Tue, Jun 03, 2025 at 05:25:40PM +0900, Shinya Kato wrote:
I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.
https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUMRight, but the GUCs that directly affect either vacuum or autovacuum
behaviour need the qualification (and then vacuum/analyze on top of it).
I think we have less constraints with the logging GUC and do not need to
mirror the behaviorial GUCs at all costs. But again, that is just my two
cents.I lean towards log_autovacuum_{vacuum|analyze}_min_duration. If
log_autovacuum_min_duration didn't exist, that's probably the naming scheme
we'd go with. However, I'm not sure we can get away with renaming
log_autovacuum_min_duration. Presumably we'd need to at least keep it
around as a backward-compatibility GUC, and its behavior would probably
change, too
I think deprecating a GUC like log_autovacuum_min_duration would be quite
difficult. May I suggest we keep its current behavior, which is to control
logging for both autoanalyze and autovacuum, and instead introduce only one
new GUC, log_autovacuum_analyze_min_duration, which defaults to -1? For
workloads that require different logging for autoanalyze, this new setting
can be enabled.
--
Sami Imseih
Amazon Web Services (AWS)
On 2025/06/04 4:32, Sami Imseih wrote:
On Tue, Jun 03, 2025 at 10:57:11AM +0200, Michael Banck wrote:
On Tue, Jun 03, 2025 at 05:25:40PM +0900, Shinya Kato wrote:
I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.
https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUMRight, but the GUCs that directly affect either vacuum or autovacuum
behaviour need the qualification (and then vacuum/analyze on top of it).
I think we have less constraints with the logging GUC and do not need to
mirror the behaviorial GUCs at all costs. But again, that is just my two
cents.I lean towards log_autovacuum_{vacuum|analyze}_min_duration. If
log_autovacuum_min_duration didn't exist, that's probably the naming scheme
we'd go with. However, I'm not sure we can get away with renaming
log_autovacuum_min_duration. Presumably we'd need to at least keep it
around as a backward-compatibility GUC, and its behavior would probably
change, tooI think deprecating a GUC like log_autovacuum_min_duration would be quite
difficult.
Also deprecating the log_autovacuum_min_duration reloption might be tricky.
If we remove support for it in v19, how should pg_dump handle tables with
this option set from older versions? Should it translate it into both
log_autovacuum_vacuum_min_duration and log_autovacuum_analyze_min_duration
during dump? Would pg_upgrade run into the same issue?
Regards,
--
Fujii Masao
NTT DATA Japan Corporation
HI
I vote log_autovacuum_{vacuum|analyze}_min_duration. Then don't remove
log_autovacuum_min_duration so easily!
On Wed, Jun 4, 2025 at 7:16 AM Fujii Masao <masao.fujii@oss.nttdata.com>
wrote:
Show quoted text
On 2025/06/04 4:32, Sami Imseih wrote:
On Tue, Jun 03, 2025 at 10:57:11AM +0200, Michael Banck wrote:
On Tue, Jun 03, 2025 at 05:25:40PM +0900, Shinya Kato wrote:
I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUM
Right, but the GUCs that directly affect either vacuum or autovacuum
behaviour need the qualification (and then vacuum/analyze on top ofit).
I think we have less constraints with the logging GUC and do not need
to
mirror the behaviorial GUCs at all costs. But again, that is just my
two
cents.
I lean towards log_autovacuum_{vacuum|analyze}_min_duration. If
log_autovacuum_min_duration didn't exist, that's probably the namingscheme
we'd go with. However, I'm not sure we can get away with renaming
log_autovacuum_min_duration. Presumably we'd need to at least keep it
around as a backward-compatibility GUC, and its behavior would probably
change, tooI think deprecating a GUC like log_autovacuum_min_duration would be quite
difficult.Also deprecating the log_autovacuum_min_duration reloption might be tricky.
If we remove support for it in v19, how should pg_dump handle tables with
this option set from older versions? Should it translate it into both
log_autovacuum_vacuum_min_duration and log_autovacuum_analyze_min_duration
during dump? Would pg_upgrade run into the same issue?Regards,
--
Fujii Masao
NTT DATA Japan Corporation
Thank you all for the comments!
On Wed, Jun 4, 2025 at 10:30 AM wenhui qiu <qiuwenhuifx@gmail.com> wrote:
HI
I vote log_autovacuum_{vacuum|analyze}_min_duration. Then don't remove log_autovacuum_min_duration so easily!On Wed, Jun 4, 2025 at 7:16 AM Fujii Masao <masao.fujii@oss.nttdata.com> wrote:
On 2025/06/04 4:32, Sami Imseih wrote:
On Tue, Jun 03, 2025 at 10:57:11AM +0200, Michael Banck wrote:
On Tue, Jun 03, 2025 at 05:25:40PM +0900, Shinya Kato wrote:
I surely think adding log_autoanalyze_min_duration is simpler and
shorter, but the reason I chose this GUC name is for consistency with
other autovacuum parameters. Existing autovacuum parameters that have
separate settings for vacuum and analyze operations follow the pattern
autovacuum_{vacuum|analyze}_*.
https://www.postgresql.org/docs/devel/runtime-config-vacuum.html#RUNTIME-CONFIG-AUTOVACUUMRight, but the GUCs that directly affect either vacuum or autovacuum
behaviour need the qualification (and then vacuum/analyze on top of it).
I think we have less constraints with the logging GUC and do not need to
mirror the behaviorial GUCs at all costs. But again, that is just my two
cents.I lean towards log_autovacuum_{vacuum|analyze}_min_duration. If
log_autovacuum_min_duration didn't exist, that's probably the naming scheme
we'd go with. However, I'm not sure we can get away with renaming
log_autovacuum_min_duration. Presumably we'd need to at least keep it
around as a backward-compatibility GUC, and its behavior would probably
change, tooI think deprecating a GUC like log_autovacuum_min_duration would be quite
difficult.Also deprecating the log_autovacuum_min_duration reloption might be tricky.
If we remove support for it in v19, how should pg_dump handle tables with
this option set from older versions? Should it translate it into both
log_autovacuum_vacuum_min_duration and log_autovacuum_analyze_min_duration
during dump? Would pg_upgrade run into the same issue?
I understand it's hard to deprecate log_autovacuum_min_duration. I
think there are three approaches that reflect your comments.
Approach 1:
- log_autovacuum_min_duration: Same behavior, which controls
autovacuum and autoanalyze logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.
Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.
Approach 3:
- log_autovacuum_min_duration: Retained for backward compatibility.
- log_autovacuum_{vacuum,analyze}_min_duration: New parameter.
Thoughts?
And I added a new entry for the next commitfest.
https://commitfest.postgresql.org/patch/5797/
--
Best regards,
Shinya Kato
NTT OSS Center
Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.
My vote is for this approach. It is probably OK to change the behavior of
log_autovacuum_min_duration, as the new GUC will have the same default
value.
log_autoanalyze_min_duration makes sense, especially since
"autoanalyze" is the term we already use in system views (e.g.,
pg_stat_all_tables.last_autoanalyze). I do not think we need to worry
about consistency with other autovacuum parameters (e.g.,
autovacuum_[vacuum|analyze]_threshold, etc.), because in this case we are
only talking about logging, so we have more flexibility in naming.
Initially, I was not sure if there is a use case in which someone would want
to turn off autovacuum logging but keep autoanalyze logging (or vice versa),
but there may be, and this will be more flexible.
--
Sami Imseih
On Thu, Jun 5, 2025 at 3:53 AM Sami Imseih <samimseih@gmail.com> wrote:
Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the behavior of
log_autovacuum_min_duration, as the new GUC will have the same default
value.
Thank you for voting. I also think this approach is reasonable to implement.
log_autoanalyze_min_duration makes sense, especially since
"autoanalyze" is the term we already use in system views (e.g.,
pg_stat_all_tables.last_autoanalyze). I do not think we need to worry
about consistency with other autovacuum parameters (e.g.,
autovacuum_[vacuum|analyze]_threshold, etc.), because in this case we are
only talking about logging, so we have more flexibility in naming.
+1.
Initially, I was not sure if there is a use case in which someone would
want
to turn off autovacuum logging but keep autoanalyze logging (or vice
versa),
but there may be, and this will be more flexible.
My concern is less about turning autovacuum and autoanalyze logs on or off
individually, and more about the fact that setting a large value for
log_autovacuum_min_duration prevents autoanalyze logs from being recorded.
--
Best regards,
Shinya Kato
NTT OSS Center
On Wed, Jun 11, 2025 at 1:49 PM Shinya Kato <shinya11.kato@gmail.com> wrote:
On Thu, Jun 5, 2025 at 3:53 AM Sami Imseih <samimseih@gmail.com> wrote:
Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the behavior of
log_autovacuum_min_duration, as the new GUC will have the same default
value.Thank you for voting. I also think this approach is reasonable to
implement.
A new patch is attached.
Thoughts?
--
Best regards,
Shinya Kato
NTT OSS Center
Attachments:
v2-0001-Add-log_autoanalyze_min_duration.patchapplication/octet-stream; name=v2-0001-Add-log_autoanalyze_min_duration.patchDownload
From d6f980cb710935549eb0b3d0cac0a830dd512318 Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Mon, 23 Jun 2025 16:20:48 +0900
Subject: [PATCH v2] Add log_autoanalyze_min_duration
The log output functionality of log_autovacuum_min_duration applies to
both VACUUM and ANALYZE, so it is not possible to separate the VACUUM
and ANALYZE log output thresholds. Logs are likely to be output only for
VACUUM and not for ANALYZE.
Therefore, we decided to separate the threshold for log output of VACUUM
by autovacuum (log_autovacuum_min_duration) and the threshold for log
output of ANALYZE by autovacuum (log_autoanalyze_min_duration).
---
doc/src/sgml/config.sgml | 41 +++++++++++++++----
doc/src/sgml/maintenance.sgml | 3 +-
doc/src/sgml/ref/create_table.sgml | 15 +++++++
src/backend/access/common/reloptions.c | 15 ++++++-
src/backend/access/heap/vacuumlazy.c | 6 +--
src/backend/commands/analyze.c | 8 ++--
src/backend/commands/vacuum.c | 10 +++--
src/backend/postmaster/autovacuum.c | 16 ++++++--
src/backend/utils/misc/guc_tables.c | 18 +++++++-
src/backend/utils/misc/postgresql.conf.sample | 7 +++-
src/bin/psql/tab-complete.in.c | 2 +
src/include/commands/vacuum.h | 9 ++--
src/include/postmaster/autovacuum.h | 1 +
src/include/utils/rel.h | 3 +-
.../xid_wraparound/t/001_emergency_vacuum.pl | 1 +
.../modules/xid_wraparound/t/002_limits.pl | 1 +
.../xid_wraparound/t/003_wraparounds.pl | 1 +
src/test/regress/pg_regress.c | 1 +
src/tools/ci/pg_ci_base.conf | 1 +
19 files changed, 128 insertions(+), 31 deletions(-)
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index b265cc89c9d..6a13de5bd06 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -7435,17 +7435,44 @@ local0.* /var/log/postgresql
</term>
<listitem>
<para>
- Causes each action executed by autovacuum to be logged if it ran for at
+ Causes vacuum action executed by autovacuum to be logged if it ran for at
least the specified amount of time. Setting this to zero logs
- all autovacuum actions. <literal>-1</literal> disables logging autovacuum
- actions. If this value is specified without units, it is taken as milliseconds.
- For example, if you set this to
- <literal>250ms</literal> then all automatic vacuums and analyzes that run
+ all vacuum actions by autovacuum. <literal>-1</literal> disables logging
+ vacuum actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic vacuums that run
250ms or longer will be logged. In addition, when this parameter is
set to any value other than <literal>-1</literal>, a message will be
- logged if an autovacuum action is skipped due to a conflicting lock or a
+ logged if a vacuum action by autovacuum is skipped due to a conflicting lock or a
concurrently dropped relation. The default is <literal>10min</literal>.
- Enabling this parameter can be helpful in tracking autovacuum activity.
+ Enabling this parameter can be helpful in tracking vacuum activity by autovacuum.
+ This parameter can only be set in the <filename>postgresql.conf</filename>
+ file or on the server command line; but the setting can be overridden for
+ individual tables by changing table storage parameters.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry id="guc-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><varname>log_autoanalyze_min_duration</varname> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>configuration parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Causes analyze action executed by autovacuum to be logged if it ran for at
+ least the specified amount of time. Setting this to zero logs
+ all analyze actions by autovacuum. <literal>-1</literal> disables logging
+ analyze actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic analyzes that run
+ 250ms or longer will be logged. In addition, when this parameter is
+ set to any value other than <literal>-1</literal>, a message will be
+ logged if an analyze action by autovacuum is skipped due to a conflicting lock or a
+ concurrently dropped relation. The default is <literal>10min</literal>.
+ Enabling this parameter can be helpful in tracking analyze activity by autovacuum.
This parameter can only be set in the <filename>postgresql.conf</filename>
file or on the server command line; but the setting can be overridden for
individual tables by changing table storage parameters.
diff --git a/doc/src/sgml/maintenance.sgml b/doc/src/sgml/maintenance.sgml
index 600e4b3f2f3..008254684c2 100644
--- a/doc/src/sgml/maintenance.sgml
+++ b/doc/src/sgml/maintenance.sgml
@@ -889,7 +889,8 @@ HINT: Execute a database-wide VACUUM in that database.
the next database will be processed as soon as the first worker finishes.
Each worker process will check each table within its database and
execute <command>VACUUM</command> and/or <command>ANALYZE</command> as needed.
- <xref linkend="guc-log-autovacuum-min-duration"/> can be set to monitor
+ <xref linkend="guc-log-autovacuum-min-duration"/> and
+ <xref linkend="guc-log-autoanalyze-min-duration"/> can be set to monitor
autovacuum workers' activity.
</para>
diff --git a/doc/src/sgml/ref/create_table.sgml b/doc/src/sgml/ref/create_table.sgml
index a5816918182..0f0d09bfa2e 100644
--- a/doc/src/sgml/ref/create_table.sgml
+++ b/doc/src/sgml/ref/create_table.sgml
@@ -1956,6 +1956,21 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</listitem>
</varlistentry>
+ <varlistentry id="reloption-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><literal>log_autoanalyze_min_duration</literal>, <literal>toast.log_autoanalyze_min_duration</literal> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>storage parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Per-table value for <xref linkend="guc-log-autoanalyze-min-duration"/>
+ parameter.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry id="reloption-vacuum-max-eager-freeze-failure-rate" xreflabel="vacuum_max_eager_freeze_failure_rate">
<term><literal>vacuum_max_eager_freeze_failure_rate</literal>, <literal>toast.vacuum_max_eager_freeze_failure_rate</literal> (<type>floating point</type>)
<indexterm>
diff --git a/src/backend/access/common/reloptions.c b/src/backend/access/common/reloptions.c
index 50747c16396..58fedc20e33 100644
--- a/src/backend/access/common/reloptions.c
+++ b/src/backend/access/common/reloptions.c
@@ -322,7 +322,16 @@ static relopt_int intRelOpts[] =
{
{
"log_autovacuum_min_duration",
- "Sets the minimum execution time above which autovacuum actions will be logged",
+ "Sets the minimum execution time above which vacuum actions by autovacuum will be logged",
+ RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
+ ShareUpdateExclusiveLock
+ },
+ -1, -1, INT_MAX
+ },
+ {
+ {
+ "log_autoanalyze_min_duration",
+ "Sets the minimum execution time above which analyze actions by autovacuum will be logged",
RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
ShareUpdateExclusiveLock
},
@@ -1895,7 +1904,9 @@ default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
{"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
{"log_autovacuum_min_duration", RELOPT_TYPE_INT,
- offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_min_duration)},
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_vacuum_min_duration)},
+ {"log_autoanalyze_min_duration", RELOPT_TYPE_INT,
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_analyze_min_duration)},
{"toast_tuple_target", RELOPT_TYPE_INT,
offsetof(StdRdOptions, toast_tuple_target)},
{"autovacuum_vacuum_cost_delay", RELOPT_TYPE_REAL,
diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index 09416450af9..86bb8083c46 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -636,7 +636,7 @@ heap_vacuum_rel(Relation rel, VacuumParams *params,
verbose = (params->options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params->log_min_duration >= 0));
+ params->log_vacuum_min_duration >= 0));
if (instrument)
{
pg_rusage_init(&ru0);
@@ -947,9 +947,9 @@ heap_vacuum_rel(Relation rel, VacuumParams *params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params->log_min_duration == 0 ||
+ if (verbose || params->log_vacuum_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params->log_min_duration))
+ params->log_vacuum_min_duration))
{
long secs_dur;
int usecs_dur;
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index 4fffb76e557..287ac50a71a 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -139,7 +139,7 @@ analyze_rel(Oid relid, RangeVar *relation,
* Make sure to generate only logs for ANALYZE in this case.
*/
onerel = vacuum_open_relation(relid, relation, params->options & ~(VACOPT_VACUUM),
- params->log_min_duration >= 0,
+ params->log_analyze_min_duration >= 0,
ShareUpdateExclusiveLock);
/* leave if relation could not be opened or locked */
@@ -311,7 +311,7 @@ do_analyze_rel(Relation onerel, VacuumParams *params,
verbose = (params->options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params->log_min_duration >= 0));
+ params->log_analyze_min_duration >= 0));
if (inh)
ereport(elevel,
(errmsg("analyzing \"%s.%s\" inheritance tree",
@@ -736,9 +736,9 @@ do_analyze_rel(Relation onerel, VacuumParams *params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params->log_min_duration == 0 ||
+ if (verbose || params->log_analyze_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params->log_min_duration))
+ params->log_analyze_min_duration))
{
long delay_in_ms;
WalUsage walusage;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 33a33bf6b1c..4c3ba5f9280 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -415,8 +415,12 @@ ExecVacuum(ParseState *pstate, VacuumStmt *vacstmt, bool isTopLevel)
/* user-invoked vacuum is never "for wraparound" */
params.is_wraparound = false;
- /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_min_duration */
- params.log_min_duration = -1;
+ /*
+ * user-invoked vacuum uses VACOPT_VERBOSE instead of
+ * log_vacuum_min_duration and log_analyze_min_duration
+ */
+ params.log_vacuum_min_duration = -1;
+ params.log_analyze_min_duration = -1;
/*
* Later, in vacuum_rel(), we check if a reloption override was specified.
@@ -2069,7 +2073,7 @@ vacuum_rel(Oid relid, RangeVar *relation, VacuumParams *params,
/* open the relation and get the appropriate lock on it */
rel = vacuum_open_relation(relid, relation, params->options,
- params->log_min_duration >= 0, lmode);
+ params->log_vacuum_min_duration >= 0, lmode);
/* leave if relation could not be opened or locked */
if (!rel)
diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c
index 451fb90a610..0d5291b55f5 100644
--- a/src/backend/postmaster/autovacuum.c
+++ b/src/backend/postmaster/autovacuum.c
@@ -134,6 +134,7 @@ double autovacuum_vac_cost_delay;
int autovacuum_vac_cost_limit;
int Log_autovacuum_min_duration = 600000;
+int Log_autoanalyze_min_duration = 600000;
/* the minimum allowed time between two awakenings of the launcher */
#define MIN_AUTOVAC_SLEEPTIME 100.0 /* milliseconds */
@@ -2791,7 +2792,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
int freeze_table_age;
int multixact_freeze_min_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
/*
* Calculate the vacuum cost parameters and the freeze ages. If there
@@ -2801,10 +2803,15 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
*/
/* -1 in autovac setting means use log_autovacuum_min_duration */
- log_min_duration = (avopts && avopts->log_min_duration >= 0)
- ? avopts->log_min_duration
+ log_vacuum_min_duration = (avopts && avopts->log_vacuum_min_duration >= 0)
+ ? avopts->log_vacuum_min_duration
: Log_autovacuum_min_duration;
+ /* -1 in autovac setting means use log_autoanalyze_min_duration */
+ log_analyze_min_duration = (avopts && avopts->log_analyze_min_duration >= 0)
+ ? avopts->log_analyze_min_duration
+ : Log_autoanalyze_min_duration;
+
/* these do not have autovacuum-specific settings */
freeze_min_age = (avopts && avopts->freeze_min_age >= 0)
? avopts->freeze_min_age
@@ -2854,7 +2861,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
tab->at_params.multixact_freeze_min_age = multixact_freeze_min_age;
tab->at_params.multixact_freeze_table_age = multixact_freeze_table_age;
tab->at_params.is_wraparound = wraparound;
- tab->at_params.log_min_duration = log_min_duration;
+ tab->at_params.log_vacuum_min_duration = log_vacuum_min_duration;
+ tab->at_params.log_analyze_min_duration = log_analyze_min_duration;
tab->at_params.toast_parent = InvalidOid;
/*
diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c
index f04bfedb2fd..0bfb38cfacc 100644
--- a/src/backend/utils/misc/guc_tables.c
+++ b/src/backend/utils/misc/guc_tables.c
@@ -3171,8 +3171,9 @@ struct config_int ConfigureNamesInt[] =
{
{"log_autovacuum_min_duration", PGC_SIGHUP, LOGGING_WHAT,
gettext_noop("Sets the minimum execution time above which "
- "autovacuum actions will be logged."),
- gettext_noop("-1 disables logging autovacuum actions. 0 means log all autovacuum actions."),
+ "vacuum actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging vacuum actions by autovacuum. "
+ "0 means log all vacuum actions by autovacuum."),
GUC_UNIT_MS
},
&Log_autovacuum_min_duration,
@@ -3180,6 +3181,19 @@ struct config_int ConfigureNamesInt[] =
NULL, NULL, NULL
},
+ {
+ {"log_autoanalyze_min_duration", PGC_SIGHUP, LOGGING_WHAT,
+ gettext_noop("Sets the minimum execution time above which "
+ "analyze actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging analyze actions by autovacuum. "
+ "0 means log all analyze actions by autovacuum."),
+ GUC_UNIT_MS
+ },
+ &Log_autoanalyze_min_duration,
+ 600000, -1, INT_MAX,
+ NULL, NULL, NULL
+ },
+
{
{"log_parameter_max_length", PGC_SUSET, LOGGING_WHAT,
gettext_noop("Sets the maximum length in bytes of data logged for bind "
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index 341f88adc87..d2ed29230ce 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -585,7 +585,12 @@
#debug_print_rewritten = off
#debug_print_plan = off
#debug_pretty_print = on
-#log_autovacuum_min_duration = 10min # log autovacuum activity;
+#log_autovacuum_min_duration = 10min # log vacuum activity by autovacuum;
+ # -1 disables, 0 logs all actions and
+ # their durations, > 0 logs only
+ # actions running at least this number
+ # of milliseconds.
+#log_autoanalyze_min_duration = 10min # log analyze activity by autovacuum;
# -1 disables, 0 logs all actions and
# their durations, > 0 logs only
# actions running at least this number
diff --git a/src/bin/psql/tab-complete.in.c b/src/bin/psql/tab-complete.in.c
index 2c0b4f28c14..5bb5b26243e 100644
--- a/src/bin/psql/tab-complete.in.c
+++ b/src/bin/psql/tab-complete.in.c
@@ -1387,6 +1387,7 @@ static const char *const table_storage_parameters[] = {
"autovacuum_vacuum_threshold",
"fillfactor",
"log_autovacuum_min_duration",
+ "log_autoanalyze_min_duration",
"parallel_workers",
"toast.autovacuum_enabled",
"toast.autovacuum_freeze_max_age",
@@ -1403,6 +1404,7 @@ static const char *const table_storage_parameters[] = {
"toast.autovacuum_vacuum_scale_factor",
"toast.autovacuum_vacuum_threshold",
"toast.log_autovacuum_min_duration",
+ "toast.log_autoanalyze_min_duration",
"toast.vacuum_index_cleanup",
"toast.vacuum_max_eager_freeze_failure_rate",
"toast.vacuum_truncate",
diff --git a/src/include/commands/vacuum.h b/src/include/commands/vacuum.h
index bc37a80dc74..f91df4c5dc8 100644
--- a/src/include/commands/vacuum.h
+++ b/src/include/commands/vacuum.h
@@ -224,9 +224,12 @@ typedef struct VacuumParams
int multixact_freeze_table_age; /* multixact age at which to scan
* whole table */
bool is_wraparound; /* force a for-wraparound vacuum */
- int log_min_duration; /* minimum execution threshold in ms at
- * which autovacuum is logged, -1 to use
- * default */
+ int log_vacuum_min_duration; /* minimum execution threshold in ms
+ * at which vacuum by autovacuum is
+ * logged, -1 to use default */
+ int log_analyze_min_duration; /* minimum execution threshold in ms
+ * at which analyze by autovacuum is
+ * logged, -1 to use default */
VacOptValue index_cleanup; /* Do index vacuum and cleanup */
VacOptValue truncate; /* Truncate empty pages at the end */
Oid toast_parent; /* for privilege checks when recursing */
diff --git a/src/include/postmaster/autovacuum.h b/src/include/postmaster/autovacuum.h
index e8135f41a1c..023ac6d5fa8 100644
--- a/src/include/postmaster/autovacuum.h
+++ b/src/include/postmaster/autovacuum.h
@@ -48,6 +48,7 @@ extern PGDLLIMPORT int autovacuum_vac_cost_limit;
extern PGDLLIMPORT int AutovacuumLauncherPid;
extern PGDLLIMPORT int Log_autovacuum_min_duration;
+extern PGDLLIMPORT int Log_autoanalyze_min_duration;
/* Status inquiry functions */
extern bool AutoVacuumingActive(void);
diff --git a/src/include/utils/rel.h b/src/include/utils/rel.h
index b552359915f..e63aa31d151 100644
--- a/src/include/utils/rel.h
+++ b/src/include/utils/rel.h
@@ -322,7 +322,8 @@ typedef struct AutoVacOpts
int multixact_freeze_min_age;
int multixact_freeze_max_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
float8 vacuum_cost_delay;
float8 vacuum_scale_factor;
float8 vacuum_ins_scale_factor;
diff --git a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
index 73d1ec4af19..59870956631 100644
--- a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
+++ b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
@@ -22,6 +22,7 @@ autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/modules/xid_wraparound/t/002_limits.pl b/src/test/modules/xid_wraparound/t/002_limits.pl
index aa1d8765d3a..05bafa12d98 100644
--- a/src/test/modules/xid_wraparound/t/002_limits.pl
+++ b/src/test/modules/xid_wraparound/t/002_limits.pl
@@ -29,6 +29,7 @@ $node->append_conf(
'postgresql.conf', qq[
autovacuum_naptime = 1s
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/modules/xid_wraparound/t/003_wraparounds.pl b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
index 2aeaee8769c..083191de06e 100644
--- a/src/test/modules/xid_wraparound/t/003_wraparounds.pl
+++ b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
@@ -25,6 +25,7 @@ autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/regress/pg_regress.c b/src/test/regress/pg_regress.c
index 5d85dcc62f0..399f1634a1c 100644
--- a/src/test/regress/pg_regress.c
+++ b/src/test/regress/pg_regress.c
@@ -2401,6 +2401,7 @@ regression_main(int argc, char *argv[],
fputs("\n# Configuration added by pg_regress\n\n", pg_conf);
fputs("log_autovacuum_min_duration = 0\n", pg_conf);
+ fputs("log_autoanalyze_min_duration = 0\n", pg_conf);
fputs("log_checkpoints = on\n", pg_conf);
fputs("log_line_prefix = '%m %b[%p] %q%a '\n", pg_conf);
fputs("log_lock_waits = on\n", pg_conf);
diff --git a/src/tools/ci/pg_ci_base.conf b/src/tools/ci/pg_ci_base.conf
index 9cec5c2910d..2f9c5b1cd27 100644
--- a/src/tools/ci/pg_ci_base.conf
+++ b/src/tools/ci/pg_ci_base.conf
@@ -7,6 +7,7 @@ max_prepared_transactions = 10
# Settings that make logs more useful
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
log_checkpoints = true
log_connections = all
log_disconnections = true
--
2.39.3
On Mon, Jun 23, 2025 at 4:24 PM Shinya Kato <shinya11.kato@gmail.com> wrote:
On Wed, Jun 11, 2025 at 1:49 PM Shinya Kato <shinya11.kato@gmail.com> wrote:
On Thu, Jun 5, 2025 at 3:53 AM Sami Imseih <samimseih@gmail.com> wrote:
Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the behavior of
log_autovacuum_min_duration, as the new GUC will have the same default
value.Thank you for voting. I also think this approach is reasonable to implement.
A new patch is attached.
Thoughts?
Rebased.
--
Best regards,
Shinya Kato
NTT OSS Center
Attachments:
v3-0001-Add-log_autoanalyze_min_duration.patchapplication/octet-stream; name=v3-0001-Add-log_autoanalyze_min_duration.patchDownload
From 30242cf1e1c5e0c4481c86e1859a827a99e281a1 Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Mon, 23 Jun 2025 16:20:48 +0900
Subject: [PATCH v3] Add log_autoanalyze_min_duration
The log output functionality of log_autovacuum_min_duration applies to
both VACUUM and ANALYZE, so it is not possible to separate the VACUUM
and ANALYZE log output thresholds. Logs are likely to be output only for
VACUUM and not for ANALYZE.
Therefore, we decided to separate the threshold for log output of VACUUM
by autovacuum (log_autovacuum_min_duration) and the threshold for log
output of ANALYZE by autovacuum (log_autoanalyze_min_duration).
---
doc/src/sgml/config.sgml | 41 +++++++++++++++----
doc/src/sgml/maintenance.sgml | 3 +-
doc/src/sgml/ref/create_table.sgml | 15 +++++++
src/backend/access/common/reloptions.c | 15 ++++++-
src/backend/access/heap/vacuumlazy.c | 6 +--
src/backend/commands/analyze.c | 8 ++--
src/backend/commands/vacuum.c | 10 +++--
src/backend/postmaster/autovacuum.c | 16 ++++++--
src/backend/utils/misc/guc_tables.c | 18 +++++++-
src/backend/utils/misc/postgresql.conf.sample | 7 +++-
src/bin/psql/tab-complete.in.c | 2 +
src/include/commands/vacuum.h | 9 ++--
src/include/postmaster/autovacuum.h | 1 +
src/include/utils/rel.h | 3 +-
.../xid_wraparound/t/001_emergency_vacuum.pl | 1 +
.../modules/xid_wraparound/t/002_limits.pl | 1 +
.../xid_wraparound/t/003_wraparounds.pl | 1 +
src/test/regress/pg_regress.c | 1 +
src/tools/ci/pg_ci_base.conf | 1 +
19 files changed, 128 insertions(+), 31 deletions(-)
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 59a0874528a..add6ea9adbd 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -7435,17 +7435,44 @@ local0.* /var/log/postgresql
</term>
<listitem>
<para>
- Causes each action executed by autovacuum to be logged if it ran for at
+ Causes vacuum action executed by autovacuum to be logged if it ran for at
least the specified amount of time. Setting this to zero logs
- all autovacuum actions. <literal>-1</literal> disables logging autovacuum
- actions. If this value is specified without units, it is taken as milliseconds.
- For example, if you set this to
- <literal>250ms</literal> then all automatic vacuums and analyzes that run
+ all vacuum actions by autovacuum. <literal>-1</literal> disables logging
+ vacuum actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic vacuums that run
250ms or longer will be logged. In addition, when this parameter is
set to any value other than <literal>-1</literal>, a message will be
- logged if an autovacuum action is skipped due to a conflicting lock or a
+ logged if a vacuum action by autovacuum is skipped due to a conflicting lock or a
concurrently dropped relation. The default is <literal>10min</literal>.
- Enabling this parameter can be helpful in tracking autovacuum activity.
+ Enabling this parameter can be helpful in tracking vacuum activity by autovacuum.
+ This parameter can only be set in the <filename>postgresql.conf</filename>
+ file or on the server command line; but the setting can be overridden for
+ individual tables by changing table storage parameters.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry id="guc-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><varname>log_autoanalyze_min_duration</varname> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>configuration parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Causes analyze action executed by autovacuum to be logged if it ran for at
+ least the specified amount of time. Setting this to zero logs
+ all analyze actions by autovacuum. <literal>-1</literal> disables logging
+ analyze actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic analyzes that run
+ 250ms or longer will be logged. In addition, when this parameter is
+ set to any value other than <literal>-1</literal>, a message will be
+ logged if an analyze action by autovacuum is skipped due to a conflicting lock or a
+ concurrently dropped relation. The default is <literal>10min</literal>.
+ Enabling this parameter can be helpful in tracking analyze activity by autovacuum.
This parameter can only be set in the <filename>postgresql.conf</filename>
file or on the server command line; but the setting can be overridden for
individual tables by changing table storage parameters.
diff --git a/doc/src/sgml/maintenance.sgml b/doc/src/sgml/maintenance.sgml
index e7a9f58c015..dc59c88319e 100644
--- a/doc/src/sgml/maintenance.sgml
+++ b/doc/src/sgml/maintenance.sgml
@@ -892,7 +892,8 @@ HINT: Execute a database-wide VACUUM in that database.
the next database will be processed as soon as the first worker finishes.
Each worker process will check each table within its database and
execute <command>VACUUM</command> and/or <command>ANALYZE</command> as needed.
- <xref linkend="guc-log-autovacuum-min-duration"/> can be set to monitor
+ <xref linkend="guc-log-autovacuum-min-duration"/> and
+ <xref linkend="guc-log-autoanalyze-min-duration"/> can be set to monitor
autovacuum workers' activity.
</para>
diff --git a/doc/src/sgml/ref/create_table.sgml b/doc/src/sgml/ref/create_table.sgml
index dc000e913c1..9d59d00f1d4 100644
--- a/doc/src/sgml/ref/create_table.sgml
+++ b/doc/src/sgml/ref/create_table.sgml
@@ -1966,6 +1966,21 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</listitem>
</varlistentry>
+ <varlistentry id="reloption-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><literal>log_autoanalyze_min_duration</literal>, <literal>toast.log_autoanalyze_min_duration</literal> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>storage parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Per-table value for <xref linkend="guc-log-autoanalyze-min-duration"/>
+ parameter.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry id="reloption-vacuum-max-eager-freeze-failure-rate" xreflabel="vacuum_max_eager_freeze_failure_rate">
<term><literal>vacuum_max_eager_freeze_failure_rate</literal>, <literal>toast.vacuum_max_eager_freeze_failure_rate</literal> (<type>floating point</type>)
<indexterm>
diff --git a/src/backend/access/common/reloptions.c b/src/backend/access/common/reloptions.c
index 50747c16396..58fedc20e33 100644
--- a/src/backend/access/common/reloptions.c
+++ b/src/backend/access/common/reloptions.c
@@ -322,7 +322,16 @@ static relopt_int intRelOpts[] =
{
{
"log_autovacuum_min_duration",
- "Sets the minimum execution time above which autovacuum actions will be logged",
+ "Sets the minimum execution time above which vacuum actions by autovacuum will be logged",
+ RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
+ ShareUpdateExclusiveLock
+ },
+ -1, -1, INT_MAX
+ },
+ {
+ {
+ "log_autoanalyze_min_duration",
+ "Sets the minimum execution time above which analyze actions by autovacuum will be logged",
RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
ShareUpdateExclusiveLock
},
@@ -1895,7 +1904,9 @@ default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
{"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
{"log_autovacuum_min_duration", RELOPT_TYPE_INT,
- offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_min_duration)},
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_vacuum_min_duration)},
+ {"log_autoanalyze_min_duration", RELOPT_TYPE_INT,
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_analyze_min_duration)},
{"toast_tuple_target", RELOPT_TYPE_INT,
offsetof(StdRdOptions, toast_tuple_target)},
{"autovacuum_vacuum_cost_delay", RELOPT_TYPE_REAL,
diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index 75979530897..bd3c7ff2013 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -636,7 +636,7 @@ heap_vacuum_rel(Relation rel, const VacuumParams params,
verbose = (params.options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params.log_min_duration >= 0));
+ params.log_vacuum_min_duration >= 0));
if (instrument)
{
pg_rusage_init(&ru0);
@@ -947,9 +947,9 @@ heap_vacuum_rel(Relation rel, const VacuumParams params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params.log_min_duration == 0 ||
+ if (verbose || params.log_vacuum_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params.log_min_duration))
+ params.log_vacuum_min_duration))
{
long secs_dur;
int usecs_dur;
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index 7111d5d5334..ee0bb63b088 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -139,7 +139,7 @@ analyze_rel(Oid relid, RangeVar *relation,
* Make sure to generate only logs for ANALYZE in this case.
*/
onerel = vacuum_open_relation(relid, relation, params.options & ~(VACOPT_VACUUM),
- params.log_min_duration >= 0,
+ params.log_analyze_min_duration >= 0,
ShareUpdateExclusiveLock);
/* leave if relation could not be opened or locked */
@@ -311,7 +311,7 @@ do_analyze_rel(Relation onerel, const VacuumParams params,
verbose = (params.options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params.log_min_duration >= 0));
+ params.log_analyze_min_duration >= 0));
if (inh)
ereport(elevel,
(errmsg("analyzing \"%s.%s\" inheritance tree",
@@ -736,9 +736,9 @@ do_analyze_rel(Relation onerel, const VacuumParams params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params.log_min_duration == 0 ||
+ if (verbose || params.log_analyze_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params.log_min_duration))
+ params.log_analyze_min_duration))
{
long delay_in_ms;
WalUsage walusage;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 733ef40ae7c..6694a705be7 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -416,8 +416,12 @@ ExecVacuum(ParseState *pstate, VacuumStmt *vacstmt, bool isTopLevel)
/* user-invoked vacuum is never "for wraparound" */
params.is_wraparound = false;
- /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_min_duration */
- params.log_min_duration = -1;
+ /*
+ * user-invoked vacuum uses VACOPT_VERBOSE instead of
+ * log_vacuum_min_duration and log_analyze_min_duration
+ */
+ params.log_vacuum_min_duration = -1;
+ params.log_analyze_min_duration = -1;
/*
* Later, in vacuum_rel(), we check if a reloption override was specified.
@@ -2073,7 +2077,7 @@ vacuum_rel(Oid relid, RangeVar *relation, VacuumParams params,
/* open the relation and get the appropriate lock on it */
rel = vacuum_open_relation(relid, relation, params.options,
- params.log_min_duration >= 0, lmode);
+ params.log_vacuum_min_duration >= 0, lmode);
/* leave if relation could not be opened or locked */
if (!rel)
diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c
index 9474095f271..07bb320ff11 100644
--- a/src/backend/postmaster/autovacuum.c
+++ b/src/backend/postmaster/autovacuum.c
@@ -134,6 +134,7 @@ double autovacuum_vac_cost_delay;
int autovacuum_vac_cost_limit;
int Log_autovacuum_min_duration = 600000;
+int Log_autoanalyze_min_duration = 600000;
/* the minimum allowed time between two awakenings of the launcher */
#define MIN_AUTOVAC_SLEEPTIME 100.0 /* milliseconds */
@@ -2791,7 +2792,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
int freeze_table_age;
int multixact_freeze_min_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
/*
* Calculate the vacuum cost parameters and the freeze ages. If there
@@ -2801,10 +2803,15 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
*/
/* -1 in autovac setting means use log_autovacuum_min_duration */
- log_min_duration = (avopts && avopts->log_min_duration >= 0)
- ? avopts->log_min_duration
+ log_vacuum_min_duration = (avopts && avopts->log_vacuum_min_duration >= 0)
+ ? avopts->log_vacuum_min_duration
: Log_autovacuum_min_duration;
+ /* -1 in autovac setting means use log_autoanalyze_min_duration */
+ log_analyze_min_duration = (avopts && avopts->log_analyze_min_duration >= 0)
+ ? avopts->log_analyze_min_duration
+ : Log_autoanalyze_min_duration;
+
/* these do not have autovacuum-specific settings */
freeze_min_age = (avopts && avopts->freeze_min_age >= 0)
? avopts->freeze_min_age
@@ -2854,7 +2861,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
tab->at_params.multixact_freeze_min_age = multixact_freeze_min_age;
tab->at_params.multixact_freeze_table_age = multixact_freeze_table_age;
tab->at_params.is_wraparound = wraparound;
- tab->at_params.log_min_duration = log_min_duration;
+ tab->at_params.log_vacuum_min_duration = log_vacuum_min_duration;
+ tab->at_params.log_analyze_min_duration = log_analyze_min_duration;
tab->at_params.toast_parent = InvalidOid;
/*
diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c
index 511dc32d519..11fbd48c331 100644
--- a/src/backend/utils/misc/guc_tables.c
+++ b/src/backend/utils/misc/guc_tables.c
@@ -3171,8 +3171,9 @@ struct config_int ConfigureNamesInt[] =
{
{"log_autovacuum_min_duration", PGC_SIGHUP, LOGGING_WHAT,
gettext_noop("Sets the minimum execution time above which "
- "autovacuum actions will be logged."),
- gettext_noop("-1 disables logging autovacuum actions. 0 means log all autovacuum actions."),
+ "vacuum actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging vacuum actions by autovacuum. "
+ "0 means log all vacuum actions by autovacuum."),
GUC_UNIT_MS
},
&Log_autovacuum_min_duration,
@@ -3180,6 +3181,19 @@ struct config_int ConfigureNamesInt[] =
NULL, NULL, NULL
},
+ {
+ {"log_autoanalyze_min_duration", PGC_SIGHUP, LOGGING_WHAT,
+ gettext_noop("Sets the minimum execution time above which "
+ "analyze actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging analyze actions by autovacuum. "
+ "0 means log all analyze actions by autovacuum."),
+ GUC_UNIT_MS
+ },
+ &Log_autoanalyze_min_duration,
+ 600000, -1, INT_MAX,
+ NULL, NULL, NULL
+ },
+
{
{"log_parameter_max_length", PGC_SUSET, LOGGING_WHAT,
gettext_noop("Sets the maximum length in bytes of data logged for bind "
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index 341f88adc87..d2ed29230ce 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -585,7 +585,12 @@
#debug_print_rewritten = off
#debug_print_plan = off
#debug_pretty_print = on
-#log_autovacuum_min_duration = 10min # log autovacuum activity;
+#log_autovacuum_min_duration = 10min # log vacuum activity by autovacuum;
+ # -1 disables, 0 logs all actions and
+ # their durations, > 0 logs only
+ # actions running at least this number
+ # of milliseconds.
+#log_autoanalyze_min_duration = 10min # log analyze activity by autovacuum;
# -1 disables, 0 logs all actions and
# their durations, > 0 logs only
# actions running at least this number
diff --git a/src/bin/psql/tab-complete.in.c b/src/bin/psql/tab-complete.in.c
index 8c2ea0b9587..154540a03e8 100644
--- a/src/bin/psql/tab-complete.in.c
+++ b/src/bin/psql/tab-complete.in.c
@@ -1395,6 +1395,7 @@ static const char *const table_storage_parameters[] = {
"autovacuum_vacuum_threshold",
"fillfactor",
"log_autovacuum_min_duration",
+ "log_autoanalyze_min_duration",
"parallel_workers",
"toast.autovacuum_enabled",
"toast.autovacuum_freeze_max_age",
@@ -1411,6 +1412,7 @@ static const char *const table_storage_parameters[] = {
"toast.autovacuum_vacuum_scale_factor",
"toast.autovacuum_vacuum_threshold",
"toast.log_autovacuum_min_duration",
+ "toast.log_autoanalyze_min_duration",
"toast.vacuum_index_cleanup",
"toast.vacuum_max_eager_freeze_failure_rate",
"toast.vacuum_truncate",
diff --git a/src/include/commands/vacuum.h b/src/include/commands/vacuum.h
index 14eeccbd718..7b9b29e673f 100644
--- a/src/include/commands/vacuum.h
+++ b/src/include/commands/vacuum.h
@@ -224,9 +224,12 @@ typedef struct VacuumParams
int multixact_freeze_table_age; /* multixact age at which to scan
* whole table */
bool is_wraparound; /* force a for-wraparound vacuum */
- int log_min_duration; /* minimum execution threshold in ms at
- * which autovacuum is logged, -1 to use
- * default */
+ int log_vacuum_min_duration; /* minimum execution threshold in ms
+ * at which vacuum by autovacuum is
+ * logged, -1 to use default */
+ int log_analyze_min_duration; /* minimum execution threshold in ms
+ * at which analyze by autovacuum is
+ * logged, -1 to use default */
VacOptValue index_cleanup; /* Do index vacuum and cleanup */
VacOptValue truncate; /* Truncate empty pages at the end */
Oid toast_parent; /* for privilege checks when recursing */
diff --git a/src/include/postmaster/autovacuum.h b/src/include/postmaster/autovacuum.h
index e8135f41a1c..023ac6d5fa8 100644
--- a/src/include/postmaster/autovacuum.h
+++ b/src/include/postmaster/autovacuum.h
@@ -48,6 +48,7 @@ extern PGDLLIMPORT int autovacuum_vac_cost_limit;
extern PGDLLIMPORT int AutovacuumLauncherPid;
extern PGDLLIMPORT int Log_autovacuum_min_duration;
+extern PGDLLIMPORT int Log_autoanalyze_min_duration;
/* Status inquiry functions */
extern bool AutoVacuumingActive(void);
diff --git a/src/include/utils/rel.h b/src/include/utils/rel.h
index b552359915f..e63aa31d151 100644
--- a/src/include/utils/rel.h
+++ b/src/include/utils/rel.h
@@ -322,7 +322,8 @@ typedef struct AutoVacOpts
int multixact_freeze_min_age;
int multixact_freeze_max_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
float8 vacuum_cost_delay;
float8 vacuum_scale_factor;
float8 vacuum_ins_scale_factor;
diff --git a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
index 73d1ec4af19..59870956631 100644
--- a/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
+++ b/src/test/modules/xid_wraparound/t/001_emergency_vacuum.pl
@@ -22,6 +22,7 @@ autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/modules/xid_wraparound/t/002_limits.pl b/src/test/modules/xid_wraparound/t/002_limits.pl
index aa1d8765d3a..05bafa12d98 100644
--- a/src/test/modules/xid_wraparound/t/002_limits.pl
+++ b/src/test/modules/xid_wraparound/t/002_limits.pl
@@ -29,6 +29,7 @@ $node->append_conf(
'postgresql.conf', qq[
autovacuum_naptime = 1s
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/modules/xid_wraparound/t/003_wraparounds.pl b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
index 2aeaee8769c..083191de06e 100644
--- a/src/test/modules/xid_wraparound/t/003_wraparounds.pl
+++ b/src/test/modules/xid_wraparound/t/003_wraparounds.pl
@@ -25,6 +25,7 @@ autovacuum_naptime = 1s
# so it's easier to verify the order of operations
autovacuum_max_workers = 1
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
]);
$node->start;
$node->safe_psql('postgres', 'CREATE EXTENSION xid_wraparound');
diff --git a/src/test/regress/pg_regress.c b/src/test/regress/pg_regress.c
index 5d85dcc62f0..399f1634a1c 100644
--- a/src/test/regress/pg_regress.c
+++ b/src/test/regress/pg_regress.c
@@ -2401,6 +2401,7 @@ regression_main(int argc, char *argv[],
fputs("\n# Configuration added by pg_regress\n\n", pg_conf);
fputs("log_autovacuum_min_duration = 0\n", pg_conf);
+ fputs("log_autoanalyze_min_duration = 0\n", pg_conf);
fputs("log_checkpoints = on\n", pg_conf);
fputs("log_line_prefix = '%m %b[%p] %q%a '\n", pg_conf);
fputs("log_lock_waits = on\n", pg_conf);
diff --git a/src/tools/ci/pg_ci_base.conf b/src/tools/ci/pg_ci_base.conf
index 695e0a0d6ec..ff05646c90e 100644
--- a/src/tools/ci/pg_ci_base.conf
+++ b/src/tools/ci/pg_ci_base.conf
@@ -7,6 +7,7 @@ max_prepared_transactions = 10
# Settings that make logs more useful
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
log_checkpoints = true
log_connections = all
log_disconnections = true
--
2.39.3
Hi,
2025-07-02 15:37 に Shinya Kato wrote:
On Mon, Jun 23, 2025 at 4:24 PM Shinya Kato <shinya11.kato@gmail.com>
wrote:On Wed, Jun 11, 2025 at 1:49 PM Shinya Kato <shinya11.kato@gmail.com>
wrote:On Thu, Jun 5, 2025 at 3:53 AM Sami Imseih <samimseih@gmail.com>
wrote:Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the
behavior of
log_autovacuum_min_duration, as the new GUC will have the same
default
value.Thank you for voting. I also think this approach is reasonable to
implement.A new patch is attached.
Thoughts?
I reviewed this patch.
I also have no particular objections to the Approach 2.
+ <term><literal>log_autoanalyze_min_duration</literal>,
<literal>toast.log_autoanalyze_min_duration</literal>(<type>integer</type>)
(snip)
+ "toast.log_autoanalyze_min_duration",
This patch adds the log_autoanalyze_min_duration parameter fot TOAST
tables.
However since PostgreSQL currently does not support ANALYZE on TOAST
tables,
isn't this parameter unnecessary?
Best regards,
--
Kasahara Tatsuhito
NTT DATA Japan Corporation
Hi,
On Wed, Aug 13, 2025 at 5:44 PM kasaharatt <kasaharatt@oss.nttdata.com> wrote:
Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the
behavior of
log_autovacuum_min_duration, as the new GUC will have the same
default
value.Thank you for voting. I also think this approach is reasonable to
implement.A new patch is attached.
Thoughts?I reviewed this patch.
I also have no particular objections to the Approach 2.
Thank you for the review!
+ <term><literal>log_autoanalyze_min_duration</literal>,
<literal>toast.log_autoanalyze_min_duration</literal>(<type>integer</type>)(snip)
+ "toast.log_autoanalyze_min_duration",
This patch adds the log_autoanalyze_min_duration parameter fot TOAST
tables.
However since PostgreSQL currently does not support ANALYZE on TOAST
tables,
isn't this parameter unnecessary?
You're right; that was a mistake. I've fixed it in the v4 patch.
+log_autoanalyze_min_duration = 0
Additionally, I removed the above setting from the test files in
src/test/modules/xid_wraparound/t/ (001_emergency_vacuum.pl,
002_limits.pl, 003_wraparounds.pl). The reason is that these tests
check for autovacuum logs, not autoanalyze logs. You can run the test
with the following command:
make check -C src/test/modules/xid_wraparound PG_TEST_EXTRA='xid_wraparound'
--
Best regards,
Shinya Kato
NTT OSS Center
Attachments:
v4-0001-Add-log_autoanalyze_min_duration.patchapplication/octet-stream; name=v4-0001-Add-log_autoanalyze_min_duration.patchDownload
From 611f211a19d5f414af04ac2cfc5946788d682321 Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Thu, 14 Aug 2025 11:58:08 +0900
Subject: [PATCH v4] Add log_autoanalyze_min_duration
The log output functionality of log_autovacuum_min_duration applies to
both VACUUM and ANALYZE, so it is not possible to separate the VACUUM
and ANALYZE log output thresholds. Logs are likely to be output only for
VACUUM and not for ANALYZE.
Therefore, we decided to separate the threshold for log output of VACUUM
by autovacuum (log_autovacuum_min_duration) and the threshold for log
output of ANALYZE by autovacuum (log_autoanalyze_min_duration).
---
doc/src/sgml/config.sgml | 41 +++++++++++++++----
doc/src/sgml/maintenance.sgml | 3 +-
doc/src/sgml/ref/create_table.sgml | 15 +++++++
src/backend/access/common/reloptions.c | 15 ++++++-
src/backend/access/heap/vacuumlazy.c | 6 +--
src/backend/commands/analyze.c | 8 ++--
src/backend/commands/vacuum.c | 10 +++--
src/backend/postmaster/autovacuum.c | 16 ++++++--
src/backend/utils/misc/guc_tables.c | 18 +++++++-
src/backend/utils/misc/postgresql.conf.sample | 7 +++-
src/bin/psql/tab-complete.in.c | 1 +
src/include/commands/vacuum.h | 9 ++--
src/include/postmaster/autovacuum.h | 1 +
src/include/utils/rel.h | 3 +-
src/test/regress/pg_regress.c | 1 +
src/tools/ci/pg_ci_base.conf | 1 +
16 files changed, 124 insertions(+), 31 deletions(-)
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 20ccb2d6b54..f210542f765 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -7439,17 +7439,44 @@ local0.* /var/log/postgresql
</term>
<listitem>
<para>
- Causes each action executed by autovacuum to be logged if it ran for at
+ Causes vacuum action executed by autovacuum to be logged if it ran for at
least the specified amount of time. Setting this to zero logs
- all autovacuum actions. <literal>-1</literal> disables logging autovacuum
- actions. If this value is specified without units, it is taken as milliseconds.
- For example, if you set this to
- <literal>250ms</literal> then all automatic vacuums and analyzes that run
+ all vacuum actions by autovacuum. <literal>-1</literal> disables logging
+ vacuum actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic vacuums that run
250ms or longer will be logged. In addition, when this parameter is
set to any value other than <literal>-1</literal>, a message will be
- logged if an autovacuum action is skipped due to a conflicting lock or a
+ logged if a vacuum action by autovacuum is skipped due to a conflicting lock or a
concurrently dropped relation. The default is <literal>10min</literal>.
- Enabling this parameter can be helpful in tracking autovacuum activity.
+ Enabling this parameter can be helpful in tracking vacuum activity by autovacuum.
+ This parameter can only be set in the <filename>postgresql.conf</filename>
+ file or on the server command line; but the setting can be overridden for
+ individual tables by changing table storage parameters.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry id="guc-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><varname>log_autoanalyze_min_duration</varname> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>configuration parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Causes analyze action executed by autovacuum to be logged if it ran for at
+ least the specified amount of time. Setting this to zero logs
+ all analyze actions by autovacuum. <literal>-1</literal> disables logging
+ analyze actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic analyzes that run
+ 250ms or longer will be logged. In addition, when this parameter is
+ set to any value other than <literal>-1</literal>, a message will be
+ logged if an analyze action by autovacuum is skipped due to a conflicting lock or a
+ concurrently dropped relation. The default is <literal>10min</literal>.
+ Enabling this parameter can be helpful in tracking analyze activity by autovacuum.
This parameter can only be set in the <filename>postgresql.conf</filename>
file or on the server command line; but the setting can be overridden for
individual tables by changing table storage parameters.
diff --git a/doc/src/sgml/maintenance.sgml b/doc/src/sgml/maintenance.sgml
index e7a9f58c015..dc59c88319e 100644
--- a/doc/src/sgml/maintenance.sgml
+++ b/doc/src/sgml/maintenance.sgml
@@ -892,7 +892,8 @@ HINT: Execute a database-wide VACUUM in that database.
the next database will be processed as soon as the first worker finishes.
Each worker process will check each table within its database and
execute <command>VACUUM</command> and/or <command>ANALYZE</command> as needed.
- <xref linkend="guc-log-autovacuum-min-duration"/> can be set to monitor
+ <xref linkend="guc-log-autovacuum-min-duration"/> and
+ <xref linkend="guc-log-autoanalyze-min-duration"/> can be set to monitor
autovacuum workers' activity.
</para>
diff --git a/doc/src/sgml/ref/create_table.sgml b/doc/src/sgml/ref/create_table.sgml
index dc000e913c1..a157a244e4e 100644
--- a/doc/src/sgml/ref/create_table.sgml
+++ b/doc/src/sgml/ref/create_table.sgml
@@ -1966,6 +1966,21 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</listitem>
</varlistentry>
+ <varlistentry id="reloption-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><literal>log_autoanalyze_min_duration</literal> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>storage parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Per-table value for <xref linkend="guc-log-autoanalyze-min-duration"/>
+ parameter.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry id="reloption-vacuum-max-eager-freeze-failure-rate" xreflabel="vacuum_max_eager_freeze_failure_rate">
<term><literal>vacuum_max_eager_freeze_failure_rate</literal>, <literal>toast.vacuum_max_eager_freeze_failure_rate</literal> (<type>floating point</type>)
<indexterm>
diff --git a/src/backend/access/common/reloptions.c b/src/backend/access/common/reloptions.c
index 0af3fea68fa..9b90e23164d 100644
--- a/src/backend/access/common/reloptions.c
+++ b/src/backend/access/common/reloptions.c
@@ -322,12 +322,21 @@ static relopt_int intRelOpts[] =
{
{
"log_autovacuum_min_duration",
- "Sets the minimum execution time above which autovacuum actions will be logged",
+ "Sets the minimum execution time above which vacuum actions by autovacuum will be logged",
RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
ShareUpdateExclusiveLock
},
-1, -1, INT_MAX
},
+ {
+ {
+ "log_autoanalyze_min_duration",
+ "Sets the minimum execution time above which analyze actions by autovacuum will be logged",
+ RELOPT_KIND_HEAP,
+ ShareUpdateExclusiveLock
+ },
+ -1, -1, INT_MAX
+ },
{
{
"toast_tuple_target",
@@ -1895,7 +1904,9 @@ default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
{"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
{"log_autovacuum_min_duration", RELOPT_TYPE_INT,
- offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_min_duration)},
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_vacuum_min_duration)},
+ {"log_autoanalyze_min_duration", RELOPT_TYPE_INT,
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_analyze_min_duration)},
{"toast_tuple_target", RELOPT_TYPE_INT,
offsetof(StdRdOptions, toast_tuple_target)},
{"autovacuum_vacuum_cost_delay", RELOPT_TYPE_REAL,
diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index 14036c27e87..76f2d456e5b 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -636,7 +636,7 @@ heap_vacuum_rel(Relation rel, const VacuumParams params,
verbose = (params.options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params.log_min_duration >= 0));
+ params.log_vacuum_min_duration >= 0));
if (instrument)
{
pg_rusage_init(&ru0);
@@ -947,9 +947,9 @@ heap_vacuum_rel(Relation rel, const VacuumParams params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params.log_min_duration == 0 ||
+ if (verbose || params.log_vacuum_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params.log_min_duration))
+ params.log_vacuum_min_duration))
{
long secs_dur;
int usecs_dur;
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index 40d66537ad7..8911c1bd0d6 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -139,7 +139,7 @@ analyze_rel(Oid relid, RangeVar *relation,
* Make sure to generate only logs for ANALYZE in this case.
*/
onerel = vacuum_open_relation(relid, relation, params.options & ~(VACOPT_VACUUM),
- params.log_min_duration >= 0,
+ params.log_analyze_min_duration >= 0,
ShareUpdateExclusiveLock);
/* leave if relation could not be opened or locked */
@@ -311,7 +311,7 @@ do_analyze_rel(Relation onerel, const VacuumParams params,
verbose = (params.options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params.log_min_duration >= 0));
+ params.log_analyze_min_duration >= 0));
if (inh)
ereport(elevel,
(errmsg("analyzing \"%s.%s\" inheritance tree",
@@ -736,9 +736,9 @@ do_analyze_rel(Relation onerel, const VacuumParams params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params.log_min_duration == 0 ||
+ if (verbose || params.log_analyze_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params.log_min_duration))
+ params.log_analyze_min_duration))
{
long delay_in_ms;
WalUsage walusage;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 733ef40ae7c..6694a705be7 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -416,8 +416,12 @@ ExecVacuum(ParseState *pstate, VacuumStmt *vacstmt, bool isTopLevel)
/* user-invoked vacuum is never "for wraparound" */
params.is_wraparound = false;
- /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_min_duration */
- params.log_min_duration = -1;
+ /*
+ * user-invoked vacuum uses VACOPT_VERBOSE instead of
+ * log_vacuum_min_duration and log_analyze_min_duration
+ */
+ params.log_vacuum_min_duration = -1;
+ params.log_analyze_min_duration = -1;
/*
* Later, in vacuum_rel(), we check if a reloption override was specified.
@@ -2073,7 +2077,7 @@ vacuum_rel(Oid relid, RangeVar *relation, VacuumParams params,
/* open the relation and get the appropriate lock on it */
rel = vacuum_open_relation(relid, relation, params.options,
- params.log_min_duration >= 0, lmode);
+ params.log_vacuum_min_duration >= 0, lmode);
/* leave if relation could not be opened or locked */
if (!rel)
diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c
index ff96b36d710..f1cae7686d0 100644
--- a/src/backend/postmaster/autovacuum.c
+++ b/src/backend/postmaster/autovacuum.c
@@ -134,6 +134,7 @@ double autovacuum_vac_cost_delay;
int autovacuum_vac_cost_limit;
int Log_autovacuum_min_duration = 600000;
+int Log_autoanalyze_min_duration = 600000;
/* the minimum allowed time between two awakenings of the launcher */
#define MIN_AUTOVAC_SLEEPTIME 100.0 /* milliseconds */
@@ -2815,7 +2816,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
int freeze_table_age;
int multixact_freeze_min_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
/*
* Calculate the vacuum cost parameters and the freeze ages. If there
@@ -2825,10 +2827,15 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
*/
/* -1 in autovac setting means use log_autovacuum_min_duration */
- log_min_duration = (avopts && avopts->log_min_duration >= 0)
- ? avopts->log_min_duration
+ log_vacuum_min_duration = (avopts && avopts->log_vacuum_min_duration >= 0)
+ ? avopts->log_vacuum_min_duration
: Log_autovacuum_min_duration;
+ /* -1 in autovac setting means use log_autoanalyze_min_duration */
+ log_analyze_min_duration = (avopts && avopts->log_analyze_min_duration >= 0)
+ ? avopts->log_analyze_min_duration
+ : Log_autoanalyze_min_duration;
+
/* these do not have autovacuum-specific settings */
freeze_min_age = (avopts && avopts->freeze_min_age >= 0)
? avopts->freeze_min_age
@@ -2878,7 +2885,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
tab->at_params.multixact_freeze_min_age = multixact_freeze_min_age;
tab->at_params.multixact_freeze_table_age = multixact_freeze_table_age;
tab->at_params.is_wraparound = wraparound;
- tab->at_params.log_min_duration = log_min_duration;
+ tab->at_params.log_vacuum_min_duration = log_vacuum_min_duration;
+ tab->at_params.log_analyze_min_duration = log_analyze_min_duration;
tab->at_params.toast_parent = InvalidOid;
/*
diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c
index d14b1678e7f..d28d62d862d 100644
--- a/src/backend/utils/misc/guc_tables.c
+++ b/src/backend/utils/misc/guc_tables.c
@@ -3171,8 +3171,9 @@ struct config_int ConfigureNamesInt[] =
{
{"log_autovacuum_min_duration", PGC_SIGHUP, LOGGING_WHAT,
gettext_noop("Sets the minimum execution time above which "
- "autovacuum actions will be logged."),
- gettext_noop("-1 disables logging autovacuum actions. 0 means log all autovacuum actions."),
+ "vacuum actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging vacuum actions by autovacuum. "
+ "0 means log all vacuum actions by autovacuum."),
GUC_UNIT_MS
},
&Log_autovacuum_min_duration,
@@ -3180,6 +3181,19 @@ struct config_int ConfigureNamesInt[] =
NULL, NULL, NULL
},
+ {
+ {"log_autoanalyze_min_duration", PGC_SIGHUP, LOGGING_WHAT,
+ gettext_noop("Sets the minimum execution time above which "
+ "analyze actions by autovacuum will be logged."),
+ gettext_noop("-1 disables logging analyze actions by autovacuum. "
+ "0 means log all analyze actions by autovacuum."),
+ GUC_UNIT_MS
+ },
+ &Log_autoanalyze_min_duration,
+ 600000, -1, INT_MAX,
+ NULL, NULL, NULL
+ },
+
{
{"log_parameter_max_length", PGC_SUSET, LOGGING_WHAT,
gettext_noop("Sets the maximum length in bytes of data logged for bind "
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index a9d8293474a..5c09956ba1d 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -585,7 +585,12 @@
#debug_print_rewritten = off
#debug_print_plan = off
#debug_pretty_print = on
-#log_autovacuum_min_duration = 10min # log autovacuum activity;
+#log_autovacuum_min_duration = 10min # log vacuum activity by autovacuum;
+ # -1 disables, 0 logs all actions and
+ # their durations, > 0 logs only
+ # actions running at least this number
+ # of milliseconds.
+#log_autoanalyze_min_duration = 10min # log analyze activity by autovacuum;
# -1 disables, 0 logs all actions and
# their durations, > 0 logs only
# actions running at least this number
diff --git a/src/bin/psql/tab-complete.in.c b/src/bin/psql/tab-complete.in.c
index 8b10f2313f3..3cc29327fc0 100644
--- a/src/bin/psql/tab-complete.in.c
+++ b/src/bin/psql/tab-complete.in.c
@@ -1411,6 +1411,7 @@ static const char *const table_storage_parameters[] = {
"autovacuum_vacuum_threshold",
"fillfactor",
"log_autovacuum_min_duration",
+ "log_autoanalyze_min_duration",
"parallel_workers",
"toast.autovacuum_enabled",
"toast.autovacuum_freeze_max_age",
diff --git a/src/include/commands/vacuum.h b/src/include/commands/vacuum.h
index 14eeccbd718..7b9b29e673f 100644
--- a/src/include/commands/vacuum.h
+++ b/src/include/commands/vacuum.h
@@ -224,9 +224,12 @@ typedef struct VacuumParams
int multixact_freeze_table_age; /* multixact age at which to scan
* whole table */
bool is_wraparound; /* force a for-wraparound vacuum */
- int log_min_duration; /* minimum execution threshold in ms at
- * which autovacuum is logged, -1 to use
- * default */
+ int log_vacuum_min_duration; /* minimum execution threshold in ms
+ * at which vacuum by autovacuum is
+ * logged, -1 to use default */
+ int log_analyze_min_duration; /* minimum execution threshold in ms
+ * at which analyze by autovacuum is
+ * logged, -1 to use default */
VacOptValue index_cleanup; /* Do index vacuum and cleanup */
VacOptValue truncate; /* Truncate empty pages at the end */
Oid toast_parent; /* for privilege checks when recursing */
diff --git a/src/include/postmaster/autovacuum.h b/src/include/postmaster/autovacuum.h
index e8135f41a1c..023ac6d5fa8 100644
--- a/src/include/postmaster/autovacuum.h
+++ b/src/include/postmaster/autovacuum.h
@@ -48,6 +48,7 @@ extern PGDLLIMPORT int autovacuum_vac_cost_limit;
extern PGDLLIMPORT int AutovacuumLauncherPid;
extern PGDLLIMPORT int Log_autovacuum_min_duration;
+extern PGDLLIMPORT int Log_autoanalyze_min_duration;
/* Status inquiry functions */
extern bool AutoVacuumingActive(void);
diff --git a/src/include/utils/rel.h b/src/include/utils/rel.h
index b552359915f..e63aa31d151 100644
--- a/src/include/utils/rel.h
+++ b/src/include/utils/rel.h
@@ -322,7 +322,8 @@ typedef struct AutoVacOpts
int multixact_freeze_min_age;
int multixact_freeze_max_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
float8 vacuum_cost_delay;
float8 vacuum_scale_factor;
float8 vacuum_ins_scale_factor;
diff --git a/src/test/regress/pg_regress.c b/src/test/regress/pg_regress.c
index 5d85dcc62f0..399f1634a1c 100644
--- a/src/test/regress/pg_regress.c
+++ b/src/test/regress/pg_regress.c
@@ -2401,6 +2401,7 @@ regression_main(int argc, char *argv[],
fputs("\n# Configuration added by pg_regress\n\n", pg_conf);
fputs("log_autovacuum_min_duration = 0\n", pg_conf);
+ fputs("log_autoanalyze_min_duration = 0\n", pg_conf);
fputs("log_checkpoints = on\n", pg_conf);
fputs("log_line_prefix = '%m %b[%p] %q%a '\n", pg_conf);
fputs("log_lock_waits = on\n", pg_conf);
diff --git a/src/tools/ci/pg_ci_base.conf b/src/tools/ci/pg_ci_base.conf
index 695e0a0d6ec..ff05646c90e 100644
--- a/src/tools/ci/pg_ci_base.conf
+++ b/src/tools/ci/pg_ci_base.conf
@@ -7,6 +7,7 @@ max_prepared_transactions = 10
# Settings that make logs more useful
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
log_checkpoints = true
log_connections = all
log_disconnections = true
--
2.47.3
Hi,
2025-08-14 13:26 に Shinya Kato wrote:
Hi,
On Wed, Aug 13, 2025 at 5:44 PM kasaharatt <kasaharatt@oss.nttdata.com>
wrote:Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the
behavior of
log_autovacuum_min_duration, as the new GUC will have the same
default
value.Thank you for voting. I also think this approach is reasonable to
implement.A new patch is attached.
Thoughts?I reviewed this patch.
I also have no particular objections to the Approach 2.Thank you for the review!
+ <term><literal>log_autoanalyze_min_duration</literal>,
<literal>toast.log_autoanalyze_min_duration</literal>(<type>integer</type>)(snip)
+ "toast.log_autoanalyze_min_duration",
This patch adds the log_autoanalyze_min_duration parameter fot TOAST
tables.
However since PostgreSQL currently does not support ANALYZE on TOAST
tables,
isn't this parameter unnecessary?You're right; that was a mistake. I've fixed it in the v4 patch.
Thanks for the patch updating.
Additionally, I removed the above setting from the test files in
src/test/modules/xid_wraparound/t/ (001_emergency_vacuum.pl,
002_limits.pl, 003_wraparounds.pl). The reason is that these tests
check for autovacuum logs, not autoanalyze logs. You can run the test
with the following command:
make check -C src/test/modules/xid_wraparound
PG_TEST_EXTRA='xid_wraparound'
Yeah, I agree that.
I confirmed this patch could apply to HEAD and all make check tests were
passed.
I've manually tested it in a few different ways, and it's working as
expected so far.
Unless there are any objections from others, I think I can mark this
patch as "Ready for Committer".
Best regards,
--
Kasahara Tatsuhito
NTT DATA Japan Corporation
2025-08-14 17:56 に kasaharatt wrote:
Hi,
2025-08-14 13:26 に Shinya Kato wrote:
Hi,
On Wed, Aug 13, 2025 at 5:44 PM kasaharatt
<kasaharatt@oss.nttdata.com> wrote:Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the
behavior of
log_autovacuum_min_duration, as the new GUC will have the same
default
value.Thank you for voting. I also think this approach is reasonable to
implement.A new patch is attached.
Thoughts?I reviewed this patch.
I also have no particular objections to the Approach 2.Thank you for the review!
+ <term><literal>log_autoanalyze_min_duration</literal>,
<literal>toast.log_autoanalyze_min_duration</literal>(<type>integer</type>)(snip)
+ "toast.log_autoanalyze_min_duration",
This patch adds the log_autoanalyze_min_duration parameter fot TOAST
tables.
However since PostgreSQL currently does not support ANALYZE on TOAST
tables,
isn't this parameter unnecessary?You're right; that was a mistake. I've fixed it in the v4 patch.
Thanks for the patch updating.
Additionally, I removed the above setting from the test files in
src/test/modules/xid_wraparound/t/ (001_emergency_vacuum.pl,
002_limits.pl, 003_wraparounds.pl). The reason is that these tests
check for autovacuum logs, not autoanalyze logs. You can run the test
with the following command:
make check -C src/test/modules/xid_wraparound
PG_TEST_EXTRA='xid_wraparound'Yeah, I agree that.
I confirmed this patch could apply to HEAD and all make check tests
were passed.
I've manually tested it in a few different ways, and it's working as
expected so far.Unless there are any objections from others, I think I can mark this
patch as "Ready for Committer".
Since there were no particular comments, I've marked it as Ready for
Committer.
Best regards,
--
Kasahara Tatsuhito
NTT DATA Japan Corporation
Hi,
2025-08-21 16:39 に kasaharatt wrote:
2025-08-14 17:56 に kasaharatt wrote:
Hi,
2025-08-14 13:26 に Shinya Kato wrote:
Hi,
On Wed, Aug 13, 2025 at 5:44 PM kasaharatt
<kasaharatt@oss.nttdata.com> wrote:Approach 2:
- log_autovacuum_min_duration: Changed behavior, which controls only
autovacuum logging.
- log_autoanalyze_min_duration: New parameter, which controls
autoanalyze logging.My vote is for this approach. It is probably OK to change the
behavior of
log_autovacuum_min_duration, as the new GUC will have the same
default
value.Thank you for voting. I also think this approach is reasonable to
implement.A new patch is attached.
Thoughts?I reviewed this patch.
I also have no particular objections to the Approach 2.Thank you for the review!
+ <term><literal>log_autoanalyze_min_duration</literal>,
<literal>toast.log_autoanalyze_min_duration</literal>(<type>integer</type>)(snip)
+ "toast.log_autoanalyze_min_duration",
This patch adds the log_autoanalyze_min_duration parameter fot TOAST
tables.
However since PostgreSQL currently does not support ANALYZE on TOAST
tables,
isn't this parameter unnecessary?You're right; that was a mistake. I've fixed it in the v4 patch.
Thanks for the patch updating.
Additionally, I removed the above setting from the test files in
src/test/modules/xid_wraparound/t/ (001_emergency_vacuum.pl,
002_limits.pl, 003_wraparounds.pl). The reason is that these tests
check for autovacuum logs, not autoanalyze logs. You can run the test
with the following command:
make check -C src/test/modules/xid_wraparound
PG_TEST_EXTRA='xid_wraparound'Yeah, I agree that.
I confirmed this patch could apply to HEAD and all make check tests
were passed.
I've manually tested it in a few different ways, and it's working as
expected so far.Unless there are any objections from others, I think I can mark this
patch as "Ready for Committer".Since there were no particular comments, I've marked it as Ready for
Committer.
The changes(*) to guc_tables.c have been pushed into HEAD,
so you may need to fix the patch.
Best regards,
--
Kasahara Tatsuhito
NTT DATA Japan Corporation
Hi,
On Thu, Sep 4, 2025 at 11:31 AM kasaharatt <kasaharatt@oss.nttdata.com> wrote:
The changes(*) to guc_tables.c have been pushed into HEAD,
so you may need to fix the patch.
Thank you for reporting and I fixed the patch.
--
Best regards,
Shinya Kato
NTT OSS Center
Attachments:
v5-0001-Add-log_autoanalyze_min_duration.patchapplication/octet-stream; name=v5-0001-Add-log_autoanalyze_min_duration.patchDownload
From fc245193dd958499c240660eec5ae328a38b78e6 Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Thu, 4 Sep 2025 12:25:27 +0900
Subject: [PATCH v5] Add log_autoanalyze_min_duration
The log output functionality of log_autovacuum_min_duration applies to
both VACUUM and ANALYZE, so it is not possible to separate the VACUUM
and ANALYZE log output thresholds. Logs are likely to be output only for
VACUUM and not for ANALYZE.
Therefore, we decided to separate the threshold for log output of VACUUM
by autovacuum (log_autovacuum_min_duration) and the threshold for log
output of ANALYZE by autovacuum (log_autoanalyze_min_duration).
---
doc/src/sgml/config.sgml | 41 +++++++++++++++----
doc/src/sgml/maintenance.sgml | 3 +-
doc/src/sgml/ref/create_table.sgml | 15 +++++++
src/backend/access/common/reloptions.c | 15 ++++++-
src/backend/access/heap/vacuumlazy.c | 6 +--
src/backend/commands/analyze.c | 8 ++--
src/backend/commands/vacuum.c | 10 +++--
src/backend/postmaster/autovacuum.c | 16 ++++++--
src/backend/utils/misc/guc_parameters.dat | 14 ++++++-
src/backend/utils/misc/postgresql.conf.sample | 7 +++-
src/bin/psql/tab-complete.in.c | 1 +
src/include/commands/vacuum.h | 9 ++--
src/include/postmaster/autovacuum.h | 1 +
src/include/utils/rel.h | 3 +-
src/test/regress/pg_regress.c | 1 +
src/tools/ci/pg_ci_base.conf | 1 +
16 files changed, 120 insertions(+), 31 deletions(-)
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 0a4b3e55ba5..6f5fb353432 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -7440,17 +7440,44 @@ local0.* /var/log/postgresql
</term>
<listitem>
<para>
- Causes each action executed by autovacuum to be logged if it ran for at
+ Causes vacuum action executed by autovacuum to be logged if it ran for at
least the specified amount of time. Setting this to zero logs
- all autovacuum actions. <literal>-1</literal> disables logging autovacuum
- actions. If this value is specified without units, it is taken as milliseconds.
- For example, if you set this to
- <literal>250ms</literal> then all automatic vacuums and analyzes that run
+ all vacuum actions by autovacuum. <literal>-1</literal> disables logging
+ vacuum actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic vacuums that run
250ms or longer will be logged. In addition, when this parameter is
set to any value other than <literal>-1</literal>, a message will be
- logged if an autovacuum action is skipped due to a conflicting lock or a
+ logged if a vacuum action by autovacuum is skipped due to a conflicting lock or a
concurrently dropped relation. The default is <literal>10min</literal>.
- Enabling this parameter can be helpful in tracking autovacuum activity.
+ Enabling this parameter can be helpful in tracking vacuum activity by autovacuum.
+ This parameter can only be set in the <filename>postgresql.conf</filename>
+ file or on the server command line; but the setting can be overridden for
+ individual tables by changing table storage parameters.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry id="guc-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><varname>log_autoanalyze_min_duration</varname> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>configuration parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Causes analyze action executed by autovacuum to be logged if it ran for at
+ least the specified amount of time. Setting this to zero logs
+ all analyze actions by autovacuum. <literal>-1</literal> disables logging
+ analyze actions by autovacuum. If this value is specified without units,
+ it is taken as milliseconds. For example, if you set this to
+ <literal>250ms</literal> then all automatic analyzes that run
+ 250ms or longer will be logged. In addition, when this parameter is
+ set to any value other than <literal>-1</literal>, a message will be
+ logged if an analyze action by autovacuum is skipped due to a conflicting lock or a
+ concurrently dropped relation. The default is <literal>10min</literal>.
+ Enabling this parameter can be helpful in tracking analyze activity by autovacuum.
This parameter can only be set in the <filename>postgresql.conf</filename>
file or on the server command line; but the setting can be overridden for
individual tables by changing table storage parameters.
diff --git a/doc/src/sgml/maintenance.sgml b/doc/src/sgml/maintenance.sgml
index e7a9f58c015..dc59c88319e 100644
--- a/doc/src/sgml/maintenance.sgml
+++ b/doc/src/sgml/maintenance.sgml
@@ -892,7 +892,8 @@ HINT: Execute a database-wide VACUUM in that database.
the next database will be processed as soon as the first worker finishes.
Each worker process will check each table within its database and
execute <command>VACUUM</command> and/or <command>ANALYZE</command> as needed.
- <xref linkend="guc-log-autovacuum-min-duration"/> can be set to monitor
+ <xref linkend="guc-log-autovacuum-min-duration"/> and
+ <xref linkend="guc-log-autoanalyze-min-duration"/> can be set to monitor
autovacuum workers' activity.
</para>
diff --git a/doc/src/sgml/ref/create_table.sgml b/doc/src/sgml/ref/create_table.sgml
index dc000e913c1..a157a244e4e 100644
--- a/doc/src/sgml/ref/create_table.sgml
+++ b/doc/src/sgml/ref/create_table.sgml
@@ -1966,6 +1966,21 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</listitem>
</varlistentry>
+ <varlistentry id="reloption-log-autoanalyze-min-duration" xreflabel="log_autoanalyze_min_duration">
+ <term><literal>log_autoanalyze_min_duration</literal> (<type>integer</type>)
+ <indexterm>
+ <primary><varname>log_autoanalyze_min_duration</varname></primary>
+ <secondary>storage parameter</secondary>
+ </indexterm>
+ </term>
+ <listitem>
+ <para>
+ Per-table value for <xref linkend="guc-log-autoanalyze-min-duration"/>
+ parameter.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry id="reloption-vacuum-max-eager-freeze-failure-rate" xreflabel="vacuum_max_eager_freeze_failure_rate">
<term><literal>vacuum_max_eager_freeze_failure_rate</literal>, <literal>toast.vacuum_max_eager_freeze_failure_rate</literal> (<type>floating point</type>)
<indexterm>
diff --git a/src/backend/access/common/reloptions.c b/src/backend/access/common/reloptions.c
index 0af3fea68fa..9b90e23164d 100644
--- a/src/backend/access/common/reloptions.c
+++ b/src/backend/access/common/reloptions.c
@@ -322,12 +322,21 @@ static relopt_int intRelOpts[] =
{
{
"log_autovacuum_min_duration",
- "Sets the minimum execution time above which autovacuum actions will be logged",
+ "Sets the minimum execution time above which vacuum actions by autovacuum will be logged",
RELOPT_KIND_HEAP | RELOPT_KIND_TOAST,
ShareUpdateExclusiveLock
},
-1, -1, INT_MAX
},
+ {
+ {
+ "log_autoanalyze_min_duration",
+ "Sets the minimum execution time above which analyze actions by autovacuum will be logged",
+ RELOPT_KIND_HEAP,
+ ShareUpdateExclusiveLock
+ },
+ -1, -1, INT_MAX
+ },
{
{
"toast_tuple_target",
@@ -1895,7 +1904,9 @@ default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
{"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
{"log_autovacuum_min_duration", RELOPT_TYPE_INT,
- offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_min_duration)},
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_vacuum_min_duration)},
+ {"log_autoanalyze_min_duration", RELOPT_TYPE_INT,
+ offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, log_analyze_min_duration)},
{"toast_tuple_target", RELOPT_TYPE_INT,
offsetof(StdRdOptions, toast_tuple_target)},
{"autovacuum_vacuum_cost_delay", RELOPT_TYPE_REAL,
diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index 932701d8420..d0ca784d2f4 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -635,7 +635,7 @@ heap_vacuum_rel(Relation rel, const VacuumParams params,
verbose = (params.options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params.log_min_duration >= 0));
+ params.log_vacuum_min_duration >= 0));
if (instrument)
{
pg_rusage_init(&ru0);
@@ -946,9 +946,9 @@ heap_vacuum_rel(Relation rel, const VacuumParams params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params.log_min_duration == 0 ||
+ if (verbose || params.log_vacuum_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params.log_min_duration))
+ params.log_vacuum_min_duration))
{
long secs_dur;
int usecs_dur;
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index 8ea2913d906..d799fc5d228 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -138,7 +138,7 @@ analyze_rel(Oid relid, RangeVar *relation,
* Make sure to generate only logs for ANALYZE in this case.
*/
onerel = vacuum_open_relation(relid, relation, params.options & ~(VACOPT_VACUUM),
- params.log_min_duration >= 0,
+ params.log_analyze_min_duration >= 0,
ShareUpdateExclusiveLock);
/* leave if relation could not be opened or locked */
@@ -310,7 +310,7 @@ do_analyze_rel(Relation onerel, const VacuumParams params,
verbose = (params.options & VACOPT_VERBOSE) != 0;
instrument = (verbose || (AmAutoVacuumWorkerProcess() &&
- params.log_min_duration >= 0));
+ params.log_analyze_min_duration >= 0));
if (inh)
ereport(elevel,
(errmsg("analyzing \"%s.%s\" inheritance tree",
@@ -735,9 +735,9 @@ do_analyze_rel(Relation onerel, const VacuumParams params,
{
TimestampTz endtime = GetCurrentTimestamp();
- if (verbose || params.log_min_duration == 0 ||
+ if (verbose || params.log_analyze_min_duration == 0 ||
TimestampDifferenceExceeds(starttime, endtime,
- params.log_min_duration))
+ params.log_analyze_min_duration))
{
long delay_in_ms;
WalUsage walusage;
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index 733ef40ae7c..6694a705be7 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -416,8 +416,12 @@ ExecVacuum(ParseState *pstate, VacuumStmt *vacstmt, bool isTopLevel)
/* user-invoked vacuum is never "for wraparound" */
params.is_wraparound = false;
- /* user-invoked vacuum uses VACOPT_VERBOSE instead of log_min_duration */
- params.log_min_duration = -1;
+ /*
+ * user-invoked vacuum uses VACOPT_VERBOSE instead of
+ * log_vacuum_min_duration and log_analyze_min_duration
+ */
+ params.log_vacuum_min_duration = -1;
+ params.log_analyze_min_duration = -1;
/*
* Later, in vacuum_rel(), we check if a reloption override was specified.
@@ -2073,7 +2077,7 @@ vacuum_rel(Oid relid, RangeVar *relation, VacuumParams params,
/* open the relation and get the appropriate lock on it */
rel = vacuum_open_relation(relid, relation, params.options,
- params.log_min_duration >= 0, lmode);
+ params.log_vacuum_min_duration >= 0, lmode);
/* leave if relation could not be opened or locked */
if (!rel)
diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c
index dce4c8c45b9..7549548fcb3 100644
--- a/src/backend/postmaster/autovacuum.c
+++ b/src/backend/postmaster/autovacuum.c
@@ -133,6 +133,7 @@ double autovacuum_vac_cost_delay;
int autovacuum_vac_cost_limit;
int Log_autovacuum_min_duration = 600000;
+int Log_autoanalyze_min_duration = 600000;
/* the minimum allowed time between two awakenings of the launcher */
#define MIN_AUTOVAC_SLEEPTIME 100.0 /* milliseconds */
@@ -2814,7 +2815,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
int freeze_table_age;
int multixact_freeze_min_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
/*
* Calculate the vacuum cost parameters and the freeze ages. If there
@@ -2824,10 +2826,15 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
*/
/* -1 in autovac setting means use log_autovacuum_min_duration */
- log_min_duration = (avopts && avopts->log_min_duration >= 0)
- ? avopts->log_min_duration
+ log_vacuum_min_duration = (avopts && avopts->log_vacuum_min_duration >= 0)
+ ? avopts->log_vacuum_min_duration
: Log_autovacuum_min_duration;
+ /* -1 in autovac setting means use log_autoanalyze_min_duration */
+ log_analyze_min_duration = (avopts && avopts->log_analyze_min_duration >= 0)
+ ? avopts->log_analyze_min_duration
+ : Log_autoanalyze_min_duration;
+
/* these do not have autovacuum-specific settings */
freeze_min_age = (avopts && avopts->freeze_min_age >= 0)
? avopts->freeze_min_age
@@ -2877,7 +2884,8 @@ table_recheck_autovac(Oid relid, HTAB *table_toast_map,
tab->at_params.multixact_freeze_min_age = multixact_freeze_min_age;
tab->at_params.multixact_freeze_table_age = multixact_freeze_table_age;
tab->at_params.is_wraparound = wraparound;
- tab->at_params.log_min_duration = log_min_duration;
+ tab->at_params.log_vacuum_min_duration = log_vacuum_min_duration;
+ tab->at_params.log_analyze_min_duration = log_analyze_min_duration;
tab->at_params.toast_parent = InvalidOid;
/*
diff --git a/src/backend/utils/misc/guc_parameters.dat b/src/backend/utils/misc/guc_parameters.dat
index a157cec3c4d..04fc57b185b 100644
--- a/src/backend/utils/misc/guc_parameters.dat
+++ b/src/backend/utils/misc/guc_parameters.dat
@@ -1758,8 +1758,8 @@
},
{ name => 'log_autovacuum_min_duration', type => 'int', context => 'PGC_SIGHUP', group => 'LOGGING_WHAT',
- short_desc => 'Sets the minimum execution time above which autovacuum actions will be logged.',
- long_desc => '-1 disables logging autovacuum actions. 0 means log all autovacuum actions.',
+ short_desc => 'Sets the minimum execution time above which vacuum actions by autovacuum will be logged.',
+ long_desc => '-1 disables logging vacuum actions by autovacuum. 0 means log all vacuum actions by autovacuum.',
flags => 'GUC_UNIT_MS',
variable => 'Log_autovacuum_min_duration',
boot_val => '600000',
@@ -1767,6 +1767,16 @@
max => 'INT_MAX',
},
+{ name => 'log_autoanalyze_min_duration', type => 'int', context => 'PGC_SIGHUP', group => 'LOGGING_WHAT',
+ short_desc => 'Sets the minimum execution time above which analyze actions by autovacuum will be logged.',
+ long_desc => '-1 disables logging analyze actions by autovacuum. 0 means log all analyze actions by autovacuum.',
+ flags => 'GUC_UNIT_MS',
+ variable => 'Log_autoanalyze_min_duration',
+ boot_val => '600000',
+ min => '-1',
+ max => 'INT_MAX',
+},
+
{ name => 'log_parameter_max_length', type => 'int', context => 'PGC_SUSET', group => 'LOGGING_WHAT',
short_desc => 'Sets the maximum length in bytes of data logged for bind parameter values when logging statements.',
long_desc => '-1 means log values in full.',
diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample
index a9d8293474a..5c09956ba1d 100644
--- a/src/backend/utils/misc/postgresql.conf.sample
+++ b/src/backend/utils/misc/postgresql.conf.sample
@@ -585,7 +585,12 @@
#debug_print_rewritten = off
#debug_print_plan = off
#debug_pretty_print = on
-#log_autovacuum_min_duration = 10min # log autovacuum activity;
+#log_autovacuum_min_duration = 10min # log vacuum activity by autovacuum;
+ # -1 disables, 0 logs all actions and
+ # their durations, > 0 logs only
+ # actions running at least this number
+ # of milliseconds.
+#log_autoanalyze_min_duration = 10min # log analyze activity by autovacuum;
# -1 disables, 0 logs all actions and
# their durations, > 0 logs only
# actions running at least this number
diff --git a/src/bin/psql/tab-complete.in.c b/src/bin/psql/tab-complete.in.c
index 6b20a4404b2..3e8c296759c 100644
--- a/src/bin/psql/tab-complete.in.c
+++ b/src/bin/psql/tab-complete.in.c
@@ -1411,6 +1411,7 @@ static const char *const table_storage_parameters[] = {
"autovacuum_vacuum_threshold",
"fillfactor",
"log_autovacuum_min_duration",
+ "log_autoanalyze_min_duration",
"parallel_workers",
"toast.autovacuum_enabled",
"toast.autovacuum_freeze_max_age",
diff --git a/src/include/commands/vacuum.h b/src/include/commands/vacuum.h
index 14eeccbd718..7b9b29e673f 100644
--- a/src/include/commands/vacuum.h
+++ b/src/include/commands/vacuum.h
@@ -224,9 +224,12 @@ typedef struct VacuumParams
int multixact_freeze_table_age; /* multixact age at which to scan
* whole table */
bool is_wraparound; /* force a for-wraparound vacuum */
- int log_min_duration; /* minimum execution threshold in ms at
- * which autovacuum is logged, -1 to use
- * default */
+ int log_vacuum_min_duration; /* minimum execution threshold in ms
+ * at which vacuum by autovacuum is
+ * logged, -1 to use default */
+ int log_analyze_min_duration; /* minimum execution threshold in ms
+ * at which analyze by autovacuum is
+ * logged, -1 to use default */
VacOptValue index_cleanup; /* Do index vacuum and cleanup */
VacOptValue truncate; /* Truncate empty pages at the end */
Oid toast_parent; /* for privilege checks when recursing */
diff --git a/src/include/postmaster/autovacuum.h b/src/include/postmaster/autovacuum.h
index e8135f41a1c..023ac6d5fa8 100644
--- a/src/include/postmaster/autovacuum.h
+++ b/src/include/postmaster/autovacuum.h
@@ -48,6 +48,7 @@ extern PGDLLIMPORT int autovacuum_vac_cost_limit;
extern PGDLLIMPORT int AutovacuumLauncherPid;
extern PGDLLIMPORT int Log_autovacuum_min_duration;
+extern PGDLLIMPORT int Log_autoanalyze_min_duration;
/* Status inquiry functions */
extern bool AutoVacuumingActive(void);
diff --git a/src/include/utils/rel.h b/src/include/utils/rel.h
index b552359915f..e63aa31d151 100644
--- a/src/include/utils/rel.h
+++ b/src/include/utils/rel.h
@@ -322,7 +322,8 @@ typedef struct AutoVacOpts
int multixact_freeze_min_age;
int multixact_freeze_max_age;
int multixact_freeze_table_age;
- int log_min_duration;
+ int log_vacuum_min_duration;
+ int log_analyze_min_duration;
float8 vacuum_cost_delay;
float8 vacuum_scale_factor;
float8 vacuum_ins_scale_factor;
diff --git a/src/test/regress/pg_regress.c b/src/test/regress/pg_regress.c
index 5d85dcc62f0..399f1634a1c 100644
--- a/src/test/regress/pg_regress.c
+++ b/src/test/regress/pg_regress.c
@@ -2401,6 +2401,7 @@ regression_main(int argc, char *argv[],
fputs("\n# Configuration added by pg_regress\n\n", pg_conf);
fputs("log_autovacuum_min_duration = 0\n", pg_conf);
+ fputs("log_autoanalyze_min_duration = 0\n", pg_conf);
fputs("log_checkpoints = on\n", pg_conf);
fputs("log_line_prefix = '%m %b[%p] %q%a '\n", pg_conf);
fputs("log_lock_waits = on\n", pg_conf);
diff --git a/src/tools/ci/pg_ci_base.conf b/src/tools/ci/pg_ci_base.conf
index 695e0a0d6ec..ff05646c90e 100644
--- a/src/tools/ci/pg_ci_base.conf
+++ b/src/tools/ci/pg_ci_base.conf
@@ -7,6 +7,7 @@ max_prepared_transactions = 10
# Settings that make logs more useful
log_autovacuum_min_duration = 0
+log_autoanalyze_min_duration = 0
log_checkpoints = true
log_connections = all
log_disconnections = true
--
2.47.3
2025-09-04 13:13 に Shinya Kato wrote:
Hi,
On Thu, Sep 4, 2025 at 11:31 AM kasaharatt <kasaharatt@oss.nttdata.com>
wrote:The changes(*) to guc_tables.c have been pushed into HEAD,
so you may need to fix the patch.Thank you for reporting and I fixed the patch.
Thank you for the quick fix.
I've confirmed that it can be applied to HEAD and that all regression
tests pass.
I've run a few quick local checks and it works as expected.
ISTM there are no particular issues with the changes.
The status has been changed to Ready for Committer again.
Best regards,
--
Kasahara Tatsuhito
NTT DATA Japan Corporation
On 04.09.25 08:16, kasaharatt wrote:
2025-09-04 13:13 に Shinya Kato wrote:
Hi,
On Thu, Sep 4, 2025 at 11:31 AM kasaharatt
<kasaharatt@oss.nttdata.com> wrote:The changes(*) to guc_tables.c have been pushed into HEAD,
so you may need to fix the patch.(*)
https://git.postgresql.org/gitweb/?
p=postgresql.git;a=commit;h=63599896545c7869f7dd28cd593e8b548983d613Thank you for reporting and I fixed the patch.
Thank you for the quick fix.
I've confirmed that it can be applied to HEAD and that all regression
tests pass.
I've run a few quick local checks and it works as expected.
ISTM there are no particular issues with the changes.The status has been changed to Ready for Committer again.
Committed, thanks.
On Wed, Oct 15, 2025 at 9:37 PM Peter Eisentraut <peter@eisentraut.org> wrote:
On 04.09.25 08:16, kasaharatt wrote:
2025-09-04 13:13 に Shinya Kato wrote:
Hi,
On Thu, Sep 4, 2025 at 11:31 AM kasaharatt
<kasaharatt@oss.nttdata.com> wrote:The changes(*) to guc_tables.c have been pushed into HEAD,
so you may need to fix the patch.(*)
https://git.postgresql.org/gitweb/?
p=postgresql.git;a=commit;h=63599896545c7869f7dd28cd593e8b548983d613Thank you for reporting and I fixed the patch.
Thank you for the quick fix.
I've confirmed that it can be applied to HEAD and that all regression
tests pass.
I've run a few quick local checks and it works as expected.
ISTM there are no particular issues with the changes.The status has been changed to Ready for Committer again.
Committed, thanks.
Thank you for pushing!
--
Best regards,
Shinya Kato
NTT OSS Center