Skip to content

Commit

Permalink
Merge pull request ManageIQ#56 from billfitzgerald0120/quota_reconfig
Browse files Browse the repository at this point in the history
Add quota checking for VMReconfigure tests.
  • Loading branch information
mkanoor authored May 4, 2017
2 parents b92d4a4 + 4ff65f9 commit 321e043
Show file tree
Hide file tree
Showing 5 changed files with 154 additions and 21 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,10 @@ def service_prov_option(prov_option, options_array = [])
options_array
end

def vendor
@reconfigure_request ? @vm.vendor : @miq_request.source.vendor
end

def service_prov_option_value(prov_option, resource, options_array = [])
args_hash = {:prov_option => prov_option,
:options_array => options_array,
Expand Down Expand Up @@ -86,10 +90,12 @@ def vm_prov_option_value(prov_option, options_array = [])
:flavor => flavor_obj(@miq_request.get_option(:instance_type)),
:number_of_vms => get_option_value(@miq_request, :number_of_vms),
:cloud => vm_provision_cloud?}
# number_of_vms doesn't exist for VmReconfigureRequest
args_hash[:number_of_vms] = 1 if @reconfigure_request

case prov_option
when :vm_memory
requested_memory(args_hash, @miq_request.source.vendor)
requested_memory(args_hash, vendor)
when :number_of_cpus
requested_number_of_cpus(args_hash)
when :storage
Expand All @@ -104,6 +110,15 @@ def requested_memory(args_hash, vendor)
memory = get_option_value(args_hash[:resource], :vm_memory)
memory = memory.megabytes if %w(amazon openstack google).exclude?(vendor)
args_hash[:prov_value] = args_hash[:number_of_vms] * memory

if @reconfigure_request && args_hash[:resource].options[:vm_memory]
# Account for the VM's existing memory
args_hash[:prov_value] = args_hash[:prov_value].to_i - @vm.hardware.memory_mb.to_i.megabytes

$evm.log(:info, "vm_memory: #{@vm.hardware.memory_mb.to_i.megabytes}")
$evm.log(:info, "requested_memory: #{args_hash[:prov_value].to_i}")
@check_quota = true if args_hash[:prov_value].to_i > 0
end
request_hash_value(args_hash)
end

Expand All @@ -112,6 +127,17 @@ def requested_number_of_cpus(args_hash)
get_option_value(args_hash[:resource], :cores_per_socket)
cpu_in_request = get_option_value(args_hash[:resource], args_hash[:number_of_cpus]) if cpu_in_request.zero?
args_hash[:prov_value] = args_hash[:number_of_vms] * cpu_in_request

if @reconfigure_request && args_hash[:resource].options[:number_of_sockets]
# Account for the VM's existing CPUs
args_hash[:prov_value] = args_hash[:prov_value].to_i - @vm.hardware.cpu_total_cores.to_i \
* @vm.hardware.cpu_cores_per_socket.to_i

$evm.log(:info, "vm_number_of_cpus: #{@vm.hardware.cpu_total_cores.to_i \
* @vm.hardware.cpu_cores_per_socket.to_i}")
$evm.log(:info, "requested_number_of_cpus: #{args_hash[:prov_value].to_i}")
@check_quota = true if args_hash[:prov_value].to_i > 0
end
request_hash_value(args_hash)
end

Expand All @@ -120,8 +146,36 @@ def vmdb_object(model, id)
end

def requested_storage(args_hash)
vm_size = args_hash[:resource].vm_template.provisioned_storage
args_hash[:prov_value] = args_hash[:number_of_vms] * vm_size
if @reconfigure_request
args_hash[:prov_value] = 0
# Adding/removing disks only supported for VMware
if args_hash[:resource].options[:disk_add]
args_hash[:resource].options[:disk_add].each do |disk|
$evm.log(:info, "Adding a disk: #{disk.inspect}")
args_hash[:prov_value] += disk['disk_size_in_mb'].to_i.megabytes
end
end
if args_hash[:resource].options[:disk_remove]
args_hash[:resource].options[:disk_remove].each do |disk|
disk_num = disk[:disk_name].match(/_(\d).vmdk/)
next unless disk_num
$evm.log(:info, "Reconfigure Disk Removal: #{disk.inspect}")
disk_n_number = "disk_#{disk_num[1].succ}_size"
disk_n_size = @vm.send(disk_n_number.to_s)
next unless disk_n_size
$evm.log(:info, "Disk size: #{disk_n_size.to_s(:human_size)}")
args_hash[:prov_value] -= disk_n_size.to_i
end
end
else
vm_size = args_hash[:resource].vm_template.provisioned_storage
args_hash[:prov_value] = args_hash[:number_of_vms] * vm_size
end

