class ManageIQ::ApplianceConsole::DatabaseConfiguration

Constants

CREATE_REGION_AGREE
DB_YML
DB_YML_TMPL
DEFAULT_PORT
FAILED_WITH_ERROR_HYPHEN
REGION_RANGE

PG 9.2 bigint max 9223372036854775807 / ArRegion::DEFAULT_RAILS_SEQUENCE_FACTOR = 9223372 www.postgresql.org/docs/9.2/static/datatype-numeric.html 9223372 won't be a full region though, so we're not including it. TODO: This information should be shared outside of appliance console code and MiqRegion.

Attributes

adapter[RW]
database[RW]
host[RW]
password[R]
port[RW]
region[RW]
username[RW]

Public Class Methods

current() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 202
def self.current
  decrypt_password(load_current)
end
database_host() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 210
def self.database_host
  database_yml_configured? ? current[rails_env]['host'] || "localhost" : nil
end
database_name() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 214
def self.database_name
  database_yml_configured? ? current[rails_env]['database'] : nil
end
database_yml_configured?() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 206
def self.database_yml_configured?
  File.exist?(DB_YML) && File.exist?(KEY_FILE)
end
decrypt_password(settings) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 198
def self.decrypt_password(settings)
  encrypt_decrypt_password(settings) { |pass| ManageIQ::Password.try_decrypt(pass) }
end
encrypt_password(settings) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 194
def self.encrypt_password(settings)
  encrypt_decrypt_password(settings) { |pass| ManageIQ::Password.try_encrypt(pass) }
end
new(hash = {}) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 36
def initialize(hash = {})
  initialize_from_hash(hash)
  @adapter ||= "postgresql"
  # introduced by Logging
  self.interactive = true unless hash.key?(:interactive)
end
region() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 218
def self.region
  database_yml_configured? ? ManageIQ::ApplianceConsole::Utilities.db_region : nil
end

Private Class Methods

encrypt_decrypt_password(settings) { |pass| ... } click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 258
def self.encrypt_decrypt_password(settings)
  new_settings = {}
  settings.each_key { |section| new_settings[section] = settings[section].dup }
  pass = new_settings["production"]["password"]
  new_settings["production"]["password"] = yield(pass) if pass
  new_settings
end
load_current() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 266
def self.load_current
  require 'yaml'
  unless File.exist?(DB_YML)
    require 'fileutils'
    FileUtils.cp(DB_YML_TMPL, DB_YML) if File.exist?(DB_YML_TMPL)
  end
  YAML.load_file(DB_YML)
end
rails_env() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 253
def self.rails_env
  ENV["RAILS_ENV"] || "development"
end

Public Instance Methods

activate() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 67
def activate
  return false unless validated

  original = self.class.current
  success  = false

  begin
    save
    success = create_or_join_region
    validate_encryption_key!
  rescue
    success = false
  ensure
    save(original) unless success
  end
end
ask_for_database_credentials(password_twice = true) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 119
def ask_for_database_credentials(password_twice = true)
  self.host     = ask_for_ip_or_hostname("database hostname or IP address", host) if host.blank? || !local?
  self.port     = ask_for_integer("port number", nil, port) unless local?
  self.database = just_ask("name of the database on #{host}", database) unless local?
  self.username = just_ask("username", username) unless local?
  count = 0
  loop do
    password1 = ask_for_password("database password on #{host}", password)
    # if they took the default, just bail
    break if (password1 == password)

    if password1.strip.length == 0
      say("\nPassword can not be empty, please try again")
      next
    end
    if password_twice
      password2 = ask_for_password("database password again")
      if password1 == password2
        self.password = password1
        break
      elsif count > 0 # only reprompt password once
        raise "passwords did not match"
      else
        count += 1
        say("\nThe passwords did not match, please try again")
      end
    else
      self.password = password1
      break
    end
  end
end
create_new_region_questions(warn = true) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 111
def create_new_region_questions(warn = true)
  clear_screen
  say("\n\nNote: Creating a new database region requires an empty database.") if warn
  say("Each database region number must be unique.\n")
  self.region = ask_for_integer("database region number", REGION_RANGE)
  raise MiqSignalError if warn && !agree(CREATE_REGION_AGREE)
end
create_or_join_region() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 84
def create_or_join_region
  region ? create_region : join_region
