morpheus-cli 5.3.2 → 5.3.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Dockerfile +1 -1
- data/lib/morpheus/api/accounts_interface.rb +4 -30
- data/lib/morpheus/api/api_client.rb +12 -0
- data/lib/morpheus/api/instances_interface.rb +18 -5
- data/lib/morpheus/api/load_balancer_pools_interface.rb +9 -0
- data/lib/morpheus/api/load_balancer_types_interface.rb +9 -0
- data/lib/morpheus/api/load_balancer_virtual_servers_interface.rb +9 -0
- data/lib/morpheus/api/load_balancers_interface.rb +4 -53
- data/lib/morpheus/api/network_routers_interface.rb +56 -0
- data/lib/morpheus/api/secondary_read_interface.rb +25 -0
- data/lib/morpheus/api/secondary_rest_interface.rb +42 -0
- data/lib/morpheus/api/virtual_images_interface.rb +23 -2
- data/lib/morpheus/cli/apps.rb +3 -2
- data/lib/morpheus/cli/cli_command.rb +21 -14
- data/lib/morpheus/cli/cli_registry.rb +55 -2
- data/lib/morpheus/cli/cloud_resource_pools_command.rb +169 -133
- data/lib/morpheus/cli/clusters.rb +51 -33
- data/lib/morpheus/cli/instances.rb +292 -174
- data/lib/morpheus/cli/invoices_command.rb +79 -99
- data/lib/morpheus/cli/library_cluster_layouts_command.rb +20 -0
- data/lib/morpheus/cli/load_balancer_types.rb +37 -0
- data/lib/morpheus/cli/load_balancers.rb +149 -314
- data/lib/morpheus/cli/log_settings_command.rb +7 -3
- data/lib/morpheus/cli/mixins/load_balancers_helper.rb +156 -0
- data/lib/morpheus/cli/mixins/print_helper.rb +11 -0
- data/lib/morpheus/cli/mixins/provisioning_helper.rb +123 -101
- data/lib/morpheus/cli/mixins/rest_command.rb +657 -0
- data/lib/morpheus/cli/monitoring_checks_command.rb +2 -0
- data/lib/morpheus/cli/network_routers_command.rb +1183 -185
- data/lib/morpheus/cli/networks_command.rb +194 -101
- data/lib/morpheus/cli/option_parser.rb +25 -17
- data/lib/morpheus/cli/option_types.rb +42 -45
- data/lib/morpheus/cli/tenants_command.rb +18 -20
- data/lib/morpheus/cli/vdi_pools_command.rb +4 -1
- data/lib/morpheus/cli/version.rb +1 -1
- data/lib/morpheus/cli/virtual_images.rb +249 -29
- data/lib/morpheus/cli.rb +1 -0
- data/lib/morpheus/ext/string.rb +41 -0
- data/lib/morpheus/formatters.rb +4 -0
- data/morpheus-cli.gemspec +1 -1
- metadata +13 -4
@@ -6,11 +6,12 @@ class Morpheus::Cli::LogSettingsCommand
|
|
6
6
|
|
7
7
|
set_command_name :'log-settings'
|
8
8
|
|
9
|
-
register_subcommands :get, :update
|
10
|
-
register_subcommands :enable_integration, :disable_integration, :remove_integration
|
9
|
+
register_subcommands :get, :update
|
11
10
|
register_subcommands :add_syslog_rule, :remove_syslog_rule
|
12
11
|
|
13
|
-
|
12
|
+
# these command are deprecated in 5.3.3 and can be removed
|
13
|
+
register_subcommands :enable_integration, :disable_integration, :remove_integration
|
14
|
+
set_subcommands_hidden :enable_integration, :disable_integration, :remove_integration
|
14
15
|
|
15
16
|
def connect(opts)
|
16
17
|
@api_client = establish_remote_appliance_connection(opts)
|
@@ -186,6 +187,7 @@ class Morpheus::Cli::LogSettingsCommand
|
|
186
187
|
end
|
187
188
|
|
188
189
|
def enable_integration(args)
|
190
|
+
print_error yellow,"[DEPRECATED] The command `#{command_name} enable-integration` is deprecated.",reset,"\n"
|
189
191
|
options = {}
|
190
192
|
|
191
193
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
@@ -240,6 +242,7 @@ class Morpheus::Cli::LogSettingsCommand
|
|
240
242
|
end
|
241
243
|
|
242
244
|
def disable_integration(args)
|
245
|
+
print_error yellow,"[DEPRECATED] The command `#{command_name} disable-integration` is deprecated.",reset,"\n"
|
243
246
|
options = {}
|
244
247
|
|
245
248
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
@@ -285,6 +288,7 @@ class Morpheus::Cli::LogSettingsCommand
|
|
285
288
|
end
|
286
289
|
|
287
290
|
def remove_integration(args)
|
291
|
+
print_error yellow,"[DEPRECATED] The command `#{command_name } remove-integration` is deprecated.",reset,"\n"
|
288
292
|
options = {}
|
289
293
|
|
290
294
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
@@ -0,0 +1,156 @@
|
|
1
|
+
require 'morpheus/cli/mixins/print_helper'
|
2
|
+
require 'morpheus/cli/option_types'
|
3
|
+
require 'morpheus/rest_client'
|
4
|
+
# Mixin for Morpheus::Cli command classes
|
5
|
+
# Provides common methods for load balancer management
|
6
|
+
# including load balancers, load balancer types, virtual servers, etc.
|
7
|
+
module Morpheus::Cli::LoadBalancersHelper
|
8
|
+
|
9
|
+
def self.included(klass)
|
10
|
+
klass.send :include, Morpheus::Cli::PrintHelper
|
11
|
+
end
|
12
|
+
|
13
|
+
def load_balancers_interface
|
14
|
+
# @api_client.load_balancers
|
15
|
+
raise "#{self.class} has not defined @load_balancers_interface" if @load_balancers_interface.nil?
|
16
|
+
@load_balancers_interface
|
17
|
+
end
|
18
|
+
|
19
|
+
def load_balancer_types_interface
|
20
|
+
# @api_client.load_balancer_types
|
21
|
+
raise "#{self.class} has not defined @load_balancer_types_interface" if @load_balancer_types_interface.nil?
|
22
|
+
@load_balancer_types_interface
|
23
|
+
end
|
24
|
+
|
25
|
+
def load_balancer_object_key
|
26
|
+
'loadBalancer'
|
27
|
+
end
|
28
|
+
|
29
|
+
def load_balancer_list_key
|
30
|
+
'loadBalancers'
|
31
|
+
end
|
32
|
+
|
33
|
+
def load_balancer_label
|
34
|
+
'Load Balancer'
|
35
|
+
end
|
36
|
+
|
37
|
+
def load_balancer_plural_label
|
38
|
+
'Load Balancers'
|
39
|
+
end
|
40
|
+
|
41
|
+
def load_balancer_type_object_key
|
42
|
+
'loadBalancerType'
|
43
|
+
end
|
44
|
+
|
45
|
+
def load_balancer_type_list_key
|
46
|
+
'loadBalancerTypes'
|
47
|
+
end
|
48
|
+
|
49
|
+
def load_balancer_type_label
|
50
|
+
'Load Balancer Type'
|
51
|
+
end
|
52
|
+
|
53
|
+
def load_balancer_type_plural_label
|
54
|
+
'Load Balancer Types'
|
55
|
+
end
|
56
|
+
|
57
|
+
def find_load_balancer_by_name_or_id(val)
|
58
|
+
if val.to_s =~ /\A\d{1,}\Z/
|
59
|
+
return find_load_balancer_by_id(val)
|
60
|
+
else
|
61
|
+
return find_load_balancer_by_name(val)
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
def find_load_balancer_by_id(id)
|
66
|
+
begin
|
67
|
+
json_response = load_balancers_interface.get(id.to_i)
|
68
|
+
return json_response[load_balancer_object_key]
|
69
|
+
rescue RestClient::Exception => e
|
70
|
+
if e.response && e.response.code == 404
|
71
|
+
print_red_alert "Load Balancer not found by id #{id}"
|
72
|
+
else
|
73
|
+
raise e
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
def find_load_balancer_by_name(name)
|
79
|
+
lbs = load_balancers_interface.list({name: name.to_s})[load_balancer_list_key]
|
80
|
+
if lbs.empty?
|
81
|
+
print_red_alert "Load Balancer not found by name #{name}"
|
82
|
+
return nil
|
83
|
+
elsif lbs.size > 1
|
84
|
+
print_red_alert "#{lbs.size} load balancers found by name #{name}"
|
85
|
+
#print_lbs_table(lbs, {color: red})
|
86
|
+
print reset,"\n\n"
|
87
|
+
return nil
|
88
|
+
else
|
89
|
+
return lbs[0]
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
def get_available_load_balancer_types(refresh=false)
|
94
|
+
if !@available_load_balancer_types || refresh
|
95
|
+
@available_load_balancer_types = load_balancer_types_interface.list({max:1000})[load_balancer_type_list_key]
|
96
|
+
end
|
97
|
+
return @available_load_balancer_types
|
98
|
+
end
|
99
|
+
|
100
|
+
def load_balancer_type_for_name_or_id(val)
|
101
|
+
if val.to_s =~ /\A\d{1,}\Z/
|
102
|
+
return load_balancer_type_for_id(val)
|
103
|
+
else
|
104
|
+
return load_balancer_type_for_name(val)
|
105
|
+
end
|
106
|
+
end
|
107
|
+
|
108
|
+
def load_balancer_type_for_id(id)
|
109
|
+
return get_available_load_balancer_types().find { |z| z['id'].to_i == id.to_i}
|
110
|
+
end
|
111
|
+
|
112
|
+
def load_balancer_type_for_name(name)
|
113
|
+
return get_available_load_balancer_types().find { |z| z['name'].downcase == name.downcase || z['code'].downcase == name.downcase}
|
114
|
+
end
|
115
|
+
|
116
|
+
def find_load_balancer_type_by_name_or_id(val)
|
117
|
+
if val.to_s =~ /\A\d{1,}\Z/
|
118
|
+
return find_load_balancer_type_by_id(val)
|
119
|
+
else
|
120
|
+
return find_load_balancer_type_by_name(val)
|
121
|
+
end
|
122
|
+
end
|
123
|
+
|
124
|
+
def find_load_balancer_type_by_id(id)
|
125
|
+
begin
|
126
|
+
json_response = load_balancer_types_interface.get(id.to_i)
|
127
|
+
return json_response[load_balancer_type_object_key]
|
128
|
+
rescue RestClient::Exception => e
|
129
|
+
if e.response && e.response.code == 404
|
130
|
+
print_red_alert "Load Balancer Type not found by id #{id}"
|
131
|
+
return nil
|
132
|
+
else
|
133
|
+
raise e
|
134
|
+
end
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
def find_load_balancer_type_by_name(name)
|
139
|
+
json_response = load_balancer_types_interface.list({name: name.to_s})
|
140
|
+
load_balancer_types = json_response[load_balancer_type_list_key]
|
141
|
+
if load_balancer_types.empty?
|
142
|
+
print_red_alert "Load Balancer Type not found by name #{name}"
|
143
|
+
return load_balancer_types
|
144
|
+
elsif load_balancer_types.size > 1
|
145
|
+
print_red_alert "#{load_balancer_types.size} load balancer types found by name #{name}"
|
146
|
+
rows = load_balancer_types.collect do |it|
|
147
|
+
{id: it['id'], name: it['name']}
|
148
|
+
end
|
149
|
+
puts as_pretty_table(rows, [:id, :name], {color:red})
|
150
|
+
return nil
|
151
|
+
else
|
152
|
+
return load_balancer_types[0]
|
153
|
+
end
|
154
|
+
end
|
155
|
+
|
156
|
+
end
|
@@ -1335,4 +1335,15 @@ module Morpheus::Cli::PrintHelper
|
|
1335
1335
|
parse_json_or_yaml(config, parsers)
|
1336
1336
|
end
|
1337
1337
|
|
1338
|
+
def format_option_types_table(option_types, options={}, domain_name=nil)
|
1339
|
+
columns = [
|
1340
|
+
{"FIELD LABEL" => lambda {|it| it['fieldLabel'] } },
|
1341
|
+
{"FIELD NAME" => lambda {|it| [it['fieldContext'] == domain_name ? nil : it['fieldContext'], it['fieldName']].select {|it| !it.to_s.empty? }.join('.') } },
|
1342
|
+
{"TYPE" => lambda {|it| it['type'] } },
|
1343
|
+
{"DEFAULT" => lambda {|it| it['defaultValue'] } },
|
1344
|
+
{"REQUIRED" => lambda {|it| format_boolean it['required'] } },
|
1345
|
+
]
|
1346
|
+
as_pretty_table(option_types, columns, options)
|
1347
|
+
end
|
1348
|
+
|
1338
1349
|
end
|
@@ -484,7 +484,7 @@ module Morpheus::Cli::ProvisioningHelper
|
|
484
484
|
if options[:instance_type_code]
|
485
485
|
instance_type_code = options[:instance_type_code]
|
486
486
|
else
|
487
|
-
instance_type_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'type', 'type' => 'select', 'fieldLabel' => 'Type', 'optionSource' => 'instanceTypes', 'required' => true, 'description' => 'Select Instance Type.'}],options[:options],api_client,{groupId: group_id})
|
487
|
+
instance_type_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'type', 'type' => 'select', 'fieldLabel' => 'Type', 'optionSource' => 'instanceTypes', 'required' => true, 'description' => 'Select Instance Type.'}],options[:options],api_client,{groupId: group_id}, no_prompt, true)
|
488
488
|
instance_type_code = instance_type_prompt['type']
|
489
489
|
end
|
490
490
|
if instance_type_code.to_s =~ /\A\d{1,}\Z/
|
@@ -657,13 +657,11 @@ module Morpheus::Cli::ProvisioningHelper
|
|
657
657
|
version_value = default_version_value
|
658
658
|
version_is_required = default_layout_value.nil?
|
659
659
|
if default_layout_value.nil? && options[:options]["layout"].nil? && options[:always_prompt] != true
|
660
|
-
#version_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'version', 'type' => 'select', 'fieldLabel' => 'Version', 'optionSource' => 'instanceVersions', 'required' => true, 'skipSingleOption' => true, 'autoPickOption' => true, 'description' => 'Select which version of the instance type to be provisioned.', 'defaultValue' => default_version_value}],options[:options],api_client,{groupId: group_id, cloudId: cloud_id, instanceTypeId: instance_type['id']})
|
661
660
|
version_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'version', 'type' => 'select', 'fieldLabel' => 'Version', 'selectOptions' => available_versions, 'required' => version_is_required, 'skipSingleOption' => true, 'autoPickOption' => true, 'description' => 'Select which version of the instance type to be provisioned.', 'defaultValue' => default_version_value}],options[:options],api_client,{groupId: group_id, cloudId: cloud_id, instanceTypeId: instance_type['id']})
|
662
661
|
version_value = version_prompt['version']
|
663
662
|
end
|
664
663
|
end
|
665
|
-
|
666
|
-
layout_id = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'layout', 'type' => 'select', 'fieldLabel' => 'Layout', 'optionSource' => 'layoutsForCloud', 'required' => true, 'description' => 'Select which configuration of the instance type to be provisioned.', 'defaultValue' => default_layout_value}],options[:options],api_client,{groupId: group_id, cloudId: cloud_id, instanceTypeId: instance_type['id'], version: version_value, creatable: true})['layout']
|
664
|
+
layout_id = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'layout', 'type' => 'select', 'fieldLabel' => 'Layout', 'optionSource' => 'layoutsForCloud', 'required' => true, 'description' => 'Select which configuration of the instance type to be provisioned.', 'defaultValue' => default_layout_value}],options[:options],api_client,{groupId: group_id, cloudId: cloud_id, instanceTypeId: instance_type['id'], version: version_value, creatable: true}, no_prompt, true)['layout']
|
667
665
|
end
|
668
666
|
end
|
669
667
|
|
@@ -679,7 +677,7 @@ module Morpheus::Cli::ProvisioningHelper
|
|
679
677
|
end
|
680
678
|
layout_id = layout['id']
|
681
679
|
payload['instance']['layout'] = {'id' => layout['id'], 'code' => layout['code']}
|
682
|
-
|
680
|
+
|
683
681
|
# need to GET provision type for optionTypes, and other settings...
|
684
682
|
provision_type_code = layout['provisionTypeCode'] || layout['provisionType']['code']
|
685
683
|
provision_type = nil
|
@@ -693,50 +691,6 @@ module Morpheus::Cli::ProvisioningHelper
|
|
693
691
|
provision_type = get_provision_type_for_zone_type(cloud['zoneType']['id'])
|
694
692
|
end
|
695
693
|
|
696
|
-
# prompt for service plan
|
697
|
-
plan_id = nil
|
698
|
-
service_plan = nil
|
699
|
-
service_plans_json = instances_interface.service_plans({zoneId: cloud_id, layoutId: layout['id'], siteId: group_id})
|
700
|
-
service_plans = service_plans_json["plans"]
|
701
|
-
if locked_fields.include?('plan.id')
|
702
|
-
plan_id = options[:options]['plan']['id'] rescue nil
|
703
|
-
if plan_id.nil?
|
704
|
-
plan_id = options[:options]['instance']['plan']['id'] rescue nil
|
705
|
-
end
|
706
|
-
service_plan = service_plans.find {|sp| sp['id'] == plan_id }
|
707
|
-
else
|
708
|
-
service_plan = service_plans.find {|sp| sp['id'] == options[:service_plan].to_i} if options[:service_plan]
|
709
|
-
|
710
|
-
if !service_plan
|
711
|
-
service_plans_dropdown = service_plans.collect {|sp| {'name' => sp["name"], 'value' => sp["id"], 'code' => sp['code']} } # already sorted
|
712
|
-
default_plan = nil
|
713
|
-
if payload['plan']
|
714
|
-
default_plan = payload['plan']
|
715
|
-
elsif payload['instance'] && payload['instance']['plan']
|
716
|
-
default_plan = payload['instance']['plan']
|
717
|
-
end
|
718
|
-
|
719
|
-
if options[:default_plan] && service_plans_dropdown.find {|sp| [sp["name"], sp["value"].to_s, sp["code"]].include?(options[:default_plan].to_s)}
|
720
|
-
default_plan_value = options[:default_plan]
|
721
|
-
else
|
722
|
-
default_plan_value = options[:default_plan] || (default_plan.is_a?(Hash) ? default_plan['id'] : default_plan)
|
723
|
-
end
|
724
|
-
plan_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'servicePlan', 'type' => 'select', 'fieldLabel' => 'Plan', 'selectOptions' => service_plans_dropdown, 'required' => true, 'description' => 'Choose the appropriately sized plan for this instance', 'defaultValue' => default_plan_value}],options[:options])
|
725
|
-
plan_id = plan_prompt['servicePlan']
|
726
|
-
service_plan = service_plans.find {|sp| sp["id"] == plan_id.to_i }
|
727
|
-
if !service_plan
|
728
|
-
print_red_alert "Plan not found by id #{plan_id}"
|
729
|
-
exit 1
|
730
|
-
end
|
731
|
-
end
|
732
|
-
#todo: consolidate these, instances api looks for instance.plan.id and apps looks for plan.id
|
733
|
-
if options[:for_app]
|
734
|
-
payload['plan'] = {'id' => service_plan["id"], 'code' => service_plan["code"], 'name' => service_plan["name"]}
|
735
|
-
else
|
736
|
-
payload['instance']['plan'] = {'id' => service_plan["id"], 'code' => service_plan["code"], 'name' => service_plan["name"]}
|
737
|
-
end
|
738
|
-
end
|
739
|
-
|
740
694
|
# build config option types
|
741
695
|
option_type_list = []
|
742
696
|
if !layout['optionTypes'].nil? && !layout['optionTypes'].empty?
|
@@ -745,47 +699,112 @@ module Morpheus::Cli::ProvisioningHelper
|
|
745
699
|
if !instance_type['optionTypes'].nil? && !instance_type['optionTypes'].empty?
|
746
700
|
option_type_list += instance_type['optionTypes']
|
747
701
|
end
|
748
|
-
if !provision_type.nil? && !provision_type['optionTypes'].nil? && !provision_type['optionTypes'].empty?
|
749
|
-
option_type_list += provision_type['optionTypes']
|
750
|
-
end
|
751
702
|
|
752
|
-
|
703
|
+
api_params = {groupId: group_id, cloudId: cloud_id, zoneId: cloud_id, instanceTypeId: instance_type['id'], version: version_value}
|
704
|
+
|
753
705
|
pool_id = nil
|
754
706
|
resource_pool = nil
|
755
|
-
|
756
|
-
|
757
|
-
|
758
|
-
|
759
|
-
|
760
|
-
|
761
|
-
|
762
|
-
|
763
|
-
|
764
|
-
|
765
|
-
|
766
|
-
|
767
|
-
|
768
|
-
|
769
|
-
|
770
|
-
|
771
|
-
|
772
|
-
|
773
|
-
|
774
|
-
|
707
|
+
service_plan = nil
|
708
|
+
|
709
|
+
prompt_service_plan = -> {
|
710
|
+
service_plans_json = instances_interface.service_plans({zoneId: cloud_id, layoutId: layout['id'], siteId: group_id}.merge(resource_pool.nil? ? {} : {'resourcePoolId' => resource_pool['id']}))
|
711
|
+
service_plans = service_plans_json["plans"]
|
712
|
+
if locked_fields.include?('plan.id')
|
713
|
+
plan_id = options[:options]['plan']['id'] rescue nil
|
714
|
+
if plan_id.nil?
|
715
|
+
plan_id = options[:options]['instance']['plan']['id'] rescue nil
|
716
|
+
end
|
717
|
+
service_plan = service_plans.find {|sp| sp['id'] == plan_id }
|
718
|
+
else
|
719
|
+
service_plan = service_plans.find {|sp| sp['id'] == options[:service_plan].to_i} if options[:service_plan]
|
720
|
+
|
721
|
+
if !service_plan
|
722
|
+
service_plans_dropdown = service_plans.collect {|sp| {'name' => sp["name"], 'value' => sp["id"], 'code' => sp['code']} } # already sorted
|
723
|
+
default_plan = nil
|
724
|
+
if payload['plan']
|
725
|
+
default_plan = payload['plan']
|
726
|
+
elsif payload['instance'] && payload['instance']['plan']
|
727
|
+
default_plan = payload['instance']['plan']
|
775
728
|
end
|
776
|
-
|
777
|
-
|
778
|
-
|
779
|
-
|
780
|
-
|
781
|
-
|
782
|
-
|
783
|
-
|
784
|
-
|
729
|
+
|
730
|
+
if options[:default_plan] && service_plans_dropdown.find {|sp| [sp["name"], sp["value"].to_s, sp["code"]].include?(options[:default_plan].to_s)}
|
731
|
+
default_plan_value = options[:default_plan]
|
732
|
+
else
|
733
|
+
default_plan_value = options[:default_plan] || (default_plan.is_a?(Hash) ? default_plan['id'] : default_plan)
|
734
|
+
end
|
735
|
+
plan_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'servicePlan', 'type' => 'select', 'fieldLabel' => 'Plan', 'selectOptions' => service_plans_dropdown, 'required' => true, 'description' => 'Choose the appropriately sized plan for this instance', 'defaultValue' => default_plan_value}],options[:options], api_client, {}, no_prompt, true)
|
736
|
+
plan_id = plan_prompt['servicePlan']
|
737
|
+
service_plan = service_plans.find {|sp| sp["id"] == plan_id.to_i }
|
738
|
+
if !service_plan
|
739
|
+
print_red_alert "Plan not found by id #{plan_id}"
|
740
|
+
exit 1
|
785
741
|
end
|
786
|
-
resource_pool ||= resource_pool_options.find {|it| it['id'] == pool_id}
|
787
742
|
end
|
743
|
+
#todo: consolidate these, instances api looks for instance.plan.id and apps looks for plan.id
|
744
|
+
if options[:for_app]
|
745
|
+
payload['plan'] = {'id' => service_plan["id"], 'code' => service_plan["code"], 'name' => service_plan["name"]}
|
746
|
+
else
|
747
|
+
payload['instance']['plan'] = {'id' => service_plan["id"], 'code' => service_plan["code"], 'name' => service_plan["name"]}
|
748
|
+
end
|
749
|
+
end
|
750
|
+
}
|
751
|
+
|
752
|
+
prompt_resource_pool = -> {
|
753
|
+
# prompt for resource pool
|
754
|
+
if locked_fields.include?('config.resourcePoolId')
|
755
|
+
pool_id = payload['config']['resourcePoolId'] rescue nil
|
756
|
+
elsif locked_fields.include?('config.resourcePool')
|
757
|
+
pool_id = payload['config']['resourcePool'] rescue nil
|
758
|
+
elsif locked_fields.include?('config.azureResourceGroupId')
|
759
|
+
pool_id = payload['config']['azureResourceGroupId'] rescue nil
|
760
|
+
else
|
761
|
+
has_zone_pools = provision_type && provision_type["id"] && provision_type["hasZonePools"]
|
762
|
+
if has_zone_pools
|
763
|
+
# pluck out the resourcePoolId option type to prompt for
|
764
|
+
resource_pool_option_type = option_type_list.find {|opt| ['resourcePool','resourcePoolId','azureResourceGroupId'].include?(opt['fieldName']) }
|
765
|
+
option_type_list = option_type_list.reject {|opt| ['resourcePool','resourcePoolId','azureResourceGroupId'].include?(opt['fieldName']) }
|
766
|
+
|
767
|
+
resource_pool_options = options_interface.options_for_source('zonePools', {groupId: group_id, siteId: group_id, zoneId: cloud_id, cloudId: cloud_id, instanceTypeId: instance_type['id'], layoutId: layout["id"]}.merge(service_plan.nil? ? {} : {planId: service_plan["id"]}))['data']
|
768
|
+
resource_pool = resource_pool_options.find {|opt| opt['id'] == options[:resource_pool].to_i} if options[:resource_pool]
|
769
|
+
|
770
|
+
if resource_pool
|
771
|
+
pool_id = resource_pool['id']
|
772
|
+
else
|
773
|
+
if options[:default_resource_pool]
|
774
|
+
default_resource_pool = resource_pool_options.find {|rp| rp['id'] == options[:default_resource_pool]}
|
775
|
+
end
|
776
|
+
resource_pool_option_type ||= {'fieldContext' => 'config', 'fieldName' => 'resourcePoolId', 'type' => 'select', 'fieldLabel' => 'Resource Pool', 'selectOptions' => resource_pool_options, 'required' => true, 'skipSingleOption' => true, 'description' => 'Select resource pool.', 'defaultValue' => default_resource_pool ? default_resource_pool['name'] : nil}
|
777
|
+
resource_pool_prompt = Morpheus::Cli::OptionTypes.prompt([resource_pool_option_type],options[:options],api_client,{}, no_prompt, true)
|
778
|
+
resource_pool_prompt.deep_compact!
|
779
|
+
payload.deep_merge!(resource_pool_prompt)
|
780
|
+
resource_pool = Morpheus::Cli::OptionTypes.get_last_select()
|
781
|
+
if resource_pool_option_type['fieldContext'] && resource_pool_prompt[resource_pool_option_type['fieldContext']]
|
782
|
+
pool_id = resource_pool_prompt[resource_pool_option_type['fieldContext']][resource_pool_option_type['fieldName']]
|
783
|
+
elsif resource_pool_prompt[resource_pool_option_type['fieldName']]
|
784
|
+
pool_id = resource_pool_prompt[resource_pool_option_type['fieldName']]
|
785
|
+
end
|
786
|
+
resource_pool ||= resource_pool_options.find {|it| it['id'] == pool_id}
|
787
|
+
end
|
788
|
+
end
|
789
|
+
end
|
790
|
+
}
|
791
|
+
|
792
|
+
prompt_provision_options = -> {
|
793
|
+
if !provision_type.nil? && !provision_type['optionTypes'].nil? && !provision_type['optionTypes'].empty?
|
794
|
+
option_type_list += provision_type['optionTypes'].reject {|it| (it['fieldGroup'] || '').downcase == 'provisiontype'}
|
795
|
+
provision_config_payload = Morpheus::Cli::OptionTypes.prompt(provision_type['optionTypes'].reject {|it| (it['fieldGroup'] || '').downcase != 'provisiontype'}, options[:options], @api_client, api_params, no_prompt, true)
|
796
|
+
payload.deep_merge!(provision_config_payload)
|
788
797
|
end
|
798
|
+
}
|
799
|
+
|
800
|
+
if ['openstack', 'huawei', 'opentelekom'].include?(cloud_type['zoneType']['code'])
|
801
|
+
prompt_resource_pool.call
|
802
|
+
prompt_provision_options.call
|
803
|
+
prompt_service_plan.call
|
804
|
+
else
|
805
|
+
prompt_service_plan.call
|
806
|
+
prompt_provision_options.call
|
807
|
+
prompt_resource_pool.call
|
789
808
|
end
|
790
809
|
|
791
810
|
# remove host selection for kubernetes
|
@@ -858,7 +877,7 @@ module Morpheus::Cli::ProvisioningHelper
|
|
858
877
|
if provision_type && provision_type["hasNetworks"]
|
859
878
|
# prompt for network interfaces (if supported)
|
860
879
|
begin
|
861
|
-
network_interfaces = prompt_network_interfaces(cloud_id, provision_type["id"], pool_id, options)
|
880
|
+
network_interfaces = prompt_network_interfaces(cloud_id, provision_type["id"], pool_id, options.merge({:api_params => payload['config']}))
|
862
881
|
if !network_interfaces.empty?
|
863
882
|
payload['networkInterfaces'] = network_interfaces
|
864
883
|
end
|
@@ -921,7 +940,6 @@ module Morpheus::Cli::ProvisioningHelper
|
|
921
940
|
end
|
922
941
|
|
923
942
|
# prompt for option types
|
924
|
-
api_params = {groupId: group_id, cloudId: cloud_id, zoneId: cloud_id, instanceTypeId: instance_type['id'], version: version_value}
|
925
943
|
api_params['config'] = payload['config'] if payload['config']
|
926
944
|
api_params['poolId'] = payload['config']['resourcePoolId'] if payload['config'] && payload['config']['resourcePoolId']
|
927
945
|
|
@@ -935,10 +953,21 @@ module Morpheus::Cli::ProvisioningHelper
|
|
935
953
|
end
|
936
954
|
end
|
937
955
|
|
938
|
-
|
939
|
-
|
956
|
+
option_type_list += [
|
957
|
+
{'fieldName' => 'userGroup.id', 'fieldLabel' => 'User Group', 'fieldGroup' => 'User Config', 'type' => 'select', 'optionSource' => 'userGroups', 'displayOrder' => 0, 'fieldContext' => 'instance'},
|
958
|
+
{'fieldName' => 'hostName', 'fieldLabel' => 'Hostname', 'fieldGroup' => 'Advanced', 'type' => 'string', 'displayOrder' => 1},
|
959
|
+
{'fieldName' => 'networkDomain.id', 'fieldLabel' => 'Domain', 'fieldGroup' => 'Advanced', 'type' => 'select', 'optionSource' => 'networkDomains', 'displayOrder' => 2, 'fieldContext' => 'instance'},
|
960
|
+
{'fieldName' => 'timezone', 'fieldLabel' => 'Time Zone', 'fieldGroup' => 'Advanced', 'type' => 'select', 'optionSource' => 'timezones', 'displayOrder' => 3, 'fieldContext' => 'config'}
|
961
|
+
]
|
940
962
|
|
941
|
-
|
963
|
+
if instance_type['hasAutoScale']
|
964
|
+
option_type_list += [
|
965
|
+
{'fieldName' => 'layoutSize', 'fieldLabel' => 'Scale Factor', 'fieldGroup' => 'Advanced', 'type' => 'number', 'defaultValue' => 1, 'displayOrder' => 0},
|
966
|
+
]
|
967
|
+
end
|
968
|
+
|
969
|
+
instance_config_payload = Morpheus::Cli::OptionTypes.prompt(option_type_list.reject {|ot| ot['type'] == 'exposedPorts'}, options[:options], @api_client, api_params, no_prompt, true)
|
970
|
+
payload.deep_merge!(instance_config_payload)
|
942
971
|
|
943
972
|
# prompt for exposed ports
|
944
973
|
if payload['ports'].nil?
|
@@ -950,10 +979,6 @@ module Morpheus::Cli::ProvisioningHelper
|
|
950
979
|
end
|
951
980
|
end
|
952
981
|
|
953
|
-
## Advanced Options
|
954
|
-
|
955
|
-
# scale factor
|
956
|
-
|
957
982
|
# prompt for environment variables
|
958
983
|
evars = prompt_evars(options)
|
959
984
|
if !evars.empty?
|
@@ -1327,13 +1352,9 @@ module Morpheus::Cli::ProvisioningHelper
|
|
1327
1352
|
|
1328
1353
|
field_context = "dataVolume#{volume_index}"
|
1329
1354
|
|
1330
|
-
|
1331
|
-
|
1332
|
-
|
1333
|
-
action_options = [{'name' => 'Modify', 'value' => 'modify'}, {'name' => 'Keep', 'value' => 'keep'}, {'name' => 'Delete', 'value' => 'delete'}]
|
1334
|
-
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldContext' => field_context, 'fieldName' => 'action', 'type' => 'select', 'fieldLabel' => "Modify/Keep/Delete volume '#{current_volume['name']}'", 'selectOptions' => action_options, 'required' => true, 'description' => 'Modify, Keep or Delete existing data volume?'}], options[:options])
|
1335
|
-
volume_action = v_prompt[field_context]['action']
|
1336
|
-
end
|
1355
|
+
action_options = [{'name' => 'Modify', 'value' => 'modify'}, {'name' => 'Keep', 'value' => 'keep'}, {'name' => 'Delete', 'value' => 'delete'}]
|
1356
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldContext' => field_context, 'fieldName' => 'action', 'type' => 'select', 'fieldLabel' => "Modify/Keep/Delete volume '#{current_volume['name']}'", 'selectOptions' => action_options, 'required' => true, 'defaultValue' => 'keep', 'description' => 'Modify, Keep or Delete existing data volume?'}], options[:options])
|
1357
|
+
volume_action = v_prompt[field_context]['action']
|
1337
1358
|
|
1338
1359
|
if volume_action == 'delete'
|
1339
1360
|
# deleted volume is just excluded from post params
|
@@ -1490,10 +1511,11 @@ module Morpheus::Cli::ProvisioningHelper
|
|
1490
1511
|
#puts "Configure Networks:"
|
1491
1512
|
no_prompt = (options[:no_prompt] || (options[:options] && options[:options][:no_prompt]))
|
1492
1513
|
network_interfaces = []
|
1493
|
-
api_params = {zoneId: zone_id, provisionTypeId: provision_type_id}
|
1514
|
+
api_params = {zoneId: zone_id, provisionTypeId: provision_type_id}.merge(options[:api_params] || {})
|
1494
1515
|
if pool_id.to_s =~ /\A\d{1,}\Z/
|
1495
1516
|
api_params[:poolId] = pool_id
|
1496
1517
|
end
|
1518
|
+
|
1497
1519
|
zone_network_options_json = api_client.options.options_for_source('zoneNetworkOptions', api_params)
|
1498
1520
|
# puts "zoneNetworkOptions JSON"
|
1499
1521
|
# puts JSON.pretty_generate(zone_network_options_json)
|
@@ -1575,7 +1597,7 @@ module Morpheus::Cli::ProvisioningHelper
|
|
1575
1597
|
default_network_value = (network_options.find {|n| n['value'] == default_network_id} || {})['name']
|
1576
1598
|
|
1577
1599
|
# choose network
|
1578
|
-
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldContext' => field_context, 'fieldName' => 'networkId', 'type' => 'select', 'fieldLabel' => "Network", 'selectOptions' => network_options, 'required' => true, 'skipSingleOption' => false, 'description' => 'Choose a network for this interface.', 'defaultValue' => default_network_value}], options[:options])
|
1600
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldContext' => field_context, 'fieldName' => 'networkId', 'type' => 'select', 'fieldLabel' => "Network", 'selectOptions' => network_options, 'required' => true, 'skipSingleOption' => false, 'description' => 'Choose a network for this interface.', 'defaultValue' => default_network_value}], options[:options], api_client, {}, no_prompt, true)
|
1579
1601
|
network_interface['network'] = {}
|
1580
1602
|
network_interface['network']['id'] = v_prompt[field_context]['networkId'].to_s
|
1581
1603
|
selected_network = networks.find {|it| it["id"].to_s == network_interface['network']['id'] }
|