From ec071144e88e26e893f1d67f9170c9ac706da55e Mon Sep 17 00:00:00 2001
From: Shinya Kato <shinya11.kato@gmail.com>
Date: Fri, 2 May 2025 19:08:45 +0900
Subject: [PATCH v3 9/9] Make pg_stat_clear_snapshot() return the reset time

---
 doc/src/sgml/monitoring.sgml            |  5 ++--
 src/backend/utils/activity/pgstat.c     |  4 +++-
 src/backend/utils/adt/pgstatfuncs.c     |  6 +++--
 src/include/catalog/pg_proc.dat         |  2 +-
 src/include/pgstat.h                    |  2 +-
 src/test/isolation/expected/stats.out   | 32 ++++++++++++-------------
 src/test/isolation/expected/stats_1.out | 32 ++++++++++++-------------
 src/test/isolation/specs/stats.spec     |  2 +-
 src/test/regress/expected/stats.out     |  8 +++----
 src/test/regress/sql/stats.sql          |  2 +-
 10 files changed, 50 insertions(+), 45 deletions(-)

diff --git a/doc/src/sgml/monitoring.sgml b/doc/src/sgml/monitoring.sgml
index fe561c01da1..08e402eb5db 100644
--- a/doc/src/sgml/monitoring.sgml
+++ b/doc/src/sgml/monitoring.sgml
@@ -5055,10 +5055,11 @@ description | Waiting for a newly initialized WAL file to reach durable storage
          <primary>pg_stat_clear_snapshot</primary>
         </indexterm>
         <function>pg_stat_clear_snapshot</function> ()
-        <returnvalue>void</returnvalue>
+        <returnvalue>timestamp with time zone</returnvalue>
        </para>
        <para>
-        Discards the current statistics snapshot or cached information.
+        Discards the current statistics snapshot or cached information, and
+        returns the time of the discard.
        </para></entry>
       </row>
 
diff --git a/src/backend/utils/activity/pgstat.c b/src/backend/utils/activity/pgstat.c
index 5b7166ee554..88e49bea703 100644
--- a/src/backend/utils/activity/pgstat.c
+++ b/src/backend/utils/activity/pgstat.c
@@ -904,7 +904,7 @@ pgstat_reset_of_kind(PgStat_Kind kind)
  * the no-longer-wanted snapshot.  Updates of stats_fetch_consistency can
  * cause this routine to be called.
  */
-void
+TimestampTz
 pgstat_clear_snapshot(void)
 {
 	pgstat_assert_is_up();
@@ -934,6 +934,8 @@ pgstat_clear_snapshot(void)
 
 	/* Reset this flag, as it may be possible that a cleanup was forced. */
 	force_stats_snapshot_clear = false;
+
+	return GetCurrentTimestamp();
 }
 
 void *
diff --git a/src/backend/utils/adt/pgstatfuncs.c b/src/backend/utils/adt/pgstatfuncs.c
index b4ffc401626..89a941a94c4 100644
--- a/src/backend/utils/adt/pgstatfuncs.c
+++ b/src/backend/utils/adt/pgstatfuncs.c
@@ -1858,9 +1858,11 @@ pg_stat_get_snapshot_timestamp(PG_FUNCTION_ARGS)
 Datum
 pg_stat_clear_snapshot(PG_FUNCTION_ARGS)
 {
-	pgstat_clear_snapshot();
+	TimestampTz ts;
 
-	PG_RETURN_VOID();
+	ts = pgstat_clear_snapshot();
+
+	PG_RETURN_TIMESTAMPTZ(ts);
 }
 
 