end
create_region() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 88
def create_region
  hint = "Please stop the EVM server process on all appliances in the region"
  ManageIQ::ApplianceConsole::Utilities.bail_if_db_connections("preventing the setup of a database region.\n#{hint}")
  log_and_feedback(__method__) do
    ManageIQ::ApplianceConsole::Utilities.rake("evm:db:region", ["--", {:region => region}])
  end
end
friendly_inspect() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 152
    def friendly_inspect
      output = <<-FRIENDLY
Host:     #{host}
Username: #{username}
Database: #{database}
FRIENDLY
      output << "Port:     #{port}\n" if port
      output << "Region:   #{region}\n" if region
      output
    end
join_region() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 96
def join_region
  ManageIQ::ApplianceConsole::Utilities.rake("evm:join_region", {})
end
local?() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 59
def local?
  host.blank? || host.in?(%w(localhost 127.0.0.1))
end
merged_settings() click to toggle source

merge all the non specified setings for all the basic attributes, overwrite from this object (including blank values)

# File lib/manageiq/appliance_console/database_configuration.rb, line 176
def merged_settings
  merged = self.class.current
  settings_hash.each do |k, v|
    if v.present?
      merged['production'][k] = v
    else
      merged['production'].delete(k)
    end
  end
  merged
end
password=(value) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 63
def password=(value)
  @password = ManageIQ::Password.try_decrypt(value)
end
reset_region() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 100
def reset_region
  say("Warning: RESETTING A DATABASE WILL DESTROY ANY EXISTING DATA AND CANNOT BE UNDONE.\n\n")
  raise MiqSignalError unless are_you_sure?("reset the configured database")

  create_new_region_questions(false)
  ENV["DISABLE_DATABASE_ENVIRONMENT_CHECK"] = "1"
  create_region
ensure
  ENV["DISABLE_DATABASE_ENVIRONMENT_CHECK"] = nil
end
run_interactive() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 43
def run_interactive
  ask_questions

  clear_screen
  say "Activating the configuration using the following settings...\n#{friendly_inspect}\n"

  raise MiqSignalError unless activate

  post_activation
  say("\nConfiguration activated successfully.\n")
rescue RuntimeError => e
  puts "Configuration failed#{": " + e.message unless e.class == MiqSignalError}"
  press_any_key
  raise MiqSignalError
end
save(settings = nil) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 188
def save(settings = nil)
  settings ||= merged_settings
  settings = self.class.encrypt_password(settings)
  do_save(settings)
end
settings_hash() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 163
def settings_hash
  {
    'adapter'  => 'postgresql',
    'host'     => local? ? "localhost" : host,
    'port'     => port,
    'username' => username,
    'password' => password.presence,
    'database' => database
  }
end
start_evm() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 239
def start_evm
  pid = fork do
    begin
      LinuxAdmin::Service.new("evmserverd").start(true)
    rescue => e
      logger.error("Failed to enable and start evmserverd service: #{e.message}")
      logger.error(e.backtrace.join("\n"))
    end
  end
  Process.detach(pid)
end
validate!() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 230
def validate!
  pool = ModelWithNoBackingTable.establish_connection(settings_hash.delete_if { |_n, v| v.blank? })
  begin
    pool.connection
  ensure
    ModelWithNoBackingTable.remove_connection
  end
end
validated() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 222
def validated
  !!validate!
rescue => err
  log_error(__method__, err.message)
  say_error(__method__, err.message)
  false
end

Private Instance Methods

do_save(settings) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 280
def do_save(settings)
  require 'yaml'
  File.open(DB_YML, "w") do |f|
    f.write(YAML.dump(settings))
    f.chown(manageiq_uid, manageiq_gid)
  end
end
initialize_from_hash(hash) click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 288
def initialize_from_hash(hash)
  hash.each do |k, v|
    next if v.nil?
    setter = "#{k}="
    if self.respond_to?(setter)
      public_send(setter, v)
    else
      raise ArgumentError, "Invalid argument: #{k}"
    end
  end
end
validate_encryption_key!() click to toggle source
# File lib/manageiq/appliance_console/database_configuration.rb, line 275
def validate_encryption_key!
  raise "Encryption key invalid" unless ManageIQ::ApplianceConsole::Utilities.rake("evm:validate_encryption_key", {})
  true
end