244 lines
10 KiB
Ruby
244 lines
10 KiB
Ruby
# The set of facts about ScaleIO cluster.
|
|
# All facts expect that MDM IPs are available via the fact 'mdm_ips'.
|
|
# If mdm_ips is absent then the facts are skipped.
|
|
# The facts about SDS/SDC and getting IPs from Gateway additionally expect that
|
|
# MDM password is available via the fact 'mdm_password'.
|
|
#
|
|
# Facts about MDM:
|
|
# (they go over the MDM IPs one by one and request informatiom from the MDM cluster
|
|
# via SCLI query_cluster command)
|
|
# ---------------------------------------------------------------------------------
|
|
# | Name | Description
|
|
# |--------------------------------------------------------------------------------
|
|
# | scaleio_mdm_ips | Comma separated list of MDM IPs (excepting stanby)
|
|
# | scaleio_mdm_names | Comma separated list of MDM names (excepting stanby)
|
|
# | scaleio_tb_ips | Comma separated list of Tie-Breaker IPs (excepting stanby)
|
|
# | scaleio_tb_names | Comma separated list of Tie-Breaker names (excepting stanby)
|
|
# | scaleio_standby_mdm_ips | Comma separated list of standby managers IPs
|
|
# | scaleio_standby_tb_ips | Comma separated list of stnadby tie breakers IPs
|
|
#
|
|
# Facts about SDS and SDC:
|
|
# (they use MDM IPs as a single list and request information from a cluster via
|
|
# SCLI query_all_sds and query_cll_sdc commands)
|
|
# ---------------------------------------------------------------------------------
|
|
# | Name | Description
|
|
# |--------------------------------------------------------------------------------
|
|
# | scaleio_sds_ips | Comma separated list of SDS IPs.
|
|
# | scaleio_sds_names | Comma separated list of SDS names.
|
|
# | scaleio_sdc_ips | Comma separated list of SDC IPs,
|
|
# | | it is list of management IPs, not storage IPs.
|
|
# | scaleio_sds_with_protection_domain_list | Comma separated list of SDS
|
|
# | | with its Protection domains: sds1,pd1,sds2,pd2,..
|
|
# Facts about MDM from Gateway:
|
|
# (It requests them from Gateway via curl and requires the fact 'gateway_ips'.
|
|
# An user is 'admin' by default or the fact 'gateway_user' if it exists.
|
|
# A port is 4443 or the fact 'gateway_port' if it exists.)
|
|
# ---------------------------------------------------------------------------------
|
|
# | Name | Description
|
|
# |--------------------------------------------------------------------------------
|
|
# | scaleio_mdm_ips_from_gateway | Comma separated list of MDM IP.
|
|
|
|
|
|
require 'date'
|
|
require 'facter'
|
|
require 'json'
|
|
|
|
$scaleio_log_file = "/var/log/fuel-plugin-scaleio.log"
|
|
|
|
def debug_log(msg)
|
|
File.open($scaleio_log_file, 'a') {|f| f.write("%s: %s\n" % [Time.now.strftime("%Y-%m-%d %H:%M:%S"), msg]) }
|
|
end
|
|
|
|
|
|
# Facter to scan existing cluster
|
|
# Controller IPs to scan
|
|
$controller_ips = Facter.value(:controller_ips)
|
|
if $controller_ips and $controller_ips != ''
|
|
# Register all facts for MDMs
|
|
# Example of output that facters below parse:
|
|
# Cluster:
|
|
# Mode: 3_node, State: Normal, Active: 3/3, Replicas: 2/2
|
|
# Master MDM:
|
|
# Name: 192.168.0.4, ID: 0x0ecb483853835e00
|
|
# IPs: 192.168.0.4, Management IPs: 192.168.0.4, Port: 9011
|
|
# Version: 2.0.5014
|
|
# Slave MDMs:
|
|
# Name: 192.168.0.5, ID: 0x3175fbe7695bbac1
|
|
# IPs: 192.168.0.5, Management IPs: 192.168.0.5, Port: 9011
|
|
# Status: Normal, Version: 2.0.5014
|
|
# Tie-Breakers:
|
|
# Name: 192.168.0.6, ID: 0x74ccbc567622b992
|
|
# IPs: 192.168.0.6, Port: 9011
|
|
# Status: Normal, Version: 2.0.5014
|
|
# Standby MDMs:
|
|
# Name: 192.168.0.5, ID: 0x0ce414fa06a17491, Manager
|
|
# IPs: 192.168.0.5, Management IPs: 192.168.0.5, Port: 9011
|
|
# Name: 192.168.0.6, ID: 0x74ccbc567622b992, Tie Breaker
|
|
# IPs: 192.168.0.6, Port: 9011
|
|
mdm_components = {
|
|
'scaleio_mdm_ips' => ['/Master MDM/,/\(Tie-Breakers\)\|\(Standby MDMs\)/p', '/./,//p', 'IPs:'],
|
|
'scaleio_tb_ips' => ['/Tie-Breakers/,/Standby MDMs/p', '/./,//p', 'IPs:'],
|
|
'scaleio_mdm_names' => ['/Master MDM/,/\(Tie-Breakers\)\|\(Standby MDMs\)/p', '/./,//p', 'Name:'],
|
|
'scaleio_tb_names' => ['/Tie-Breakers/,/Standby MDMs/p', '/./,//p', 'Name:'],
|
|
'scaleio_standby_mdm_ips' => ['/Standby MDMs/,//p', '/Manager/,/Tie Breaker/p', 'IPs:'],
|
|
'scaleio_standby_tb_ips' => ['/Standby MDMs/,//p', '/Tie Breaker/,/Manager/p', 'IPs:'],
|
|
}
|
|
# Define mdm opts for SCLI tool to connect to ScaleIO cluster.
|
|
# If there is no mdm_ips available it is expected to be run on a node with MDM Master.
|
|
mdm_opts = []
|
|
$controller_ips.split(',').each do |ip|
|
|
mdm_opts.push("--mdm_ip %s" % ip)
|
|
end
|
|
# the cycle over MDM IPs because for query cluster SCLI's behaiveour is strange
|
|
# it works for one IP but doesn't for the list.
|
|
query_result = nil
|
|
mdm_opts.detect do |opts|
|
|
query_cmd = "scli %s --query_cluster --approve_certificate 2>>%s && echo success" % [opts, $scaleio_log_file]
|
|
res = Facter::Util::Resolution.exec(query_cmd)
|
|
debug_log("%s returns:\n'%s'" % [query_cmd, res])
|
|
query_result = res unless !res or !res.include?('success')
|
|
end
|
|
if query_result
|
|
mdm_components.each do |name, selector|
|
|
Facter.add(name) do
|
|
setcode do
|
|
ip = nil
|
|
cmd = "echo '%s' | sed -n '%s' | sed -n '%s' | awk '/%s/ {print($2)}' | tr -d ','" % [query_result, selector[0], selector[1], selector[2]]
|
|
res = Facter::Util::Resolution.exec(cmd)
|
|
ip = res.split(' ').join(',') unless !res
|
|
debug_log("%s='%s'" % [name, ip])
|
|
ip
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|
|
# Facter to scan existing cluster
|
|
# MDM IPs to scan
|
|
$discovery_allowed = Facter.value(:discovery_allowed)
|
|
$mdm_ips = Facter.value(:mdm_ips)
|
|
$mdm_password = Facter.value(:mdm_password)
|
|
if $discovery_allowed == 'yes' and $mdm_ips and $mdm_ips != '' and $mdm_password and $mdm_password != ''
|
|
sds_sdc_components = {
|
|
'scaleio_sdc_ips' => ['sdc', 'IP: [^ ]*', nil],
|
|
'scaleio_sds_ips' => ['sds', 'IP: [^ ]*', 'Protection Domain'],
|
|
'scaleio_sds_names' => ['sds', 'Name: [^ ]*', 'Protection Domain'],
|
|
}
|
|
|
|
sds_sdc_components.each do |name, selector|
|
|
Facter.add(name) do
|
|
setcode do
|
|
mdm_opts = "--mdm_ip %s" % $mdm_ips
|
|
login_cmd = "scli %s --approve_certificate --login --username admin --password %s 1>/dev/null 2>>%s" % [mdm_opts, $mdm_password, $scaleio_log_file]
|
|
query_cmd = "scli %s --approve_certificate --query_all_%s 2>>%s" % [mdm_opts, selector[0], $scaleio_log_file]
|
|
cmd = "%s && %s" % [login_cmd, query_cmd]
|
|
debug_log(cmd)
|
|
result = Facter::Util::Resolution.exec(cmd)
|
|
if result
|
|
skip_cmd = ''
|
|
if selector[2]
|
|
skip_cmd = "grep -v '%s' | " % selector[2]
|
|
end
|
|
select_cmd = "%s grep -o '%s' | awk '{print($2)}'" % [skip_cmd, selector[1]]
|
|
cmd = "echo '%s' | %s" % [result, select_cmd]
|
|
debug_log(cmd)
|
|
result = Facter::Util::Resolution.exec(cmd)
|
|
if result
|
|
result = result.split(' ')
|
|
if result.count() > 0
|
|
result = result.join(',')
|
|
end
|
|
end
|
|
end
|
|
debug_log("%s='%s'" % [name, result])
|
|
result
|
|
end
|
|
end
|
|
end
|
|
|
|
Facter.add(:scaleio_storage_pools) do
|
|
setcode do
|
|
mdm_opts = "--mdm_ip %s" % $mdm_ips
|
|
login_cmd = "scli %s --approve_certificate --login --username admin --password %s 1>/dev/null 2>>%s" % [mdm_opts, $mdm_password, $scaleio_log_file]
|
|
query_cmd = "scli %s --approve_certificate --query_all 2>>%s" % [mdm_opts, $scaleio_log_file]
|
|
fiter_cmd = "awk '/Protection Domain|Storage Pool/ {if($2==\"Domain\"){pd=$3}else{if($2==\"Pool\"){print(pd\":\"$3)}}}'"
|
|
cmd = "%s && %s | %s" % [login_cmd, query_cmd, fiter_cmd]
|
|
debug_log(cmd)
|
|
result = Facter::Util::Resolution.exec(cmd)
|
|
if result
|
|
result = result.split(' ')
|
|
if result.count() > 0
|
|
result = result.join(',')
|
|
end
|
|
end
|
|
debug_log("%s='%s'" % ['scaleio_storage_pools', result])
|
|
result
|
|
end
|
|
end
|
|
|
|
Facter.add(:scaleio_sds_with_protection_domain_list) do
|
|
setcode do
|
|
mdm_opts = "--mdm_ip %s" % $mdm_ips
|
|
login_cmd = "scli %s --approve_certificate --login --username admin --password %s 1>/dev/null 2>>%s" % [mdm_opts, $mdm_password, $scaleio_log_file]
|
|
query_cmd = "scli %s --approve_certificate --query_all_sds 2>>%s" % [mdm_opts, $scaleio_log_file]
|
|
fiter_cmd = "awk '/Protection Domain/ {domain=$5} /SDS ID:/ {print($5\",\"domain)}'"
|
|
cmd = "%s && %s | %s" % [login_cmd, query_cmd, fiter_cmd]
|
|
debug_log(cmd)
|
|
result = Facter::Util::Resolution.exec(cmd)
|
|
if result
|
|
result = result.split(' ')
|
|
if result.count() > 0
|
|
result = result.join(',')
|
|
end
|
|
end
|
|
debug_log("%s='%s'" % ['scaleio_sds_with_protection_domain_list', result])
|
|
result
|
|
end
|
|
end
|
|
|
|
end
|
|
|
|
|
|
#The fact about MDM IPs.
|
|
#It requests them from Gateway.
|
|
$gw_ips = Facter.value(:gateway_ips)
|
|
$gw_passw = Facter.value(:gateway_password)
|
|
if $gw_passw && $gw_passw != '' and $gw_ips and $gw_ips != ''
|
|
Facter.add('scaleio_mdm_ips_from_gateway') do
|
|
setcode do
|
|
result = nil
|
|
if Facter.value('gateway_user')
|
|
gw_user = Facter.value('gateway_user')
|
|
else
|
|
gw_user = 'admin'
|
|
end
|
|
host = $gw_ips.split(',')[0]
|
|
if Facter.value('gateway_port')
|
|
port = Facter.value('gateway_port')
|
|
else
|
|
port = 4443
|
|
end
|
|
base_url = "https://%s:%s/api/%s"
|
|
login_url = base_url % [host, port, 'login']
|
|
config_url = base_url % [host, port, 'Configuration']
|
|
login_req = "curl -k --basic --connect-timeout 5 --user #{gw_user}:#{$gw_passw} #{login_url} 2>>%s | sed 's/\"//g'" % $scaleio_log_file
|
|
debug_log(login_req)
|
|
token = Facter::Util::Resolution.exec(login_req)
|
|
if token && token != ''
|
|
req_url = "curl -k --basic --connect-timeout 5 --user #{gw_user}:#{token} #{config_url} 2>>%s" % $scaleio_log_file
|
|
debug_log(req_url)
|
|
request_result = Facter::Util::Resolution.exec(req_url)
|
|
if request_result
|
|
config = JSON.parse(request_result)
|
|
if config and config['mdmAddresses']
|
|
result = config['mdmAddresses'].join(',')
|
|
end
|
|
end
|
|
end
|
|
debug_log("%s='%s'" % ['scaleio_mdm_ips_from_gateway', result])
|
|
result
|
|
end
|
|
end
|
|
end
|