manageiq-postgres_ha_admin 2.0.0 → 3.1.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 2ea7e89193add948ecd827491eae6c7e055c20a6
4
- data.tar.gz: d416a3b5fd696ca582e13e360b6ea00af762aa58
2
+ SHA256:
3
+ metadata.gz: 4bbec7e79b7ae7140dadbeb59bd561ef7469f8568a9c1d5b8a78d2464b50d57d
4
+ data.tar.gz: 4f04ad4bb6a91887e77e5b85247510294a18ef8083c1883d5be0ff7ae21898ca
5
5
  SHA512:
6
- metadata.gz: a76ffe81cb4c0f218a5374a333f2458da83c59ff14cbc285ba9787c58e4362568c7c0303d794f587098ae3aa4b6fe144fc44c6ef1270e990e1581e5c83521394
7
- data.tar.gz: 2aaeb1824891fad95440f473ccd864a048538ddcdf37832a9d3b8c492d29d81e1a1d353ee070aca4861136a5cea8a2152bd26bf90c94c989df29e2f1bd97e088
6
+ metadata.gz: b6767d711af5f8b2b219e9924c8293f89c29f4b03770151f100e6a390f92eafc9be1630c43aa7149414fdec3b5ef6c6d6c12983b6a7d78c5d774ce0a8b870db5
7
+ data.tar.gz: e6e63fa21d95062f54fcbb9dde5efa942ca46f0627a0d243076d4f2a7bd034029610ff722e1cf8bd04dae897ae314e2e04a0112d255392ffd3e9447f073e674a
@@ -34,6 +34,7 @@ engines:
34
34
  rubocop:
35
35
  enabled: true
36
36
  config: '.rubocop_cc.yml'
37
+ channel: 'rubocop-0-69'
37
38
  prepare:
38
39
  fetch:
39
40
  - url: "https://raw.githubusercontent.com/ManageIQ/guides/master/.rubocop_base.yml"
@@ -2,7 +2,6 @@ language: ruby
2
2
  rvm:
3
3
  - '2.3.1'
4
4
  - '2.4.2'
5
- sudo: false
6
5
  cache: bundler
7
6
  env:
8
7
  global:
@@ -10,5 +9,5 @@ env:
10
9
  - RUBY_GC_HEAP_INIT_SLOTS=600000
11
10
  - RUBY_GC_HEAP_GROWTH_FACTOR=1.25
12
11
  addons:
13
- postgresql: '9.5'
12
+ postgresql: '10'
14
13
  after_script: bundle exec codeclimate-test-reporter