if @reconfigure_request
$evm.log(:info, "VM Reconfigure storage change: #{args_hash[:prov_value].to_s(:human_size)}")
@check_quota = true if args_hash[:prov_value].to_i > 0
end
request_hash_value(args_hash)
end

Expand Down Expand Up @@ -265,4 +319,14 @@ def error(type)
exit MIQ_OK
end

@reconfigure_request = @miq_request.type == "VmReconfigureRequest"
if @reconfigure_request
@check_quota = false # default, unless additional quota is requested
vm_id = @miq_request.options[:src_ids]
@vm = $evm.vmdb(:vm).find_by(:id => vm_id)
raise "VM not found" if @vm.nil?
end

$evm.root['quota_requested'] = calculate_requested(options_hash)

$evm.root['check_quota'] = @check_quota unless @check_quota.nil?
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,14 @@ def error(type)
exit MIQ_OK
end

unless $evm.root['check_quota'].nil?
if $evm.root['check_quota'] == false
$evm.log(:info, "VmReconfigureRequest: Bypassing quota check.")
$evm.root['ae_result'] = 'ok'
exit MIQ_OK
end
end

check_quotas

check_quota_results
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
---
object_type: instance
version: 1.0
object:
attributes:
display_name:
name: VmReconfigureRequest_starting
inherits:
description:
fields:
- rel2:
value: "/System/CommonMethods/QuotaStatemachine/quota"
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,15 @@ def vm_attrs
end

def service_attrs
["MiqRequest::miq_request=#{@service_request.id}&" \
["MiqRequest::miq_request=#{@service_request.id}&"\
"vmdb_object_type=service_template_provision_request"]
end

def reconfigure_attrs
["MiqRequest::miq_request=#{@reconfigure_request.id}&"\
"vmdb_object_type=VmReconfigureRequest"]
end

def check_results(requested_hash, storage, cpu, vms, memory)
expect(requested_hash[:storage]).to eq(storage)
expect(requested_hash[:cpu]).to eq(cpu)
Expand Down Expand Up @@ -70,4 +75,32 @@ def check_results(requested_hash, storage, cpu, vms, memory)
check_results(ws.root['quota_requested'], 10.gigabytes, 4, 1, 1024)
end
end

context "VmReconfig quota calculate_request" do
it "add 2 cpus and add 4096 memory " do
setup_model("vmware_reconfigure")
@reconfigure_request.update_attributes(:options => {:src_ids => [@vm_vmware.id], :cores_per_socket => 2,\
:number_of_sockets => 2, :number_of_cpus => 4, :vm_memory => 8192, :request_type => :vm_reconfigure,\
:disk_add => [{"disk_size_in_mb" => "10", "persistent" => true, "thin_provisioned" => true,\
"dependent" => true, "bootable" => false}]})
ws = run_automate_method(reconfigure_attrs)
check_results(ws.root['quota_requested'], 10.megabytes, 2, 0, 4096.megabytes)
end

it "minus 1 cpu and minus 2048 memory" do
setup_model("vmware_reconfigure")
@reconfigure_request.update_attributes(:options => {:src_ids => [@vm_vmware.id], :cores_per_socket => 1,\
:number_of_sockets => 1, :number_of_cpus => 1, :vm_memory => 2048, :request_type => :vm_reconfigure})
ws = run_automate_method(reconfigure_attrs)
check_results(ws.root['quota_requested'], 0, -1, 0, -2048.megabytes)
end

it "no change" do
setup_model("vmware_reconfigure")
@reconfigure_request.update_attributes(:options => {:src_ids => [@vm_vmware.id], :cores_per_socket => 2,\
:number_of_sockets => 1, :number_of_cpus => 2, :vm_memory => 4096, :request_type => :vm_reconfigure})
ws = run_automate_method(reconfigure_attrs)
check_results(ws.root['quota_requested'], 0, 0, 0, 0.megabytes)
end
end
end
50 changes: 33 additions & 17 deletions spec/automation/unit/method_validation/validate_quota_spec.rb
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
describe "Quota Validation" do
include Spec::Support::QuotaHelper

def run_automate_method(provision_request)
def run_automate_method
@quota_used = YAML.dump(:storage => 32_768, :vms => 2, :cpu => 2, :memory => 4096)
@quota_requested = YAML.dump(:storage => 10_240, :vms => 1, :cpu => 1, :memory => 1024)
attrs = []
Expand All @@ -11,7 +11,8 @@ def run_automate_method(provision_request)
"quota_limit_warn_yaml=#{@quota_limit_warn}&" \
"quota_used_yaml=#{@quota_used}&" \
"Tenant::quota_source=#{@tenant.id}&" \
"quota_requested_yaml=#{@quota_requested}" if provision_request
"quota_requested_yaml=#{@quota_requested}"
attrs << @extra_attrs if @extra_attrs
MiqAeEngine.instantiate("/ManageIQ/system/request/Call_Instance?namespace=System/CommonMethods&" \
"class=QuotaMethods&instance=validate_quota&#{attrs.join('&')}", @user)
end
Expand All @@ -24,7 +25,7 @@ def run_automate_method(provision_request)
it "no quota limits set" do
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eq('ok')
end
end
Expand All @@ -35,7 +36,7 @@ def run_automate_method(provision_request)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds maximum allowed for the following:" \
" (memory - Used: 4 KB plus requested: 1 KB exceeds quota: 4 KB) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('error')
@miq_request.reload
expect(@miq_request.options[:quota_max_exceeded]).to eql(err_msg)
Expand All @@ -47,7 +48,7 @@ def run_automate_method(provision_request)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds warning limits for the following:" \
" (memory - Used: 4 KB plus requested: 1 KB exceeds quota: 4 KB) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('ok')
@miq_request.reload
expect(@miq_request.options[:quota_warn_exceeded]).to eql(err_msg)
Expand All @@ -59,19 +60,19 @@ def run_automate_method(provision_request)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds maximum allowed for the following:" \
" (vms - Used: 2 plus requested: 1 exceeds quota: 2) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('error')
@miq_request.reload
expect(@miq_request.options[:quota_max_exceeded]).to eql(err_msg)
expect(@miq_request.message).to eql(err_msg)
end

it "failure warn vms" do
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 1, :cpu => 0, :memory => 0)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 1, :cpu => 0, :memory => 0)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds warning limits for the following:" \
" (vms - Used: 2 plus requested: 1 exceeds quota: 1) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('ok')
@miq_request.reload
expect(@miq_request.options[:quota_warn_exceeded]).to eql(err_msg)
Expand All @@ -83,19 +84,19 @@ def run_automate_method(provision_request)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds maximum allowed for the following:" \
" (cpu - Used: 2 plus requested: 1 exceeds quota: 2) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('error')
@miq_request.reload
expect(@miq_request.options[:quota_max_exceeded]).to eql(err_msg)
expect(@miq_request.message).to eql(err_msg)
end