diff --git a/src/include/catalog/pg_proc.dat b/src/include/catalog/pg_proc.dat
index e9b56688032..0a89cc02df9 100644
--- a/src/include/catalog/pg_proc.dat
+++ b/src/include/catalog/pg_proc.dat
@@ -6150,7 +6150,7 @@
 { oid => '2230',
   descr => 'statistics: discard current transaction\'s statistics snapshot',
   proname => 'pg_stat_clear_snapshot', proisstrict => 'f', provolatile => 'v',
-  proparallel => 'r', prorettype => 'void', proargtypes => '',
+  proparallel => 'r', prorettype => 'timestamptz', proargtypes => '',
   prosrc => 'pg_stat_clear_snapshot' },
 { oid => '2137',
   descr => 'statistics: force stats to be flushed after the next commit',
diff --git a/src/include/pgstat.h b/src/include/pgstat.h
index dca57e27599..80d7842822d 100644
--- a/src/include/pgstat.h
+++ b/src/include/pgstat.h
@@ -534,7 +534,7 @@ extern TimestampTz pgstat_reset(PgStat_Kind kind, Oid dboid, uint64 objid);
 extern TimestampTz pgstat_reset_of_kind(PgStat_Kind kind);
 
 /* stats accessors */
-extern void pgstat_clear_snapshot(void);
+extern TimestampTz pgstat_clear_snapshot(void);
 extern TimestampTz pgstat_get_stat_snapshot_timestamp(bool *have_snapshot);
 
 /* helpers */
diff --git a/src/test/isolation/expected/stats.out b/src/test/isolation/expected/stats.out
index 3b50447179d..8fe02a660d6 100644
--- a/src/test/isolation/expected/stats.out
+++ b/src/test/isolation/expected/stats.out
@@ -3440,10 +3440,10 @@ step s1_slru_check_stats:
 t       
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_slru_check_stats: 
@@ -3513,10 +3513,10 @@ step s1_slru_check_stats:
 f       
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_slru_check_stats: 
@@ -3586,10 +3586,10 @@ step s1_slru_check_stats:
 f       
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_slru_check_stats: 
@@ -3730,10 +3730,10 @@ name          |pg_stat_get_function_calls|total_above_zero|self_above_zero
 test_stat_func|                          |                |               
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_func_stats: 
diff --git a/src/test/isolation/expected/stats_1.out b/src/test/isolation/expected/stats_1.out
index 6960faa2930..0e3bf074abb 100644
--- a/src/test/isolation/expected/stats_1.out
+++ b/src/test/isolation/expected/stats_1.out
@@ -3464,10 +3464,10 @@ step s1_slru_check_stats:
 t       
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_slru_check_stats: 
@@ -3537,10 +3537,10 @@ step s1_slru_check_stats:
 f       
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_slru_check_stats: 
@@ -3610,10 +3610,10 @@ step s1_slru_check_stats:
 f       
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_slru_check_stats: 
@@ -3754,10 +3754,10 @@ name          |pg_stat_get_function_calls|total_above_zero|self_above_zero
 test_stat_func|                          |                |               
 (1 row)
 
-step s1_clear_snapshot: SELECT pg_stat_clear_snapshot();
-pg_stat_clear_snapshot
-----------------------
-                      
+step s1_clear_snapshot: SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+t
+-
+t
 (1 row)
 
 step s1_func_stats: 
diff --git a/src/test/isolation/specs/stats.spec b/src/test/isolation/specs/stats.spec
index a9f4e741d37..677e381ab12 100644
--- a/src/test/isolation/specs/stats.spec
+++ b/src/test/isolation/specs/stats.spec
@@ -43,7 +43,7 @@ setup { SET stats_fetch_consistency = 'none'; }
 step s1_fetch_consistency_none { SET stats_fetch_consistency = 'none'; }
 step s1_fetch_consistency_cache { SET stats_fetch_consistency = 'cache'; }
 step s1_fetch_consistency_snapshot { SET stats_fetch_consistency = 'snapshot'; }
-step s1_clear_snapshot { SELECT pg_stat_clear_snapshot(); }
+step s1_clear_snapshot { SELECT pg_stat_clear_snapshot() IS NOT NULL AS t; }
 step s1_begin { BEGIN; }
 step s1_commit { COMMIT; }
 step s1_rollback { ROLLBACK; }
diff --git a/src/test/regress/expected/stats.out b/src/test/regress/expected/stats.out
index c62d8ad26ff..5e4b637792e 100644
--- a/src/test/regress/expected/stats.out
+++ b/src/test/regress/expected/stats.out
@@ -1178,10 +1178,10 @@ SELECT pg_stat_get_snapshot_timestamp() >= NOW();
 (1 row)
 
 -- shows NULL again after clearing
-SELECT pg_stat_clear_snapshot();
- pg_stat_clear_snapshot 
-------------------------
- 
+SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
+ t 
+---
+ t
 (1 row)
 
 SELECT pg_stat_get_snapshot_timestamp();
diff --git a/src/test/regress/sql/stats.sql b/src/test/regress/sql/stats.sql
index 9e7f1a5fd2f..7e9a5a9c343 100644
--- a/src/test/regress/sql/stats.sql
+++ b/src/test/regress/sql/stats.sql
@@ -543,7 +543,7 @@ SELECT pg_stat_get_snapshot_timestamp();
 SELECT pg_stat_get_function_calls(0);
 SELECT pg_stat_get_snapshot_timestamp() >= NOW();
 -- shows NULL again after clearing
-SELECT pg_stat_clear_snapshot();
+SELECT pg_stat_clear_snapshot() IS NOT NULL AS t;
 SELECT pg_stat_get_snapshot_timestamp();
 COMMIT;
 
-- 
2.47.3

