Skip to content

Commit e4e45df

Browse files
robinsCommitfest Bot
authored and
Commitfest Bot
committed
Add support for pg_postmaster_open_time()
It is not always reliable to depend on pg_postmaster_start_time() for database uptime calculations, owing to how postmaster catches child process crashes, startup recovery etc. and continues without a restart. This could lead to multiple seconds (minutes or even hours) of difference when although postmaster was up, the database was not accepting connections. This function returns the start time when the database was ready to accept new database connections, allowing better calculation of database availability. On a standby, this time reflects the time the database was ready to accept read-only connections, whereas in single-user mode this time reflects the time the database was ready to accept user commands.
1 parent 15f0cb2 commit e4e45df

File tree

7 files changed

+52
-0
lines changed

7 files changed

+52
-0
lines changed

doc/src/sgml/func.sgml

+16
Original file line numberDiff line numberDiff line change
@@ -24916,6 +24916,22 @@ SELECT * FROM pg_ls_dir('.') WITH ORDINALITY AS t(ls,n);
2491624916
</para></entry>
2491724917
</row>
2491824918

24919+
<row>
24920+
<entry role="func_table_entry"><para role="func_signature">
24921+
<indexterm>
24922+
<primary>pg_postmaster_open_time</primary>
24923+
</indexterm>
24924+
<function>pg_postmaster_open_time</function> ()
24925+
<returnvalue>timestamp with time zone</returnvalue>
24926+
</para>
24927+
<para>
24928+
Returns the time when the server was open to connections. On a standby
24929+
this will be the time when the server was open to read-only connections.
24930+
In single-user mode this returns the time the server was ready to accept
24931+
user commands.
24932+
</para></entry>
24933+
</row>
24934+
2491924935
<row>
2492024936
<entry role="func_table_entry"><para role="func_signature">
2492124937
<indexterm>

src/backend/postmaster/launch_backend.c

+3
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,7 @@ typedef struct
111111
ProcSignalHeader *ProcSignal;
112112
pid_t PostmasterPid;
113113
TimestampTz PgStartTime;
114+
TimestampTz PgOpenStartTime;
114115
TimestampTz PgReloadTime;
115116
pg_time_t first_syslogger_file_time;
116117
bool redirection_done;
@@ -771,6 +772,7 @@ save_backend_variables(BackendParameters *param,
771772

772773
param->PostmasterPid = PostmasterPid;
773774
param->PgStartTime = PgStartTime;
775+
param->PgOpenStartTime = PgOpenStartTime;
774776
param->PgReloadTime = PgReloadTime;
775777
param->first_syslogger_file_time = first_syslogger_file_time;
776778

@@ -1031,6 +1033,7 @@ restore_backend_variables(BackendParameters *param)
10311033

10321034
PostmasterPid = param->PostmasterPid;
10331035
PgStartTime = param->PgStartTime;
1036+
PgOpenStartTime = param->PgOpenStartTime;
10341037
PgReloadTime = param->PgReloadTime;
10351038
first_syslogger_file_time = param->first_syslogger_file_time;
10361039

src/backend/postmaster/postmaster.c

+10
Original file line numberDiff line numberDiff line change
@@ -2342,6 +2342,11 @@ process_pm_child_exit(void)
23422342
*/
23432343
StartWorkerNeeded = true;
23442344

2345+
/*
2346+
* Remember time when database was open to connections
2347+
*/
2348+
PgOpenStartTime = GetCurrentTimestamp();
2349+
23452350
/* at this point we are really open for business */
23462351
ereport(LOG,
23472352
(errmsg("database system is ready to accept connections")));
@@ -3737,6 +3742,11 @@ process_pm_pmsignal(void)
37373742
ereport(LOG,
37383743
(errmsg("database system is ready to accept read-only connections")));
37393744

3745+
/*
3746+
* Remember time when database was open to connections
3747+
*/
3748+
PgOpenStartTime = GetCurrentTimestamp();
3749+
37403750
/* Report status */
37413751
AddToDataDirLockFile(LOCK_FILE_LINE_PM_STATUS, PM_STATUS_READY);
37423752
#ifdef USE_SYSTEMD

src/backend/tcop/postgres.c

+5
Original file line numberDiff line numberDiff line change
@@ -4157,6 +4157,11 @@ PostgresSingleUserMain(int argc, char *argv[],
41574157
*/
41584158
PgStartTime = GetCurrentTimestamp();
41594159

4160+
/*
4161+
* Remember when stand-alone was open to user commands.
4162+
*/
4163+
PgOpenStartTime = GetCurrentTimestamp();
4164+
41604165
/*
41614166
* Create a per-backend PGPROC struct in shared memory. We must do this
41624167
* before we can use LWLocks.

src/backend/utils/adt/timestamp.c

+9
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,9 @@
5353
/* Set at postmaster start */
5454
TimestampTz PgStartTime;
5555

56+
/* Set when database is open to connections */
57+
TimestampTz PgOpenStartTime;
58+
5659
/* Set at configuration reload */
5760
TimestampTz PgReloadTime;
5861

@@ -1629,6 +1632,12 @@ pg_postmaster_start_time(PG_FUNCTION_ARGS)
16291632
PG_RETURN_TIMESTAMPTZ(PgStartTime);
16301633
}
16311634

1635+
Datum
1636+
pg_postmaster_open_time(PG_FUNCTION_ARGS)
1637+
{
1638+
PG_RETURN_TIMESTAMPTZ(PgOpenStartTime);
1639+
}
1640+
16321641
Datum
16331642
pg_conf_load_time(PG_FUNCTION_ARGS)
16341643
{

src/include/catalog/pg_proc.dat

+6
Original file line numberDiff line numberDiff line change
@@ -8741,6 +8741,12 @@
87418741
prorettype => 'timestamptz', proargtypes => '',
87428742
prosrc => 'pg_postmaster_start_time' },
87438743

8744+
# open to connections start time function
8745+
{ oid => '8600', descr => 'open connections start time',
8746+
proname => 'pg_postmaster_open_time', provolatile => 's',
8747+
prorettype => 'timestamptz', proargtypes => '',
8748+
prosrc => 'pg_postmaster_open_time' },
8749+
87448750
# config reload time function
87458751
{ oid => '2034', descr => 'configuration load time',
87468752
proname => 'pg_conf_load_time', provolatile => 's', proparallel => 'r',

src/include/utils/timestamp.h

+3
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,9 @@ TimestampDifferenceMicroseconds(TimestampTz start_time,
9898
/* Set at postmaster start */
9999
extern PGDLLIMPORT TimestampTz PgStartTime;
100100

101+
/* Set when database is open to connections */
102+
extern PGDLLIMPORT TimestampTz PgOpenStartTime;
103+
101104
/* Set at configuration reload */
102105
extern PGDLLIMPORT TimestampTz PgReloadTime;
103106

0 commit comments

Comments
 (0)