* generate node network data section (deduplication);
* fix validation for quantum params; * update deploy and provision examples; * up version to 0.0.2
This commit is contained in:
parent
7aa7e9c15c
commit
e9c21e6282
|
@ -1,6 +1,6 @@
|
||||||
# Nodes
|
# Nodes
|
||||||
nodes:
|
nodes:
|
||||||
- name: controller-5
|
- name: controller-8
|
||||||
role: controller
|
role: controller
|
||||||
public_br: br-ex
|
public_br: br-ex
|
||||||
internal_br: br-mgmt
|
internal_br: br-mgmt
|
||||||
|
@ -8,42 +8,48 @@ nodes:
|
||||||
- name: eth2
|
- name: eth2
|
||||||
ip_address: 10.20.0.187
|
ip_address: 10.20.0.187
|
||||||
netmask: 255.255.255.0
|
netmask: 255.255.255.0
|
||||||
static: '0'
|
static: 0
|
||||||
mac_address: '08:00:27:31:09:34'
|
mac_address: '08:00:27:31:09:34'
|
||||||
onboot: 'no'
|
onboot: 'no'
|
||||||
peerdns: 'no'
|
peerdns: 'no'
|
||||||
|
network_name:
|
||||||
|
- fixed
|
||||||
- name: eth1
|
- name: eth1
|
||||||
ip_address: 10.20.0.186
|
ip_address: 10.20.0.186
|
||||||
netmask: 255.255.255.0
|
netmask: 255.255.255.0
|
||||||
static: '0'
|
static: 0
|
||||||
mac_address: 08:00:27:93:54:B0
|
mac_address: 08:00:27:93:54:B0
|
||||||
onboot: 'no'
|
onboot: 'no'
|
||||||
peerdns: 'no'
|
peerdns: 'no'
|
||||||
|
network_name:
|
||||||
|
- management
|
||||||
|
- storage
|
||||||
- name: eth0
|
- name: eth0
|
||||||
#ip_address: 10.20.0.49 # ip, power_address
|
#ip_address: 10.20.0.49 # ip, power_address
|
||||||
#netmask: 255.255.255.0
|
#netmask: 255.255.255.0
|
||||||
dns_name: controller-5.domain.tld # fqdn
|
dns_name: controller-8.domain.tld # fqdn
|
||||||
static: '0'
|
static: 0
|
||||||
mac_address: 08:00:27:53:0B:6C # mac
|
mac_address: 08:00:27:83:80:92 # mac
|
||||||
onboot: 'yes'
|
onboot: 'yes'
|
||||||
peerdns: 'no'
|
peerdns: 'no'
|
||||||
use_for_provision: true
|
use_for_provision: true
|
||||||
#End data for provision
|
network_name:
|
||||||
|
- public
|
||||||
default_gateway: 10.20.0.1
|
default_gateway: 10.20.0.1
|
||||||
network_data:
|
# network_data:
|
||||||
- name: public
|
# - name: public
|
||||||
ip: 172.18.94.41
|
# ip: 172.18.94.41
|
||||||
dev: eth1
|
# dev: eth1
|
||||||
netmask: 255.255.255.0
|
# netmask: 255.255.255.0
|
||||||
gateway: 172.18.94.33
|
# gateway: 172.18.94.33
|
||||||
- name:
|
# - name:
|
||||||
- management
|
# - management
|
||||||
- storage
|
# - storage
|
||||||
ip: 10.20.0.45
|
# ip: 10.20.0.45
|
||||||
dev: eth0
|
# dev: eth0
|
||||||
netmask: 255.255.255.0
|
# netmask: 255.255.255.0
|
||||||
- name: fixed
|
# - name: fixed
|
||||||
dev: eth2
|
# dev: eth2
|
||||||
|
|
||||||
attributes:
|
attributes:
|
||||||
master_ip: 10.20.0.2
|
master_ip: 10.20.0.2
|
||||||
|
@ -92,6 +98,7 @@ attributes:
|
||||||
password: cinder
|
password: cinder
|
||||||
user: cinder
|
user: cinder
|
||||||
floating_network_range: 10.20.0.150/28
|
floating_network_range: 10.20.0.150/28
|
||||||
|
#fixed_network_range: CIDR
|
||||||
fixed_network_range: 10.20.1.0/24
|
fixed_network_range: 10.20.1.0/24
|
||||||
base_syslog:
|
base_syslog:
|
||||||
syslog_port: '514'
|
syslog_port: '514'
|
||||||
|
|
|
@ -6,7 +6,6 @@ engine:
|
||||||
username: cobbler
|
username: cobbler
|
||||||
password: cobbler
|
password: cobbler
|
||||||
|
|
||||||
|
|
||||||
# These parameters can be overridden in the specification of a particular node
|
# These parameters can be overridden in the specification of a particular node
|
||||||
common_node_settings:
|
common_node_settings:
|
||||||
name_servers: "10.20.0.2"
|
name_servers: "10.20.0.2"
|
||||||
|
@ -37,8 +36,8 @@ common_ks_meta:
|
||||||
|
|
||||||
# Nodes
|
# Nodes
|
||||||
nodes:
|
nodes:
|
||||||
- name: controller-5
|
- name: controller-8
|
||||||
hostname: controller-5.domain.tld
|
hostname: controller-8.domain.tld
|
||||||
|
|
||||||
# Data for provision
|
# Data for provision
|
||||||
profile: centos-x86_64
|
profile: centos-x86_64
|
||||||
|
@ -95,23 +94,23 @@ nodes:
|
||||||
- name: eth2
|
- name: eth2
|
||||||
ip_address: 10.20.0.187
|
ip_address: 10.20.0.187
|
||||||
netmask: 255.255.255.0
|
netmask: 255.255.255.0
|
||||||
static: '0'
|
static: 0
|
||||||
mac_address: '08:00:27:31:09:34'
|
mac_address: '08:00:27:31:09:34'
|
||||||
onboot: 'no'
|
onboot: 'no'
|
||||||
peerdns: 'no'
|
peerdns: 'no'
|
||||||
- name: eth1
|
- name: eth1
|
||||||
ip_address: 10.20.0.186
|
ip_address: 10.20.0.186
|
||||||
netmask: 255.255.255.0
|
netmask: 255.255.255.0
|
||||||
static: '0'
|
static: 0
|
||||||
mac_address: 08:00:27:93:54:B0
|
mac_address: 08:00:27:93:54:B0
|
||||||
onboot: 'no'
|
onboot: 'no'
|
||||||
peerdns: 'no'
|
peerdns: 'no'
|
||||||
- name: eth0
|
- name: eth0
|
||||||
#ip_address: 10.20.0.49 # ip, power_address
|
#ip_address: 10.20.0.49 # ip, power_address
|
||||||
#netmask: 255.255.255.0
|
#netmask: 255.255.255.0
|
||||||
dns_name: controller-22.domain.tld # fqdn
|
dns_name: controller-8.domain.tld # fqdn
|
||||||
static: '0'
|
static: 1
|
||||||
mac_address: 08:00:27:53:0B:6C # mac
|
mac_address: 08:00:27:83:80:92 # mac
|
||||||
onboot: 'yes'
|
onboot: 'yes'
|
||||||
peerdns: 'no'
|
peerdns: 'no'
|
||||||
use_for_provision: true
|
use_for_provision: true
|
||||||
|
|
|
@ -26,6 +26,9 @@ mapping:
|
||||||
type: text
|
type: text
|
||||||
required: true
|
required: true
|
||||||
enum: ["primary-controller", "controller", "storage", "swift-proxy", "primary-swift-proxy", "compute", "quantum"]
|
enum: ["primary-controller", "controller", "storage", "swift-proxy", "primary-swift-proxy", "compute", "quantum"]
|
||||||
|
"status":
|
||||||
|
type: text
|
||||||
|
enum: ["ready", "provisioned", "discover"]
|
||||||
# Quantum true
|
# Quantum true
|
||||||
"public_br":
|
"public_br":
|
||||||
type: text
|
type: text
|
||||||
|
@ -34,10 +37,53 @@ mapping:
|
||||||
"internal_br":
|
"internal_br":
|
||||||
type: text
|
type: text
|
||||||
desc: Name of the internal bridge for Quantum-enabled configuration
|
desc: Name of the internal bridge for Quantum-enabled configuration
|
||||||
|
"interfaces":
|
||||||
|
type: seq
|
||||||
|
required: true
|
||||||
|
sequence:
|
||||||
|
- type: map
|
||||||
|
mapping:
|
||||||
|
"name":
|
||||||
|
type: text
|
||||||
|
required: true
|
||||||
|
unique: yes
|
||||||
|
"ip_address":
|
||||||
|
type: text
|
||||||
|
unique: yes
|
||||||
|
"netmask":
|
||||||
|
type: text
|
||||||
|
"dns_name":
|
||||||
|
type: text
|
||||||
|
unique: yes
|
||||||
|
"static":
|
||||||
|
type: int
|
||||||
|
range: { min: 0, max: 1 }
|
||||||
|
"mac_address":
|
||||||
|
type: text
|
||||||
|
required: true
|
||||||
|
unique: yes
|
||||||
|
"onboot":
|
||||||
|
type: text
|
||||||
|
required: true
|
||||||
|
enum: ['yes', 'no']
|
||||||
|
"peerdns":
|
||||||
|
type: text
|
||||||
|
required: true
|
||||||
|
enum: ['yes', 'no']
|
||||||
|
"use_for_provision":
|
||||||
|
type: bool
|
||||||
|
default: false
|
||||||
|
name: use_for_provision
|
||||||
|
"network_name":
|
||||||
|
type: seq
|
||||||
|
desc: Array of OpenStack network names
|
||||||
|
sequence:
|
||||||
|
- type: text
|
||||||
|
enum: ["public", "management", "storage", "fixed"]
|
||||||
|
# Full config block
|
||||||
"network_data":
|
"network_data":
|
||||||
type: seq
|
type: seq
|
||||||
desc: Array of network interfaces hashes
|
desc: Array of network interfaces hashes
|
||||||
required: true
|
|
||||||
sequence:
|
sequence:
|
||||||
- type: map
|
- type: map
|
||||||
mapping:
|
mapping:
|
||||||
|
|
|
@ -34,6 +34,9 @@ module Astute
|
||||||
PROVISION_OPERATIONS = [:provision, :provision_and_deploy]
|
PROVISION_OPERATIONS = [:provision, :provision_and_deploy]
|
||||||
DEPLOY_OPERATIONS = [:deploy, :provision_and_deploy]
|
DEPLOY_OPERATIONS = [:deploy, :provision_and_deploy]
|
||||||
|
|
||||||
|
CIDR_REGEXP = '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|
|
||||||
|
2[0-4][0-9]|25[0-5])(\/(\d|[1-2]\d|3[0-2]))$'
|
||||||
|
|
||||||
def initialize(file, operation)
|
def initialize(file, operation)
|
||||||
@config = YAML.load_file(file)
|
@config = YAML.load_file(file)
|
||||||
validate_enviroment(operation)
|
validate_enviroment(operation)
|
||||||
|
@ -68,25 +71,29 @@ module Astute
|
||||||
if DEPLOY_OPERATIONS.include? operation
|
if DEPLOY_OPERATIONS.include? operation
|
||||||
define_meta_interfaces(node)
|
define_meta_interfaces(node)
|
||||||
define_fqdn(node)
|
define_fqdn(node)
|
||||||
|
define_network_data(node)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
def validate_enviroment(operation)
|
def validate_enviroment(operation)
|
||||||
validator = YamlValidator.new(operation)
|
validator = YamlValidator.new(operation)
|
||||||
errors = validator.validate(@config)
|
errors = validator.validate(@config)
|
||||||
|
|
||||||
errors.each do |e|
|
errors.each do |e|
|
||||||
title = e.message.include?("is undefined") ? "WARNING" : "ERROR"
|
if e.message.include?("is undefined")
|
||||||
puts "#{title}: [#{e.path}] #{e.message}"
|
Astute.logger.debug "WARNING: [#{e.path}] #{e.message}"
|
||||||
|
else
|
||||||
|
Astute.logger.error "ERROR: [#{e.path}] #{e.message}"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if errors.select {|e| !e.message.include?("is undefined") }.size > 0
|
if errors.select {|e| !e.message.include?("is undefined") }.size > 0
|
||||||
raise Enviroment::ValidationError, "Environment validation failed"
|
raise Enviroment::ValidationError, "Environment validation failed"
|
||||||
end
|
end
|
||||||
|
|
||||||
if PROVISION_OPERATIONS.include? operation && @config['attributes']['quantum']
|
if DEPLOY_OPERATIONS.include?(operation)
|
||||||
|
if @config['attributes']['quantum']
|
||||||
@config['nodes'].each do |node|
|
@config['nodes'].each do |node|
|
||||||
['public_br', 'internal_br'].each do |br|
|
['public_br', 'internal_br'].each do |br|
|
||||||
if node[br].nil? || node[br].empty?
|
if node[br].nil? || node[br].empty?
|
||||||
|
@ -95,6 +102,35 @@ module Astute
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
errors = []
|
||||||
|
['quantum_parameters', 'quantum_access'].each do |param|
|
||||||
|
errors << param unless @config['attributes'].present?(param)
|
||||||
|
end
|
||||||
|
errors.each do |field|
|
||||||
|
msg = "#{field} is required when quantim is true"
|
||||||
|
raise Enviroment::ValidationError, msg
|
||||||
|
end
|
||||||
|
|
||||||
|
if !is_cidr_notation?(@config['attributes']['floating_network_range'])
|
||||||
|
msg = "'floating_network_range' is required CIDR notation when quantum is 'true'"
|
||||||
|
raise Enviroment::ValidationError, msg
|
||||||
|
end
|
||||||
|
|
||||||
|
if !is_cidr_notation?(@config['attributes']['floating_network_range'])
|
||||||
|
msg = "'floating_network_range' is required CIDR notation"
|
||||||
|
raise Enviroment::ValidationError, msg
|
||||||
|
end
|
||||||
|
else
|
||||||
|
if @config['attributes']['floating_network_range'].is_a?(Array)
|
||||||
|
msg = "'floating_network_range' is required array of IPs when quantum is 'false'"
|
||||||
|
raise Enviroment::ValidationError, msg
|
||||||
|
end
|
||||||
|
end
|
||||||
|
if !is_cidr_notation?(@config['attributes']['fixed_network_range'])
|
||||||
|
msg = "'fixed_network_range' is required CIDR notation"
|
||||||
|
raise Enviroment::ValidationError, msg
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -105,8 +141,8 @@ module Astute
|
||||||
@api_data = JSON.parse(response).freeze
|
@api_data = JSON.parse(response).freeze
|
||||||
end
|
end
|
||||||
if node['mac']
|
if node['mac']
|
||||||
node = @api_data.find{ |n| n['mac'].upcase == node['mac'].upcase }
|
api_node = @api_data.find{ |n| n['mac'].upcase == node['mac'].upcase }
|
||||||
return node if node
|
return api_node if api_node
|
||||||
end
|
end
|
||||||
raise Enviroment::ValidationError, "Node #{node['name']} with mac address #{node['mac']}
|
raise Enviroment::ValidationError, "Node #{node['name']} with mac address #{node['mac']}
|
||||||
not find among discovered nodes"
|
not find among discovered nodes"
|
||||||
|
@ -250,6 +286,44 @@ module Astute
|
||||||
node['meta']['interfaces'] = find_node_api_data(node)['meta']['interfaces']
|
node['meta']['interfaces'] = find_node_api_data(node)['meta']['interfaces']
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# Add network_data section for node:
|
||||||
|
# network_data:
|
||||||
|
# - dev: eth1
|
||||||
|
# ip: 10.108.1.8
|
||||||
|
# name: public
|
||||||
|
# netmask: 255.255.255.0
|
||||||
|
# - dev: eth0
|
||||||
|
# ip: 10.108.0.8
|
||||||
|
# name:
|
||||||
|
# - management
|
||||||
|
# - storage
|
||||||
|
def define_network_data(node)
|
||||||
|
return if node['network_data'].is_a?(Array) && !node['network_data'].empty?
|
||||||
|
|
||||||
|
node['network_data'] = []
|
||||||
|
|
||||||
|
# If define_interfaces_and_interfaces_extra was call or format of config is full
|
||||||
|
if node['interfaces'].is_a?(Hash)
|
||||||
|
node['interfaces'].each do |key, value|
|
||||||
|
node['network_data'] << {
|
||||||
|
'dev' => key,
|
||||||
|
'ip' => value['ip_address'],
|
||||||
|
'name' => value['network_name'],
|
||||||
|
'netmask' => value['netmask']
|
||||||
|
}
|
||||||
|
end
|
||||||
|
else
|
||||||
|
node['interfaces'].each do |eth|
|
||||||
|
node['network_data'] << {
|
||||||
|
'dev' => eth['name'],
|
||||||
|
'ip' => eth['ip_address'],
|
||||||
|
'name' => eth['network_name'],
|
||||||
|
'netmask' => eth['netmask']
|
||||||
|
}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
# Generate 'ks_spaces' param from 'ks_disks' param in section 'ks_meta'
|
# Generate 'ks_spaces' param from 'ks_disks' param in section 'ks_meta'
|
||||||
# Example input for 'ks_disks' param:
|
# Example input for 'ks_disks' param:
|
||||||
# [{
|
# [{
|
||||||
|
@ -283,6 +357,12 @@ module Astute
|
||||||
node['ks_meta']['ks_spaces'] = '"' + node['ks_meta']['ks_disks'].to_json.gsub("\"", "\\\"") + '"'
|
node['ks_meta']['ks_spaces'] = '"' + node['ks_meta']['ks_disks'].to_json.gsub("\"", "\\\"") + '"'
|
||||||
node['ks_meta'].delete('ks_disks')
|
node['ks_meta'].delete('ks_disks')
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def is_cidr_notation?(value)
|
||||||
|
cidr = Regexp.new(CIDR_REGEXP)
|
||||||
|
!cidr.match(value).nil?
|
||||||
|
end
|
||||||
|
|
||||||
end # class end
|
end # class end
|
||||||
|
|
||||||
class Enviroment::ValidationError < StandardError; end
|
class Enviroment::ValidationError < StandardError; end
|
||||||
|
|
|
@ -141,9 +141,9 @@ mapping:
|
||||||
type: text
|
type: text
|
||||||
desc: Password/credentials for cobbler to manage power of this machine
|
desc: Password/credentials for cobbler to manage power of this machine
|
||||||
"netboot_enabled":
|
"netboot_enabled":
|
||||||
type: text
|
type: int
|
||||||
|
range: { min: 0, max: 1 }
|
||||||
desc: Disable/enable netboot for this node.
|
desc: Disable/enable netboot for this node.
|
||||||
enum: ['0', '1']
|
|
||||||
"ks_meta":
|
"ks_meta":
|
||||||
type: map
|
type: map
|
||||||
required: true
|
required: true
|
||||||
|
@ -240,8 +240,8 @@ mapping:
|
||||||
type: text
|
type: text
|
||||||
unique: yes
|
unique: yes
|
||||||
"static":
|
"static":
|
||||||
type: text
|
type: int
|
||||||
#range: { min: 0, max: 1 }
|
range: { min: 0, max: 1 }
|
||||||
"mac_address":
|
"mac_address":
|
||||||
type: text
|
type: text
|
||||||
required: true
|
required: true
|
||||||
|
|
|
@ -14,9 +14,6 @@
|
||||||
|
|
||||||
require 'kwalify'
|
require 'kwalify'
|
||||||
|
|
||||||
CIDR_REGEXP = '^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|
|
|
||||||
2[0-4][0-9]|25[0-5])(\/(\d|[1-2]\d|3[0-2]))$'
|
|
||||||
|
|
||||||
module Astute
|
module Astute
|
||||||
module Cli
|
module Cli
|
||||||
class YamlValidator < Kwalify::Validator
|
class YamlValidator < Kwalify::Validator
|
||||||
|
@ -32,59 +29,18 @@ module Astute
|
||||||
|
|
||||||
schema_hashes = []
|
schema_hashes = []
|
||||||
schema_dir_path = File.expand_path(File.dirname(__FILE__))
|
schema_dir_path = File.expand_path(File.dirname(__FILE__))
|
||||||
|
|
||||||
schemas.each do |schema_name|
|
schemas.each do |schema_name|
|
||||||
schema_path = File.join(schema_dir_path, "#{schema_name}_schema.yaml")
|
schema_path = File.join(schema_dir_path, "#{schema_name}_schema.yaml")
|
||||||
schema_hashes << YAML.load_file(schema_path)
|
schema_hashes << YAML.load_file(schema_path)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
#p schema_hashes[0].recursive_merge!(schema_hashes[1])
|
||||||
#FIXME: key 'hostname:' is undefined for provision_and_deploy. Why?
|
#FIXME: key 'hostname:' is undefined for provision_and_deploy. Why?
|
||||||
@schema = schema_hashes.size == 1 ? schema_hashes.first : schema_hashes[0].deep_merge(schema_hashes[1])
|
@schema = schema_hashes.size == 1 ? schema_hashes.first : schema_hashes[0].deep_merge(schema_hashes[1])
|
||||||
super(@schema)
|
super(@schema)
|
||||||
end
|
end
|
||||||
|
|
||||||
# hook method called by Validator#validate()
|
|
||||||
def validate_hook(value, rule, path, errors)
|
|
||||||
case rule.name
|
|
||||||
when 'Attributes'
|
|
||||||
require_field(value, path, errors, 'quantum', true, 'quantum_parameters')
|
|
||||||
require_field(value, path, errors, 'quantum', true, 'fixed_network_range')
|
|
||||||
require_field(value, path, errors, 'quantum', true, 'quantum_access')
|
|
||||||
#require_field(value, path, errors, 'quantum', false, 'floating_network_range')
|
|
||||||
if value['quantum']
|
|
||||||
is_cidr_notation?(value['floating_network_range'])
|
|
||||||
msg = "'floating_network_range' is required CIDR notation when quantum is 'true'"
|
|
||||||
errors << Kwalify::ValidationError.new(msg, path)
|
|
||||||
elsif !floating_network_range.is_a?(Array)
|
|
||||||
msg = "'floating_network_range' is required array of IPs when quantum is 'false'"
|
|
||||||
errors << Kwalify::ValidationError.new(msg, path)
|
|
||||||
end
|
|
||||||
if !is_cidr_notation?(value['fixed_network_range'])
|
|
||||||
msg = "'floating_network_range' is required CIDR notation"
|
|
||||||
errors << Kwalify::ValidationError.new(msg, path)
|
|
||||||
end
|
|
||||||
|
|
||||||
when 'Nodes'
|
|
||||||
#require_field(value, path, errors, 'quantum', true, 'public_br')
|
|
||||||
#require_field(value, path, errors, 'quantum', true, 'internal_br')
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
private
|
|
||||||
|
|
||||||
def is_cidr_notation?(value)
|
|
||||||
cidr = Regexp.new(CIDR_REGEXP)
|
|
||||||
!cidr.match(value).nil?
|
|
||||||
end
|
|
||||||
|
|
||||||
def require_field(value, path, errors, condition_key, condition_value, key)
|
|
||||||
return if value[condition_key] != condition_value
|
|
||||||
field_value = value[key]
|
|
||||||
if field_value.nil? || field_value.empty?
|
|
||||||
msg = "#{key} is required when #{condition_key} is '#{condition_value}'"
|
|
||||||
errors << Kwalify::ValidationError.new(msg, path)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
end # YamlValidator
|
end # YamlValidator
|
||||||
end # Cli
|
end # Cli
|
||||||
end # Astute
|
end # Astute
|
|
@ -31,7 +31,7 @@ module Astute
|
||||||
attrs['use_cinder'] ||= nodes.any?{|n| n['role'] == 'cinder'}
|
attrs['use_cinder'] ||= nodes.any?{|n| n['role'] == 'cinder'}
|
||||||
@ctx.deploy_log_parser.deploy_type = attrs['deployment_mode']
|
@ctx.deploy_log_parser.deploy_type = attrs['deployment_mode']
|
||||||
Astute.logger.info "Deployment mode #{attrs['deployment_mode']}"
|
Astute.logger.info "Deployment mode #{attrs['deployment_mode']}"
|
||||||
result = self.send("deploy_#{attrs['deployment_mode']}", nodes, attrs)
|
self.send("deploy_#{attrs['deployment_mode']}", nodes, attrs)
|
||||||
end
|
end
|
||||||
|
|
||||||
def method_missing(method, *args)
|
def method_missing(method, *args)
|
||||||
|
|
|
@ -36,6 +36,19 @@ class Hash
|
||||||
!absent?(key)
|
!absent?(key)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# def recursive_merge!(other)
|
||||||
|
# other.keys.each do |k|
|
||||||
|
# if self[k].is_a?(Array) && other[k].is_a?(Array)
|
||||||
|
# self[k] += other[k]
|
||||||
|
# elsif self[k].is_a?(Hash) && other[k].is_a?(Hash)
|
||||||
|
# self[k].recursive_merge!(other[k])
|
||||||
|
# else
|
||||||
|
# self[k] = other[k]
|
||||||
|
# end
|
||||||
|
# end
|
||||||
|
# self
|
||||||
|
# end
|
||||||
|
|
||||||
def deep_merge(other_hash)
|
def deep_merge(other_hash)
|
||||||
self.merge(other_hash) do |key, oldval, newval|
|
self.merge(other_hash) do |key, oldval, newval|
|
||||||
oldval = oldval.to_hash if oldval.respond_to?(:to_hash)
|
oldval = oldval.to_hash if oldval.respond_to?(:to_hash)
|
||||||
|
|
|
@ -14,5 +14,5 @@
|
||||||
|
|
||||||
|
|
||||||
module Astute
|
module Astute
|
||||||
VERSION = '0.0.1'
|
VERSION = '0.0.2'
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in New Issue