Class: ManageIQ::ApplianceConsole::DatabaseReplication

Inherits:
Object
  • Object
show all
Includes:
Logging, Prompts
Defined in:
lib/manageiq/appliance_console/database_replication.rb

Constant Summary collapse

PGPASS_FILE =
'/var/lib/pgsql/.pgpass'.freeze
NETWORK_INTERFACE =
'eth0'.freeze
REPGMR_FILE_LOCATIONS =
{
  "repmgr13" => {
    "config" => "/etc/repmgr/13/repmgr.conf",
    "log"    => "/var/log/repmgr/repmgrd-13.log"
  },
  "repmgr16" => {
    "config" => "/etc/repmgr/16/repmgr.conf",
    "log"    => "/var/log/repmgr/repmgrd-16.log"
  }
}.freeze

Constants included from Prompts

Prompts::CLEAR_CODE, Prompts::DOMAIN_REGEXP, Prompts::HOSTNAME_REGEXP, Prompts::INT_REGEXP, Prompts::IPV4_REGEXP, Prompts::IPV6_REGEXP, Prompts::IP_REGEXP, Prompts::MESSAGING_HOSTNAME_REGEXP, Prompts::MESSAGING_PASSWORD_REGEXP, Prompts::NONE_REGEXP

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Prompts

#are_you_sure?, #ask_for_disk, #ask_for_domain, #ask_for_hostname, #ask_for_hour_number, #ask_for_integer, #ask_for_ip, #ask_for_ip_or_hostname, #ask_for_ip_or_hostname_or_none, #ask_for_many, #ask_for_messaging_hostname, #ask_for_messaging_password, #ask_for_month_day_number, #ask_for_new_password, #ask_for_password, #ask_for_schedule_frequency, #ask_for_string, #ask_for_uri, #ask_for_week_day_number, #ask_with_menu, #ask_yn?, #clear_screen, #default_to_index, #just_ask, #press_any_key

Methods included from Logging

#error_and_logging_from_command_result_error, #error_and_logging_from_standard_error, #interactive, #interactive=, interactive?, #interactive?, #log_and_feedback, #log_and_feedback_exception, #log_and_feedback_info, #log_error, #log_prefix, #logger, #logger=, #say_error, #say_info

Instance Attribute Details

#database_nameObject

Returns the value of attribute database_name.



25
26
27
# File 'lib/manageiq/appliance_console/database_replication.rb', line 25

def database_name
  @database_name
end

#database_passwordObject

Returns the value of attribute database_password.



25
26
27
# File 'lib/manageiq/appliance_console/database_replication.rb', line 25

def database_password
  @database_password
end

#database_userObject

Returns the value of attribute database_user.



25
26
27
# File 'lib/manageiq/appliance_console/database_replication.rb', line 25

def database_user
  @database_user
end

#node_numberObject

Returns the value of attribute node_number.



25
26
27
# File 'lib/manageiq/appliance_console/database_replication.rb', line 25

def node_number
  @node_number
end

#primary_hostObject

Returns the value of attribute primary_host.



25
26
27
# File 'lib/manageiq/appliance_console/database_replication.rb', line 25

def primary_host
  @primary_host
end

Class Method Details

.repmgr_configObject



62
63
64
# File 'lib/manageiq/appliance_console/database_replication.rb', line 62

def self.repmgr_config
  repmgr_file_locations["config"]
end

.repmgr_configured?Boolean

Returns:

  • (Boolean)


66
67
68
# File 'lib/manageiq/appliance_console/database_replication.rb', line 66

def self.repmgr_configured?
  File.exist?(repmgr_config)
end

.repmgr_file_locationsObject



70
71
72
# File 'lib/manageiq/appliance_console/database_replication.rb', line 70

def self.repmgr_file_locations
  REPGMR_FILE_LOCATIONS[repmgr_service_name]
end

.repmgr_logObject



74
75
76
# File 'lib/manageiq/appliance_console/database_replication.rb', line 74

def self.repmgr_log
  repmgr_file_locations["log"]
end

.repmgr_service_nameObject



78
79
80
# File 'lib/manageiq/appliance_console/database_replication.rb', line 78