it "failure warn cpu" do
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 1, :memory => 0)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 1, :memory => 0)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds warning limits for the following:" \
" (cpu - Used: 2 plus requested: 1 exceeds quota: 1) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('ok')
@miq_request.reload
expect(@miq_request.options[:quota_warn_exceeded]).to eql(err_msg)
Expand All @@ -107,23 +108,38 @@ def run_automate_method(provision_request)
@quota_limit_warn = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds maximum allowed for the following:" \
" (storage - Used: 32 KB plus requested: 10 KB exceeds quota: 20 KB) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('error')
@miq_request.reload
expect(@miq_request.options[:quota_max_exceeded]).to eql(err_msg)
expect(@miq_request.message).to eql(err_msg)
end

it "failure warn storage" do
@quota_limit_warn = YAML.dump(:storage => 10_240, :vms => 0, :cpu => 0, :memory => 0)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
@quota_limit_warn = YAML.dump(:storage => 10_240, :vms => 0, :cpu => 0, :memory => 0)
@quota_limit_max = YAML.dump(:storage => 0, :vms => 0, :cpu => 0, :memory => 0)
err_msg = "Request exceeds warning limits for the following:" \
" (storage - Used: 32 KB plus requested: 10 KB exceeds quota: 10 KB) "
ws = run_automate_method(@miq_provision_request)
ws = run_automate_method
expect(ws.root['ae_result']).to eql('ok')
@miq_request.reload
expect(@miq_request.options[:quota_warn_exceeded]).to eql(err_msg)
expect(@miq_request.message).to eql(err_msg)
end
end

context "check_quota for VMReconfigure" do
it "check_quota false " do
ws = run_automate_method
expect(ws.root['ae_result']).to eq('ok')
expect(ws.root['check_quota']).to be_nil
end

it "check_quota true " do
@extra_attrs = "check_quota=true"
ws = run_automate_method
expect(ws.root['ae_result']).to eq('ok')
expect(ws.root['check_quota']).to eq('true')
end
end
end

0 comments on commit 321e043

Please sign in to comment.