@@ -3,7 +3,31 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  This project adheres to [Semantic Versioning](http://semver.org/).
5
5
 
6
- ## [Unreleased]
6
+ ## [3.1.2] - 2020-12-21
7
+ - Allow for Rails 6.0 [#23](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/23)
8
+
9
+ ## [3.1.1] - 2019-12-12
10
+ - Remove the dependency on linux_admin [#19](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/19)
11
+
12
+ ## [3.1.0] - 2019-05-09
13
+
14
+ ### Added
15
+ - Add a logical replication config handler [#17](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/17)
16
+
17
+ ## [3.0.1] - 2019-03-19
18
+
19
+ ### Changed
20
+ - Remove references to MiqPassword [#15](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/15)
21
+
22
+ ## [3.0.0] - 2018-09-05
23
+
24
+ ### Added
25
+ - Allow users of the gem to specify a logger object [#7](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/7)
26
+
27
+ ### Changed
28
+ - Make sources of database connection info pluggable [#8](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/8)
29
+ - Improve FailoverDatabases/ServerStore class [#9](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/9)
30
+ - Make failover monitor generic [#10](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/10)
7
31
 
8
32
  ## [2.0.0] - 2018-08-01
9
33
 
@@ -14,5 +38,10 @@ This project adheres to [Semantic Versioning](http://semver.org/).
14
38
  ### Changed
15
39
  - Make changes for upgrading repmgr to version 4 [#4](https://github.com/ManageIQ/manageiq-postgres_ha_admin/pull/4)
16
40
 
17
- [Unreleased]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v2.0.0...master
41
+ [Unreleased]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v3.1.2...master
42
+ [3.1.2]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v3.1.1...v3.1.2
43
+ [3.1.1]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v3.1.0...v3.1.1
44
+ [3.1.0]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v3.0.1...v3.1.0
45
+ [3.0.1]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v3.0.0...v3.0.1
46
+ [3.0.0]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v2.0.0...v3.0.0
18
47
  [2.0.0]: https://github.com/ManageIQ/manageiq-postgres_ha_admin/compare/v1.0.0...v2.0.0
@@ -0,0 +1 @@
1
+ * @carbonin
data/Gemfile CHANGED
@@ -1,7 +1,4 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
- # Specify your gem's dependencies in manageiq-smartstate.gemspec
3
+ # Specify your gem's dependencies in manageiq-postgres_ha_admin.gemspec
4
4
  gemspec
5
-
6
- # For MiqPassword
7
- gem "manageiq-gems-pending", :git => "https://github.com/ManageIQ/manageiq-gems-pending", :branch => "master"
data/README.md CHANGED
@@ -4,7 +4,6 @@
4
4
  [![Build Status](https://travis-ci.org/ManageIQ/manageiq-postgres_ha_admin.svg)](https://travis-ci.org/ManageIQ/manageiq-postgres_ha_admin)
5
5
  [![Code Climate](https://codeclimate.com/github/ManageIQ/manageiq-postgres_ha_admin.svg)](https://codeclimate.com/github/ManageIQ/manageiq-postgres_ha_admin)
6
6
  [![Test Coverage](https://codeclimate.com/github/ManageIQ/manageiq-postgres_ha_admin/badges/coverage.svg)](https://codeclimate.com/github/ManageIQ/manageiq-postgres_ha_admin/coverage)
7
- [![Dependency Status](https://gemnasium.com/ManageIQ/manageiq-postgres_ha_admin.svg)](https://gemnasium.com/ManageIQ/manageiq-postgres_ha_admin)
8
7
  [![Security](https://hakiri.io/github/ManageIQ/manageiq-postgres_ha_admin/master.svg)](https://hakiri.io/github/ManageIQ/manageiq-postgres_ha_admin/master)
9
8
 
10
9
  [![Chat](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ManageIQ/manageiq-postgres_ha_admin?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
@@ -1,4 +1,24 @@
1
1
  require 'manageiq/postgres_ha_admin/version'
2
- require 'manageiq/postgres_ha_admin/database_yml'
3
- require 'manageiq/postgres_ha_admin/failover_databases'
2
+
3
+ require 'manageiq/postgres_ha_admin/logging'
4
+ require 'manageiq/postgres_ha_admin/null_logger'
5
+
6
+ require 'manageiq/postgres_ha_admin/server_store'
4
7
  require 'manageiq/postgres_ha_admin/failover_monitor'
8
+
9
+ require 'manageiq/postgres_ha_admin/config_handler'
10
+ require 'manageiq/postgres_ha_admin/config_handler/rails_config_handler'
11
+ require 'manageiq/postgres_ha_admin/config_handler/pglogical_config_handler'
12
+ require 'manageiq/postgres_ha_admin/config_handler/logical_replication_config_handler'
13
+
14
+ module ManageIQ
15
+ module PostgresHaAdmin
16
+ class << self
17
+ attr_writer :logger
18
+ end
19
+
20
+ def self.logger
21
+ @logger ||= NullLogger.new
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,35 @@
1
+ module ManageIQ
2
+ module PostgresHaAdmin
3
+ class ConfigHandler
4
+ def name
5
+ "Config Handler"
6
+ end
7
+
8
+ def read
9
+ raise NotImplementedError
10
+ end
11
+
12
+ def write(_conninfo)
13
+ raise NotImplementedError
14
+ end
15
+
16
+ def before_failover(&block)
17
+ raise ArgumentError, "A block is required to set the before failover callback" unless block_given?
18
+ @before_failover_cb = block
19
+ end
20
+
21
+ def after_failover(&block)
22
+ raise ArgumentError, "A block is required to set the after failover callback" unless block_given?
23
+ @after_failover_cb = block
24
+ end
25
+
26
+ def do_before_failover
27
+ @before_failover_cb&.call
28
+ end
29
+
30
+ def do_after_failover(new_primary_conn_info)
31
+ @after_failover_cb&.call(new_primary_conn_info)
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,34 @@
1
+ require 'pg'
2
+ require 'pg/dsn_parser'
3
+
4
+ module ManageIQ
5
+ module PostgresHaAdmin
6
+ class LogicalReplicationConfigHandler < ConfigHandler
7
+ attr_reader :subscription, :conn_info
8
+
9
+ def initialize(options = {})
10
+ @subscription = options[:subscription]
11
+ @conn_info = options[:conn_info]
12
+ end
13
+
14
+ def name
15
+ "Logical Replication subscription #{subscription} Config Handler"
16
+ end
17
+
18
+ def read
19
+ conn = PG::Connection.open(@conn_info)
20
+ dsn = conn.exec_params(<<~SQL, [@subscription]).first["subconninfo"]
21
+ SELECT subconninfo
22
+ FROM pg_subscription
23
+ WHERE subname = $1
24
+ SQL
25
+ PG::DSNParser.new.parse(dsn)
26
+ end
27
+
28
+ def write(_params)
29
+ # Nothing to do here as the expectation is that the user will
30
+ # remove and re-add the subscription in the after failover callback
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,36 @@
1
+ require 'pg'
2
+ require 'pg/dsn_parser'
3
+
4
+ module ManageIQ
5
+ module PostgresHaAdmin
6
+ class PglogicalConfigHandler < ConfigHandler
7
+ attr_reader :subscription, :conn_info
8
+
9
+ def initialize(options = {})
10
+ @subscription = options[:subscription]
11
+ @conn_info = options[:conn_info]
12
+ end
13
+
14
+ def name
15
+ "pglogical subscription #{subscription} Config Handler"
16
+ end
17
+
18
+ def read
19
+ conn = PG::Connection.open(@conn_info)
20
+ dsn = conn.exec_params(<<~SQL, [@subscription]).first["if_dsn"]
21
+ SELECT if_dsn
22
+ FROM pglogical.subscription s
23
+ JOIN pglogical.node_interface i
24
+ ON s.sub_origin_if = i.if_id
25
+ WHERE s.sub_name = $1
26
+ SQL
27
+ PG::DSNParser.new.parse(dsn)
28
+ end
29
+
30
+ def write(_params)
31
+ # Nothing to do here as the expectation is that the user will
32
+ # remove and re-add the subscription in the after failover callback
33
+ end
34
+ end
35
+ end
36
+ end
@@ -1,32 +1,36 @@
1
1
  require 'active_support/all'
2
- require 'util/miq-password'
2
+ require 'manageiq-password'
3
3
  require 'fileutils'
4
4
 
5
5
  module ManageIQ
6
6
  module PostgresHaAdmin
7
- class DatabaseYml
8
- attr_reader :db_yml_file, :environment
7
+ class RailsConfigHandler < ConfigHandler
8
+ attr_reader :environment, :file_path
9
9
 
10
- def initialize(db_yml_file, environment)
11
- @db_yml_file = db_yml_file
12
- @environment = environment
10
+ def initialize(options = {})
11
+ @file_path = options[:file_path]
12
+ @environment = options[:environment]
13
13
  end
14
14
 
15
- def pg_params_from_database_yml
16
- rails_params_to_pg(YAML.load_file(db_yml_file)[environment])
15
+ def name
16
+ "Rails #{environment} Config Handler"
17
17
  end
18
18
 
19
- def update_database_yml(params)
20
- db_yml = YAML.load_file(db_yml_file)
19
+ def read
20
+ rails_params_to_pg(YAML.load_file(file_path)[environment])
21
+ end
22
+
23
+ def write(params)
24
+ db_yml = YAML.load_file(file_path)
21
25
  db_yml[environment].merge!(pg_parameters_to_rails(params))
22
26
  remove_empty(db_yml[environment])
23
27
 
24
- new_name = "#{db_yml_file}_#{Time.current.strftime("%d-%B-%Y_%H.%M.%S")}"
25
- FileUtils.copy(db_yml_file, new_name)
28
+ new_name = "#{file_path}_#{Time.current.strftime("%d-%B-%Y_%H.%M.%S")}"
29
+ FileUtils.copy(file_path, new_name)
26
30
  begin
27
- File.write(db_yml_file, db_yml.to_yaml)
31
+ File.write(file_path, db_yml.to_yaml)
28
32
  rescue
29
- FileUtils.mv(new_name, db_yml_file)
33
+ FileUtils.mv(new_name, file_path)
30
34
  raise
31
35
  end
32
36
  new_name
@@ -40,7 +44,7 @@ module PostgresHaAdmin
40
44
  pg_params[:user] = params['username']
41
45
  pg_params[:port] = params['port']
42
46
  pg_params[:host] = params['host']
43
- pg_params[:password] = MiqPassword.try_decrypt(params['password'])
47
+ pg_params[:password] = ManageIQ::Password.try_decrypt(params['password'])
44
48
  remove_empty(pg_params)
45
49
  end
46
50
 
@@ -1,52 +1,49 @@
1
1
  require 'active_support/all'
2
2
  require 'pg'
3
- require 'linux_admin'
4
3
 
5
4
  module ManageIQ
6
5
  module PostgresHaAdmin
7
6
  class FailoverMonitor
8
- RAILS_ROOT = [
9
- Pathname.new("/var/www/miq/vmdb"),
10
- Pathname.new(File.expand_path(File.join(__dir__, "../..")))
11
- ].detect { |f| File.exist?(f) }
7
+ include Logging
8
+
12
9
  FAILOVER_ATTEMPTS = 10
13
10
  DB_CHECK_FREQUENCY = 300
14
11
  FAILOVER_CHECK_FREQUENCY = 60
15
- LOG_FILE = '/var/www/miq/vmdb/log/ha_admin.log'.freeze
16
12
  attr_accessor :failover_attempts, :db_check_frequency, :failover_check_frequency
13
+ attr_reader :config_handlers
17
14
 
18
- def initialize(db_yml_file: '/var/www/miq/vmdb/config/database.yml',
19
- failover_yml_file: '/var/www/miq/vmdb/config/failover_databases.yml',
20
- ha_admin_yml_file: '/var/www/miq/vmdb/config/ha_admin.yml',
21
- logger: nil,
22
- environment: 'production')
23
- if logger.respond_to?(:error, :info)
24
- @logger = logger
25
- else
26
- @logger = Logger.new(LOG_FILE)
27
- @logger.level = Logger::INFO
28
- end
29
- @database_yml = DatabaseYml.new(db_yml_file, environment)
30
- @failover_db = FailoverDatabases.new(failover_yml_file, @logger)
31
- initialize_settings(ha_admin_yml_file)
15
+ def initialize(config_path = "")
16
+ initialize_settings(config_path)
17
+ @config_handlers = []
32
18
  end
33
19
 
34
- def monitor
35
- connection = pg_connection(@database_yml.pg_params_from_database_yml)
36
- if connection
37
- @failover_db.update_failover_yml(connection)
38
- connection.finish
39
- return
40
- end
41
-
42
- @logger.error("Primary Database is not available. EVM server stop initiated. Starting to execute failover...")
43
- stop_evmserverd
20
+ def add_handler(handler)
21
+ @config_handlers << [handler, ServerStore.new]
22
+ end
44
23
 
45
- if execute_failover
46
- start_evmserverd
47
- raise_failover_event
48
- else
49
- @logger.error("Failover failed")
24
+ def monitor
25
+ config_handlers.each do |handler, server_store|
26
+ begin
27
+ connection = pg_connection(handler.read)
28
+ if connection
29
+ server_store.update_servers(connection)
30
+ connection.finish
31
+ next
32
+ end
33
+
34
+ logger.error("Primary Database is not available for #{handler.name}. Starting to execute failover...")
35
+ handler.do_before_failover
36
+
37
+ new_conn_info = execute_failover(handler, server_store)
38
+ if new_conn_info
39
+ handler.do_after_failover(new_conn_info)
40
+ else
41
+ logger.error("Failover failed")
42
+ end
43
+ rescue => e
44
+ logger.error("Received #{e.class} error while monitoring #{handler.name}: #{e.message}")
45
+ logger.error(e.backtrace)
46
+ end
50
47
  end
51
48
  end
52
49
 
@@ -55,59 +52,52 @@ module PostgresHaAdmin
55
52
  begin
56
53
  monitor
57
54
  rescue => err
58
- @logger.error("#{err.class}: #{err}")
59
- @logger.error(err.backtrace.join("\n"))
55
+ logger.error("#{err.class}: #{err}")
56
+ logger.error(err.backtrace.join("\n"))
60
57
  end
61
58
  sleep(db_check_frequency)
62
59
  end
63
60
  end
64
61
 
65
- def active_servers_conninfo
66
- servers = @failover_db.active_databases_conninfo_hash
67
- db_yml_params = @database_yml.pg_params_from_database_yml
68
- servers.map! { |info| db_yml_params.merge(info) }
69
- end
70
-
71
- def raise_failover_event
72
- require "awesome_spawn"
73
- AwesomeSpawn.run("rake evm:raise_server_event",
74
- :chdir => RAILS_ROOT,
75
- :params => ["--", {:event => "db_failover_executed"}])
62
+ def active_servers_conninfo(handler, server_store)
63
+ servers = server_store.connection_info_list
64
+ current_params = handler.read
65
+ servers.map! { |info| current_params.merge(info) }
76
66
  end
77
67
 
78
68
  private
79
69
 
80
70
  def initialize_settings(ha_admin_yml_file)
71
+ ha_admin_yml = {}
81
72
  begin
82
- ha_admin_yml = YAML.load_file(ha_admin_yml_file)
73
+ ha_admin_yml = YAML.load_file(ha_admin_yml_file) if File.exist?(ha_admin_yml_file)
83
74
  rescue SystemCallError, IOError => err
84
- ha_admin_yml = {}
85
- @logger.error("#{err.class}: #{err}")
86
- @logger.info("File not loaded: #{ha_admin_yml_file}. Default settings for failover will be used.")
75
+ logger.error("#{err.class}: #{err}")
76
+ logger.info("File not loaded: #{ha_admin_yml_file}. Default settings for failover will be used.")
87
77
  end
88
78
  @failover_attempts = ha_admin_yml['failover_attempts'] || FAILOVER_ATTEMPTS
89
79
  @db_check_frequency = ha_admin_yml['db_check_frequency'] || DB_CHECK_FREQUENCY
90
80
  @failover_check_frequency = ha_admin_yml['failover_check_frequency'] || FAILOVER_CHECK_FREQUENCY
91
- @logger.info("FAILOVER_ATTEMPTS=#{@failover_attempts} DB_CHECK_FREQUENCY=#{@db_check_frequency} FAILOVER_CHECK_FREQUENCY=#{@failover_check_frequency}")
81
+ logger.info("FAILOVER_ATTEMPTS=#{@failover_attempts} DB_CHECK_FREQUENCY=#{@db_check_frequency} FAILOVER_CHECK_FREQUENCY=#{@failover_check_frequency}")
92
82
  end
93
83
 
94
- def execute_failover
84
+ def execute_failover(handler, server_store)
95
85
  failover_attempts.times do
96
- with_each_standby_connection do |connection, params|
86
+ with_each_standby_connection(handler, server_store) do |connection, params|
97
87
  next if database_in_recovery?(connection)
98
- next unless @failover_db.host_is_repmgr_primary?(params[:host], connection)
99
- @logger.info("Failing over to server using conninfo: #{params.reject { |k, _v| k == :password }}")
100
- @failover_db.update_failover_yml(connection)
101
- @database_yml.update_database_yml(params)
102
- return true
88
+ next unless server_store.host_is_primary?(params[:host], connection)
89
+ logger.info("Failing over to server using conninfo: #{params.reject { |k, _v| k == :password }}")
90
+ server_store.update_servers(connection)
91
+ handler.write(params)
92
+ return params
103
93
  end
104
94
  sleep(failover_check_frequency)
105
95
  end
106
96
  false
107
97
  end
108
98
 
109
- def with_each_standby_connection
110
- active_servers_conninfo.each do |params|
99
+ def with_each_standby_connection(handler, server_store)
100
+ active_servers_conninfo(handler, server_store).each do |params|
111
101
  connection = pg_connection(params)
112
102
  next if connection.nil?
113
103
  begin
@@ -121,19 +111,10 @@ module PostgresHaAdmin
121
111
  def pg_connection(params)
122
112
  PG::Connection.open(params)
123
113
  rescue PG::Error => e
124
- @logger.error("Failed to establish PG connection: #{e.message}")
114
+ logger.error("Failed to establish PG connection: #{e.message}")
125
115
  nil
126
116
  end
127
117
 
128
- def start_evmserverd
129
- LinuxAdmin::Service.new("evmserverd").restart
130
- @logger.info("Starting EVM server from failover monitor")
131
- end
132
-
133
- def stop_evmserverd
134
- LinuxAdmin::Service.new("evmserverd").stop
135
- end
136
-
137
118
  # Checks if postgres database is in recovery mode
138
119
  #
139
120
  # @param pg_connection [PG::Connection] established pg connection
@@ -0,0 +1,9 @@
1
+ module ManageIQ
2
+ module PostgresHaAdmin
3
+ module Logging
4
+ def logger
5
+ ManageIQ::PostgresHaAdmin.logger
6
+ end
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,13 @@
1
+ require 'logger'
2
+
3
+ module ManageIQ
4
+ module PostgresHaAdmin
5
+ class NullLogger < Logger
6
+ def initialize(*_args)
7
+ end
8
+
9
+ def add(*_args, &_block)
10
+ end
11
+ end
12
+ end
13
+ end
@@ -4,38 +4,38 @@ require 'pg/dsn_parser'
4
4
 
5
5
  module ManageIQ
6
6
  module PostgresHaAdmin
7
- class FailoverDatabases
7
+ class ServerStore
8
+ include Logging
9
+
8
10
  TABLE_NAME = "repmgr.nodes".freeze
9
11
 
10
- attr_reader :yml_file
12
+ attr_reader :servers
11
13
 
12
- def initialize(yml_file, logger)
13
- @yml_file = yml_file
14
- @logger = logger
14
+ def initialize
15
+ @servers = []
15
16
  end
16
17
 
17
- def active_databases_conninfo_hash
18
+ def connection_info_list
18
19
  valid_keys = PG::Connection.conndefaults_hash.keys + [:requiressl]
19
- active_databases.map! do |db_info|
20
+ servers.map! do |db_info|
20
21
  db_info.keep_if { |k, _v| valid_keys.include?(k) }
21
22
  end
22
23
  end
23
24
 
24
- def active_databases
25
- all_databases.select { |record| record[:active] }
26
- end
27
-
28
- def update_failover_yml(connection)
29
- arr_yml = query_repmgr(connection)
30
- File.write(yml_file, arr_yml.to_yaml) unless arr_yml.empty?
25
+ def update_servers(connection)
26
+ new_servers = query_repmgr(connection)
27
+ if servers_changed?(new_servers)
28
+ logger.info("Updating servers cache to #{new_servers}")
29
+ @servers = new_servers
30
+ end
31
31
  rescue IOError => err
32
- @logger.error("#{err.class}: #{err}")
33
- @logger.error(err.backtrace.join("\n"))
32
+ logger.error("#{err.class}: #{err}")
33
+ logger.error(err.backtrace.join("\n"))
34
34
  end
35
35
 
36
- def host_is_repmgr_primary?(host, connection)
36
+ def host_is_primary?(host, connection)
37
37
  query_repmgr(connection).each do |record|
38
- if record[:host] == host && entry_is_active_master?(record)
38
+ if record[:host] == host && record[:type] == 'primary'
39
39
  return true
40
40
  end
41
41
  end
@@ -44,10 +44,14 @@ module PostgresHaAdmin
44
44
 
45
45
  private
46
46
 
47
+ def servers_changed?(new_servers)
48
+ ((servers - new_servers) + (new_servers - servers)).any?
49
+ end
50
+
47
51
  def query_repmgr(connection)
48
52
  return [] unless table_exists?(connection, TABLE_NAME)
49
53
  result = []
50
- db_result = connection.exec("SELECT type, conninfo, active FROM #{TABLE_NAME}")
54
+ db_result = connection.exec("SELECT type, conninfo, active FROM #{TABLE_NAME} WHERE active")
51
55
  db_result.map_types!(PG::BasicTypeMapForResults.new(connection)).each do |record|
52
56
  dsn = PG::DSNParser.parse(record.delete("conninfo"))
53
57
  result << record.symbolize_keys.merge(dsn)
@@ -55,20 +59,11 @@ module PostgresHaAdmin
55
59
  db_result.clear
56
60
  result
57
61
  rescue PG::Error => err
58
- @logger.error("#{err.class}: #{err}")
59
- @logger.error(err.backtrace.join("\n"))
62
+ logger.error("#{err.class}: #{err}")
63
+ logger.error(err.backtrace.join("\n"))
60
64
  result
61
65
  end
62
66
 
63
- def entry_is_active_master?(record)
64
- record[:type] == 'primary' && record[:active]
65
- end
66
-
67
- def all_databases
68
- return [] unless File.exist?(yml_file)
69
- YAML.load_file(yml_file)
70
- end
71
-
72
67
  def table_exists?(connection, table_name)
73
68
  result = connection.exec("SELECT to_regclass('#{table_name}')").first
74
69
  !result['to_regclass'].nil?
@@ -1,5 +1,5 @@
1
1
  module ManageIQ
2
2
  module PostgresHaAdmin
3
- VERSION = '2.0.0'.freeze
3
+ VERSION = '3.1.2'.freeze
4
4
  end
5
5
  end
@@ -20,10 +20,11 @@ Gem::Specification.new do |spec|
20
20
  spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
21
21
  spec.require_paths = ["lib"]
22
22
 
23
- spec.add_runtime_dependency "awesome_spawn", "~> 1.4"
24
- spec.add_runtime_dependency "linux_admin", "~> 1.0"
23
+ spec.add_runtime_dependency "activesupport", ">=5.0", "< 6.1"
24
+ spec.add_runtime_dependency "awesome_spawn", "~> 1.4"
25
+ spec.add_runtime_dependency "manageiq-password", "~> 0.3"
25
26
  spec.add_runtime_dependency "pg"
26
- spec.add_runtime_dependency "pg-dsn_parser", "~> 0.1"
27
+ spec.add_runtime_dependency "pg-dsn_parser", "~> 0.1"
27
28
 
28
29
  spec.add_development_dependency "bundler"
29
30
  spec.add_development_dependency "codeclimate-test-reporter", "~> 1.0.0"
metadata CHANGED
@@ -1,15 +1,35 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: manageiq-postgres_ha_admin
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.0
4
+ version: 3.1.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - ManageIQ Developers
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-08-01 00:00:00.000000000 Z
11
+ date: 2020-12-21 00:00:00.000000000 Z
12
12
  dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: activesupport
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '5.0'
20
+ - - "<"
21
+ - !ruby/object:Gem::Version
22
+ version: '6.1'
23
+ type: :runtime
24
+ prerelease: false
25
+ version_requirements: !ruby/object:Gem::Requirement
26
+ requirements:
27
+ - - ">="
28
+ - !ruby/object:Gem::Version
29
+ version: '5.0'
30
+ - - "<"
31
+ - !ruby/object:Gem::Version
32
+ version: '6.1'
13
33
  - !ruby/object:Gem::Dependency
14
34
  name: awesome_spawn
15
35
  requirement: !ruby/object:Gem::Requirement
@@ -25,19 +45,19 @@ dependencies:
25
45
  - !ruby/object:Gem::Version
26
46
  version: '1.4'
27
47
  - !ruby/object:Gem::Dependency
28
- name: linux_admin
48
+ name: manageiq-password
29
49
  requirement: !ruby/object:Gem::Requirement
30
50
  requirements:
31
51
  - - "~>"
32
52
  - !ruby/object:Gem::Version
33
- version: '1.0'
53
+ version: '0.3'
34
54
  type: :runtime
35
55
  prerelease: false
36
56
  version_requirements: !ruby/object:Gem::Requirement
37
57
  requirements:
38
58
  - - "~>"
39
59
  - !ruby/object:Gem::Version
40
- version: '1.0'
60
+ version: '0.3'
41
61
  - !ruby/object:Gem::Dependency
42
62
  name: pg
43
63
  requirement: !ruby/object:Gem::Requirement
@@ -152,8 +172,7 @@ dependencies:
152
172
  version: '0'
153
173
  description: ManageIQ Postgres H.A. Admin
154
174
  email:
155
- executables:
156
- - postgres_ha_admin
175
+ executables: []
157
176
  extensions: []
158
177
  extra_rdoc_files: []
159
178
  files:
@@ -166,15 +185,20 @@ files:
166
185
  - ".rubocop_local.yml"
167
186
  - ".travis.yml"
168
187
  - CHANGELOG.md
188
+ - CODEOWNERS
169
189
  - Gemfile
170
190
  - LICENSE.txt
171
191
  - README.md
172
192
  - Rakefile
173
- - bin/postgres_ha_admin
174
193
  - lib/manageiq-postgres_ha_admin.rb
175
- - lib/manageiq/postgres_ha_admin/database_yml.rb
176
- - lib/manageiq/postgres_ha_admin/failover_databases.rb
194
+ - lib/manageiq/postgres_ha_admin/config_handler.rb
195
+ - lib/manageiq/postgres_ha_admin/config_handler/logical_replication_config_handler.rb
196
+ - lib/manageiq/postgres_ha_admin/config_handler/pglogical_config_handler.rb
197
+ - lib/manageiq/postgres_ha_admin/config_handler/rails_config_handler.rb
177
198
  - lib/manageiq/postgres_ha_admin/failover_monitor.rb
199
+ - lib/manageiq/postgres_ha_admin/logging.rb
200
+ - lib/manageiq/postgres_ha_admin/null_logger.rb
201
+ - lib/manageiq/postgres_ha_admin/server_store.rb
178
202
  - lib/manageiq/postgres_ha_admin/version.rb
179
203
  - manageiq-postgres_ha_admin.gemspec
180
204
  homepage: https://github.com/ManageIQ/manageiq-postgres_ha_admin
@@ -196,8 +220,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
196
220
  - !ruby/object:Gem::Version
197
221
  version: '0'
198
222
  requirements: []
199
- rubyforge_project:
200
- rubygems_version: 2.6.14
223
+ rubygems_version: 3.0.6
201
224
  signing_key:
202
225
  specification_version: 4
203
226
  summary: ManageIQ Postgres H.A. Admin
@@ -1,7 +0,0 @@
1
- #!/bin/env ruby
2
-
3
- require 'bundler/setup'
4
- require 'manageiq-postgres_ha_admin'
5
-
6
- monitor = ManageIQ::PostgresHaAdmin::FailoverMonitor.new
7
- monitor.monitor_loop