def self.repmgr_service_name
  @repmgr_service_name ||= File.exist?(REPGMR_FILE_LOCATIONS["repmgr16"]["config"]) ? "repmgr16" : "repmgr13"
end

Instance Method Details

#ask_for_database_credentialsObject



44
45
46
47
# File 'lib/manageiq/appliance_console/database_replication.rb', line 44

def ask_for_database_credentials
  ask_for_cluster_database_credentials
  self.primary_host = ask_for_ip_or_hostname("primary database hostname or IP address", primary_host)
end

#ask_for_unique_cluster_node_numberObject



40
41
42
# File 'lib/manageiq/appliance_console/database_replication.rb', line 40

def ask_for_unique_cluster_node_number
  self.node_number = ask_for_integer("number uniquely identifying this node in the replication cluster")
end

#config_file_contents(host) ⇒ Object



95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
# File 'lib/manageiq/appliance_console/database_replication.rb', line 95

def config_file_contents(host)
  service_name = PostgresAdmin.service_name
  # FYI, 5.0 made quoting strings strict.  Always use single quoted strings.
  # https://repmgr.org/docs/current/release-5.0.html
  <<-EOS.strip_heredoc
    node_id='#{node_number}'
    node_name='#{host}'
    conninfo='host=#{host} user=#{database_user} dbname=#{database_name}'
    use_replication_slots='1'
    pg_basebackup_options='--wal-method=stream'
    failover='automatic'
    promote_command='repmgr standby promote -f #{repmgr_config} --log-to-file'
    follow_command='repmgr standby follow -f #{repmgr_config} --log-to-file --upstream-node-id=%n'
    log_file='#{repmgr_log}'
    service_start_command='sudo systemctl start #{service_name}'
    service_stop_command='sudo systemctl stop #{service_name}'
    service_restart_command='sudo systemctl restart #{service_name}'
    service_reload_command='sudo systemctl reload #{service_name}'
    data_directory='#{PostgresAdmin.data_directory}'
  EOS
end

#confirmObject



49
50
51
52
53
54
55
56
57
58
59
60
# File 'lib/manageiq/appliance_console/database_replication.rb', line 49

def confirm
  clear_screen
  say(<<-EOL)
Replication Server Configuration

    Cluster Node Number:        #{node_number}
    Cluster Database Name:      #{database_name}
    Cluster Database User:      #{database_user}
    Cluster Database Password:  "********"
    Cluster Primary Host:       #{primary_host}
    EOL
end

#confirm_reconfigurationObject



84
85
86
87
88
# File 'lib/manageiq/appliance_console/database_replication.rb', line 84

def confirm_reconfiguration
  say("Warning: File #{repmgr_config} exists. Replication is already configured")
  logger.warn("Warning: File #{repmgr_config} exists. Replication is already configured")
  agree("Continue with configuration? (Y/N): ")
end

#create_config_file(host) ⇒ Object



90
91
92
93
# File 'lib/manageiq/appliance_console/database_replication.rb', line 90

def create_config_file(host)
  File.write(repmgr_config, config_file_contents(host))
  true
end

#network_interfacesObject



36
37
38
# File 'lib/manageiq/appliance_console/database_replication.rb', line 36

def network_interfaces
  @network_interfaces ||= LinuxAdmin::NetworkInterface.list.reject(&:loopback?)
end

#pgsslcertObject



28
29
30
# File 'lib/manageiq/appliance_console/database_replication.rb', line 28

def pgsslcert
  @pgsslcert ||= PostgresAdmin.data_directory.join("server.crt").freeze
end

#pgsslkeyObject



32
33
34
# File 'lib/manageiq/appliance_console/database_replication.rb', line 32

def pgsslkey
  @pgsslkey ||= PostgresAdmin.data_directory.join("server.key").freeze
end

#write_pgpass_fileObject



117
118
119
120
121
122
123
124
125
126
# File 'lib/manageiq/appliance_console/database_replication.rb', line 117

def write_pgpass_file
  File.open(PGPASS_FILE, "w") do |f|
    f.write("*:*:#{database_name}:#{database_user}:#{database_password}\n")
    f.write("*:*:replication:#{database_user}:#{database_password}\n")
  end

  FileUtils.chmod(0600, PGPASS_FILE)
  FileUtils.chown("postgres", "postgres", PGPASS_FILE)
  true
end