standby clone: improve --dry-run output

Log positive check results as an additional confirmation that the
upstream configuration appears to be correct.
This commit is contained in:
Ian Barwick
2019-05-28 00:54:39 +09:00
parent 44a39760a1
commit c153e2fc02
3 changed files with 152 additions and 136 deletions

View File

@@ -53,6 +53,8 @@ static PGconn *_establish_db_connection(const char *conninfo,
static PGconn *_get_primary_connection(PGconn *standby_conn, int *primary_id, char *primary_conninfo_out, bool quiet);
static bool _set_config(PGconn *conn, const char *config_param, const char *sqlquery);
static bool _get_pg_setting(PGconn *conn, const char *setting, char *str_output, int *int_output);
static RecordStatus _get_node_record(PGconn *conn, char *sqlquery, t_node_info *node_info, bool init_defaults);
static void _populate_node_record(PGresult *res, t_node_info *node_info, int row, bool init_defaults);
@@ -995,52 +997,37 @@ guc_set(PGconn *conn, const char *parameter, const char *op,
return retval;
}
/**
* Just like guc_set except with an extra parameter containing the name of
* the pg datatype so that the comparison can be done properly.
*/
int
guc_set_typed(PGconn *conn, const char *parameter, const char *op,
const char *value, const char *datatype)
bool
get_pg_setting(PGconn *conn, const char *setting, char *output)
{
PQExpBufferData query;
PGresult *res = NULL;
int retval = 1;
bool success = _get_pg_setting(conn, setting, output, NULL);
char *escaped_parameter = escape_string(conn, parameter);
char *escaped_value = escape_string(conn, value);
initPQExpBuffer(&query);
appendPQExpBuffer(&query,
"SELECT true FROM pg_catalog.pg_settings "
" WHERE name = '%s' AND setting::%s %s '%s'::%s",
parameter, datatype, op, value, datatype);
log_verbose(LOG_DEBUG, "guc_set_typed():\n%s", query.data);
res = PQexec(conn, query.data);
if (PQresultStatus(res) != PGRES_TUPLES_OK)
if (success == true)
{
log_db_error(conn, query.data, _("guc_set_typed(): unable to execute query"));
retval = -1;
}
else if (PQntuples(res) == 0)
{
retval = 0;
log_verbose(LOG_DEBUG, _("get_pg_setting(): returned value is \"%s\""), output);
}
pfree(escaped_parameter);
pfree(escaped_value);
termPQExpBuffer(&query);
PQclear(res);
return retval;
return success;
}
bool
get_pg_setting(PGconn *conn, const char *setting, char *output)
get_pg_setting_int(PGconn *conn, const char *setting, int *output)
{
bool success = _get_pg_setting(conn, setting, NULL, output);
if (success == true)
{
log_verbose(LOG_DEBUG, _("get_pg_setting_int(): returned value is \"%i\""), *output);
}
return success;
}
bool
_get_pg_setting(PGconn *conn, const char *setting, char *str_output, int *int_output)
{
PQExpBufferData query;
PGresult *res = NULL;
@@ -1081,7 +1068,11 @@ get_pg_setting(PGconn *conn, const char *setting, char *output)
{
if (strcmp(PQgetvalue(res, i, 0), setting) == 0)
{
snprintf(output, MAXLEN, "%s", PQgetvalue(res, i, 1));
if (str_output != NULL)
snprintf(str_output, MAXLEN, "%s", PQgetvalue(res, i, 1));
else if (int_output != NULL)
*int_output = atoi(PQgetvalue(res, i, 1));
success = true;
break;
}
@@ -1092,10 +1083,6 @@ get_pg_setting(PGconn *conn, const char *setting, char *output)
}
}
if (success == true)
{
log_verbose(LOG_DEBUG, _("get_pg_setting(): returned value is \"%s\""), output);
}
termPQExpBuffer(&query);
PQclear(res);
@@ -1104,6 +1091,7 @@ get_pg_setting(PGconn *conn, const char *setting, char *output)
}
bool
alter_system_int(PGconn *conn, const char *name, int value)
{

View File

@@ -465,8 +465,8 @@ bool rollback_transaction(PGconn *conn);
bool set_config(PGconn *conn, const char *config_param, const char *config_value);
bool set_config_bool(PGconn *conn, const char *config_param, bool state);
int guc_set(PGconn *conn, const char *parameter, const char *op, const char *value);
int guc_set_typed(PGconn *conn, const char *parameter, const char *op, const char *value, const char *datatype);
bool get_pg_setting(PGconn *conn, const char *setting, char *output);
bool get_pg_setting_int(PGconn *conn, const char *setting, int *output);
bool alter_system_int(PGconn *conn, const char *name, int value);
bool pg_reload_conf(PGconn *conn);

View File

@@ -5198,6 +5198,7 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
ItemList backup_option_errors = {NULL, NULL};
bool xlog_stream = true;
standy_clone_mode mode;
bool pg_setting_ok;
/*
* Detecting the intended cloning mode
@@ -5299,13 +5300,14 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
if (config_file_options.use_replication_slots)
{
i = guc_set_typed(conn, "max_replication_slots", ">",
"0", "integer");
if (i == 0 || i == -1)
pg_setting_ok = get_pg_setting_int(conn, "max_replication_slots", &i);
if (pg_setting_ok == false || i < 1)
{
if (i == 0)
if (pg_setting_ok == true)
{
log_error(_("parameter \"max_replication_slots\" must be set to at least 1 to enable replication slots"));
log_detail(_("current value is %i"), i);
log_hint(_("\"max_replication_slots\" should be set to at least the number of expected standbys"));
if (exit_on_error == true)
{
@@ -5316,6 +5318,11 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
config_ok = false;
}
}
if (pg_setting_ok == true && i > 0 && runtime_options.dry_run == true)
{
log_info(_("parameter \"max_replication_slots\" set to %i"), i);
}
}
/*
@@ -5327,7 +5334,7 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
bool check_wal_keep_segments = false;
/*
* A non-zero `wal_keep_segments` value will almost certainly be
* A non-zero "wal_keep_segments" value will almost certainly be
* required if pg_basebackup is being used with --xlog-method=fetch,
* *and* no restore command has been specified
*/
@@ -5339,11 +5346,12 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
if (check_wal_keep_segments == true)
{
i = guc_set_typed(conn, "wal_keep_segments", ">", "0", "integer");
if (i == 0 || i == -1)
pg_setting_ok = get_pg_setting_int(conn, "wal_keep_segments", &i);
if (pg_setting_ok == false || i < 1)
{
if (i == 0)
if (pg_setting_ok == true)
{
log_error(_("parameter \"wal_keep_segments\" on the upstream server must be be set to a non-zero value"));
log_hint(_("Choose a value sufficiently high enough to retain enough WAL "
@@ -5355,8 +5363,7 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
{
log_hint(_("In PostgreSQL 9.4 and later, replication slots can be used, which "
"do not require \"wal_keep_segments\" to be set "
"(set parameter \"use_replication_slots\" in repmgr.conf to enable)\n"
));
"(set parameter \"use_replication_slots\" in repmgr.conf to enable)\n"));
}
}
@@ -5368,6 +5375,11 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
config_ok = false;
}
if (pg_setting_ok == true && i > 0 && runtime_options.dry_run == true)
{
log_info(_("parameter \"wal_keep_segments\" set to %i"), i);
}
}
}
@@ -5426,12 +5438,13 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
config_ok = false;
}
i = guc_set_typed(conn, "max_wal_senders", ">", "0", "integer");
if (i == 0 || i == -1)
pg_setting_ok = get_pg_setting_int(conn, "max_wal_senders", &i);
if (pg_setting_ok == false || i < 1)
{
if (i == 0)
if (pg_setting_ok == true)
{
log_error(_("parameter \"max_wal_senders\" must be set to be at least 1"));
log_error(_("parameter \"max_wal_senders\" must be set to be at least 1 %i"), i);
log_hint(_("\"max_wal_senders\" should be set to at least the number of expected standbys"));
}
@@ -5443,6 +5456,10 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
config_ok = false;
}
else if (pg_setting_ok == true && i > 0 && runtime_options.dry_run == true)
{
log_info(_("parameter \"max_wal_senders\" set to %i"), i);
}
/*
* If using pg_basebackup, ensure sufficient replication connections can
@@ -5458,7 +5475,7 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
int i;
int available_wal_senders;
int min_replication_connections = 1;
int possible_replication_connections = 0;
t_conninfo_param_list repl_conninfo = T_CONNINFO_PARAM_LIST_INITIALIZER;
@@ -5472,7 +5489,6 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
log_notice(_("checking for available walsenders on the source node (%i required)"),
min_replication_connections);
/*
* check how many free walsenders are available
*/
@@ -5496,8 +5512,15 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
exit(ERR_BAD_CONFIG);
}
}
else
else if (runtime_options.dry_run == true)
{
log_info(_("sufficient walsenders available on the source node"));
log_detail(_("%i required, %i available"),
min_replication_connections,
available_wal_senders);
}
/*
* Sufficient free walsenders appear to be available, check if
* we can connect to them. We check that the required number
@@ -5505,8 +5528,6 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
* "CONNECTION LIMIT" setting.
*/
int possible_replication_connections = 0;
log_notice(_("checking replication connections can be made to the source server (%i required)"),
min_replication_connections);
@@ -5571,7 +5592,6 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
config_ok = false;
log_error(_("unable to establish necessary replication connections"));
log_hint(_("check replication permissions on the source server"));
if (exit_on_error == true)
@@ -5580,11 +5600,19 @@ check_upstream_config(PGconn *conn, int server_version_num, t_node_info *upstrea
exit(ERR_BAD_CONFIG);
}
}
}
log_verbose(LOG_INFO, "sufficient walsenders available on source node (%i required)",
if (runtime_options.dry_run == true)
{
log_info(_("required number of replication connections could be made to the source server"));
log_detail(_("%i replication connections required"),
min_replication_connections);
}
else
{
log_verbose(LOG_INFO, _("sufficient replication connections could be made to the source server (%i required)"),
min_replication_connections);
}
}
return config_ok;
}