morpheus-cli 5.4.2 → 5.4.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/morpheus/api/api_client.rb +4 -1
- data/lib/morpheus/api/catalog_item_types_interface.rb +20 -0
- data/lib/morpheus/api/instances_interface.rb +28 -0
- data/lib/morpheus/api/ping_interface.rb +2 -0
- data/lib/morpheus/api/setup_interface.rb +4 -0
- data/lib/morpheus/api/snapshots_interface.rb +19 -0
- data/lib/morpheus/cli/commands/catalog_item_types_command.rb +88 -0
- data/lib/morpheus/cli/commands/clusters.rb +59 -46
- data/lib/morpheus/cli/commands/hosts.rb +12 -0
- data/lib/morpheus/cli/commands/instances.rb +250 -1
- data/lib/morpheus/cli/commands/library_instance_types_command.rb +3 -0
- data/lib/morpheus/cli/commands/network_static_routes_command.rb +5 -0
- data/lib/morpheus/cli/commands/networks_command.rb +2 -2
- data/lib/morpheus/cli/commands/ping.rb +3 -5
- data/lib/morpheus/cli/commands/policies_command.rb +1 -1
- data/lib/morpheus/cli/commands/provisioning_settings_command.rb +1 -0
- data/lib/morpheus/cli/commands/remote.rb +16 -10
- data/lib/morpheus/cli/commands/security_groups.rb +2 -2
- data/lib/morpheus/cli/commands/service_plans_command.rb +1 -1
- data/lib/morpheus/cli/commands/setup.rb +1 -1
- data/lib/morpheus/cli/commands/snapshots.rb +139 -0
- data/lib/morpheus/cli/commands/tasks.rb +5 -5
- data/lib/morpheus/cli/commands/user_settings_command.rb +1 -1
- data/lib/morpheus/cli/commands/virtual_images.rb +4 -1
- data/lib/morpheus/cli/mixins/provisioning_helper.rb +80 -0
- data/lib/morpheus/cli/option_types.rb +26 -11
- data/lib/morpheus/cli/version.rb +1 -1
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1115efb46c7480c6a3814183c5748f27ce92d8be5ca935116fac0a26d66a58aa
|
4
|
+
data.tar.gz: a47a2aa8cb3d36dfff5de6e811c2948e54e54771d3e00c47ca377db50b77fbbf
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ab05b111e694eded06459369814d4dcf462766a48a861831a004e428324b7181b570b8df6b6c8097f5be6bc5fc3be2d2ea59ac44ae4003cc444b53e49d2a3665
|
7
|
+
data.tar.gz: b4760ef297c3a3dd9b19b71c0d4702885803dc5ae107a2cf538c074fd6a17191303910b28e119560113ce6f50208e250b6c07659e003da80c8c6c068cfad26ed
|
@@ -347,7 +347,6 @@ class Morpheus::APIClient
|
|
347
347
|
end
|
348
348
|
|
349
349
|
def auth
|
350
|
-
# Morpheus::AuthInterface.new(common_interface_options).setopts(@options)
|
351
350
|
Morpheus::AuthInterface.new({url: @base_url, client_id: @client_id, verify_ssl: @verify_ssl}).setopts(@options)
|
352
351
|
end
|
353
352
|
|
@@ -889,6 +888,10 @@ class Morpheus::APIClient
|
|
889
888
|
Morpheus::NetworkStaticRoutesInterface.new(common_interface_options).setopts(@options)
|
890
889
|
end
|
891
890
|
|
891
|
+
def snapshots
|
892
|
+
Morpheus::SnapshotsInterface.new(common_interface_options).setopts(@options)
|
893
|
+
end
|
894
|
+
|
892
895
|
def rest(endpoint)
|
893
896
|
Morpheus::RestInterface.new(common_interface_options).setopts(@options.merge({base_path: "#{@base_url}/api/#{endpoint}"}))
|
894
897
|
end
|
@@ -6,4 +6,24 @@ class Morpheus::CatalogItemTypesInterface < Morpheus::RestInterface
|
|
6
6
|
"/api/catalog-item-types"
|
7
7
|
end
|
8
8
|
|
9
|
+
# NOT json, multipart file upload
|
10
|
+
# def update_logo(id, logo_file)
|
11
|
+
# url = "#{base_path}/#{id}/update-logo"
|
12
|
+
# headers = { :params => {}, :authorization => "Bearer #{@access_token}"}
|
13
|
+
# payload = {}
|
14
|
+
# payload[:logo] = logo_file
|
15
|
+
# payload[:multipart] = true
|
16
|
+
# execute(method: :post, url: url, headers: headers, payload: payload)
|
17
|
+
# end
|
18
|
+
|
19
|
+
# NOT json, multipart file upload, uses PUT update endpoint
|
20
|
+
def update_logo(id, logo_file)
|
21
|
+
url = "#{base_path}/#{id}"
|
22
|
+
headers = { :params => {}, :authorization => "Bearer #{@access_token}"}
|
23
|
+
payload = {}
|
24
|
+
payload["catalogItemType"] = {"logo" => logo_file}
|
25
|
+
payload[:multipart] = true
|
26
|
+
execute(method: :put, url: url, headers: headers, payload: payload)
|
27
|
+
end
|
28
|
+
|
9
29
|
end
|
@@ -262,6 +262,34 @@ class Morpheus::InstancesInterface < Morpheus::APIClient
|
|
262
262
|
execute(opts)
|
263
263
|
end
|
264
264
|
|
265
|
+
def revert_to_snapshot(id, snapshot_id, payload={})
|
266
|
+
url = "#{@base_url}/api/instances/#{id}/revert-snapshot/#{snapshot_id}"
|
267
|
+
headers = {:authorization => "Bearer #{@access_token}", 'Content-Type' => 'application/json' }
|
268
|
+
opts = {method: :put, url: url, headers: headers, payload: payload.to_json}
|
269
|
+
execute(opts)
|
270
|
+
end
|
271
|
+
|
272
|
+
def remove_all_container_snapshots(id, container_id, payload={})
|
273
|
+
url = "#{@base_url}/api/instances/#{id}/delete-container-snapshots/#{container_id}"
|
274
|
+
headers = {:authorization => "Bearer #{@access_token}", 'Content-Type' => 'application/json' }
|
275
|
+
opts = {method: :delete, url: url, headers: headers, payload: payload.to_json}
|
276
|
+
execute(opts)
|
277
|
+
end
|
278
|
+
|
279
|
+
def remove_all_instance_snapshots(id, payload={})
|
280
|
+
url = "#{@base_url}/api/instances/#{id}/delete-all-snapshots"
|
281
|
+
headers = {:authorization => "Bearer #{@access_token}", 'Content-Type' => 'application/json' }
|
282
|
+
opts = {method: :delete, url: url, headers: headers, payload: payload.to_json}
|
283
|
+
execute(opts)
|
284
|
+
end
|
285
|
+
|
286
|
+
def create_linked_clone(id, snapshot_id, payload={})
|
287
|
+
url = "#{@base_url}/api/instances/#{id}/linked-clone/#{snapshot_id}"
|
288
|
+
headers = {:authorization => "Bearer #{@access_token}", 'Content-Type' => 'application/json' }
|
289
|
+
opts = {method: :put, url: url, headers: headers, payload: payload.to_json}
|
290
|
+
execute(opts)
|
291
|
+
end
|
292
|
+
|
265
293
|
def service_plans(params={})
|
266
294
|
url = "#{@base_url}/api/instances/service-plans"
|
267
295
|
headers = { params: params, authorization: "Bearer #{@access_token}" }
|
@@ -14,6 +14,8 @@ class Morpheus::PingInterface < Morpheus::APIClient
|
|
14
14
|
|
15
15
|
def get(params={})
|
16
16
|
headers = {params: params}
|
17
|
+
# use access token if authenticated
|
18
|
+
headers[:authorization] = "Bearer #{@access_token}" if @access_token
|
17
19
|
execute(method: :get, url: "/api/ping", headers: headers)
|
18
20
|
end
|
19
21
|
|
@@ -14,12 +14,16 @@ class Morpheus::SetupInterface < Morpheus::APIClient
|
|
14
14
|
|
15
15
|
def get(params={})
|
16
16
|
headers = {params: params}
|
17
|
+
# use access token if authenticated
|
18
|
+
headers[:authorization] = "Bearer #{@access_token}" if @access_token
|
17
19
|
execute(method: :get, url: "/api/setup", headers: headers)
|
18
20
|
end
|
19
21
|
|
20
22
|
#this should go away and just use
|
21
23
|
def check(params={}, timeout=5)
|
22
24
|
headers = {params: params}
|
25
|
+
# use access token if authenticated
|
26
|
+
headers[:authorization] = "Bearer #{@access_token}" if @access_token
|
23
27
|
execute(method: :get, url: "/api/setup/check", headers: headers, timeout: timeout)
|
24
28
|
end
|
25
29
|
|
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'morpheus/api/api_client'
|
2
|
+
|
3
|
+
# Snapshots API interface.
|
4
|
+
class Morpheus::SnapshotsInterface < Morpheus::APIClient
|
5
|
+
|
6
|
+
def get(snapshot_id)
|
7
|
+
url = "#{@base_url}/api/snapshots/#{snapshot_id}"
|
8
|
+
headers = { :authorization => "Bearer #{@access_token}", 'Content-Type' => 'application/json' }
|
9
|
+
opts = {method: :get, url: url, headers: headers}
|
10
|
+
execute(opts)
|
11
|
+
end
|
12
|
+
|
13
|
+
def remove(snapshot_id, payload={})
|
14
|
+
url = "#{@base_url}/api/snapshots/#{snapshot_id}"
|
15
|
+
headers = {:authorization => "Bearer #{@access_token}", 'Content-Type' => 'application/json' }
|
16
|
+
opts = {method: :delete, url: url, headers: headers, payload: payload.to_json}
|
17
|
+
execute(opts)
|
18
|
+
end
|
19
|
+
end
|
@@ -13,6 +13,7 @@ class Morpheus::Cli::CatalogItemTypesCommand
|
|
13
13
|
set_command_description "Self Service: View and manage catalog item types"
|
14
14
|
|
15
15
|
register_subcommands :list, :get, :add, :update, :remove
|
16
|
+
register_subcommands({:'update-logo' => :update_logo})
|
16
17
|
|
17
18
|
def connect(opts)
|
18
19
|
@api_client = establish_remote_appliance_connection(opts)
|
@@ -222,6 +223,7 @@ EOT
|
|
222
223
|
def add(args)
|
223
224
|
options = {}
|
224
225
|
params = {}
|
226
|
+
logo_file = nil
|
225
227
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
226
228
|
opts.banner = subcommand_usage("[name] [options]")
|
227
229
|
# opts.on('-t', '--type [instance|blueprint|workflow]', "Item Type, default is instance.") do |val|
|
@@ -229,6 +231,19 @@ EOT
|
|
229
231
|
# options[:options]['type'] = val.to_s.downcase
|
230
232
|
# end
|
231
233
|
build_option_type_options(opts, options, add_catalog_item_type_option_types)
|
234
|
+
opts.on('--logo FILE', String, "Upload a custom logo icon") do |val|
|
235
|
+
filename = val
|
236
|
+
logo_file = nil
|
237
|
+
if filename == 'null'
|
238
|
+
filename = 'null' # clear it
|
239
|
+
else
|
240
|
+
filename = File.expand_path(filename)
|
241
|
+
if !File.exists?(filename)
|
242
|
+
raise_command_error "File not found: #{filename}"
|
243
|
+
end
|
244
|
+
logo_file = File.new(filename, 'rb')
|
245
|
+
end
|
246
|
+
end
|
232
247
|
opts.on('--config-file FILE', String, "Config from a local JSON or YAML file") do |val|
|
233
248
|
options[:config_file] = val.to_s
|
234
249
|
file_content = nil
|
@@ -330,6 +345,16 @@ EOT
|
|
330
345
|
return 0, nil
|
331
346
|
end
|
332
347
|
json_response = @catalog_item_types_interface.create(payload)
|
348
|
+
if json_response['success']
|
349
|
+
if logo_file
|
350
|
+
begin
|
351
|
+
@catalog_item_types_interface.update_logo(json_response['catalogItemType']['id'], logo_file)
|
352
|
+
rescue RestClient::Exception => e
|
353
|
+
print_red_alert "Failed to save logo!"
|
354
|
+
print_rest_exception(e, options)
|
355
|
+
end
|
356
|
+
end
|
357
|
+
end
|
333
358
|
catalog_item_type = json_response[catalog_item_type_object_key]
|
334
359
|
render_response(json_response, options, catalog_item_type_object_key) do
|
335
360
|
print_green_success "Added catalog item type #{catalog_item_type['name']}"
|
@@ -342,9 +367,23 @@ EOT
|
|
342
367
|
options = {}
|
343
368
|
params = {}
|
344
369
|
payload = {}
|
370
|
+
logo_file = nil
|
345
371
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
346
372
|
opts.banner = subcommand_usage("[type] [options]")
|
347
373
|
build_option_type_options(opts, options, update_catalog_item_type_option_types)
|
374
|
+
opts.on('--logo FILE', String, "Upload a custom logo icon") do |val|
|
375
|
+
filename = val
|
376
|
+
logo_file = nil
|
377
|
+
if filename == 'null'
|
378
|
+
filename = 'null' # clear it
|
379
|
+
else
|
380
|
+
filename = File.expand_path(filename)
|
381
|
+
if !File.exists?(filename)
|
382
|
+
raise_command_error "File not found: #{filename}"
|
383
|
+
end
|
384
|
+
logo_file = File.new(filename, 'rb')
|
385
|
+
end
|
386
|
+
end
|
348
387
|
opts.on('--config-file FILE', String, "Config from a local JSON or YAML file") do |val|
|
349
388
|
options[:config_file] = val.to_s
|
350
389
|
file_content = nil
|
@@ -445,6 +484,16 @@ EOT
|
|
445
484
|
return
|
446
485
|
end
|
447
486
|
json_response = @catalog_item_types_interface.update(catalog_item_type['id'], payload)
|
487
|
+
if json_response['success']
|
488
|
+
if logo_file
|
489
|
+
begin
|
490
|
+
@catalog_item_types_interface.update_logo(json_response['catalogItemType']['id'], logo_file)
|
491
|
+
rescue RestClient::Exception => e
|
492
|
+
print_red_alert "Failed to save logo!"
|
493
|
+
print_rest_exception(e, options)
|
494
|
+
end
|
495
|
+
end
|
496
|
+
end
|
448
497
|
catalog_item_type = json_response[catalog_item_type_object_key]
|
449
498
|
render_response(json_response, options, catalog_item_type_object_key) do
|
450
499
|
print_green_success "Updated catalog item type #{catalog_item_type['name']}"
|
@@ -453,6 +502,45 @@ EOT
|
|
453
502
|
return 0, nil
|
454
503
|
end
|
455
504
|
|
505
|
+
def update_logo(args)
|
506
|
+
options = {}
|
507
|
+
params = {}
|
508
|
+
filename = nil
|
509
|
+
optparse = Morpheus::Cli::OptionParser.new do|opts|
|
510
|
+
opts.banner = subcommand_usage("[type] [file]")
|
511
|
+
build_common_options(opts, options, [:json, :dry_run, :remote])
|
512
|
+
opts.footer = "Update the logo for a catalog item type." + "\n" +
|
513
|
+
"[type] is required. This is the name or id of a catalog item type." + "\n" +
|
514
|
+
"[file] is required. This is the path of the logo file"
|
515
|
+
end
|
516
|
+
optparse.parse!(args)
|
517
|
+
verify_args!(args:args, optparse:optparse, count:2)
|
518
|
+
connect(options)
|
519
|
+
catalog_item_type = find_catalog_item_type_by_name_or_id(args[0])
|
520
|
+
return 1 if catalog_item_type.nil?
|
521
|
+
filename = args[1]
|
522
|
+
logo_file = nil
|
523
|
+
if filename == 'null'
|
524
|
+
filename = 'null' # clear it
|
525
|
+
else
|
526
|
+
filename = File.expand_path(filename)
|
527
|
+
if !File.exists?(filename)
|
528
|
+
raise_command_error "File not found: #{filename}"
|
529
|
+
end
|
530
|
+
logo_file = File.new(filename, 'rb')
|
531
|
+
end
|
532
|
+
@catalog_item_types_interface.setopts(options)
|
533
|
+
if options[:dry_run]
|
534
|
+
print_dry_run @catalog_item_types_interface.dry.update_logo(catalog_item_type['id'], logo_file)
|
535
|
+
return
|
536
|
+
end
|
537
|
+
json_response = @catalog_item_types_interface.update_logo(catalog_item_type['id'], logo_file)
|
538
|
+
render_response(json_response, options, catalog_item_type_object_key) do
|
539
|
+
print_green_success "Updated catalog item type #{catalog_item_type['name']} logo"
|
540
|
+
return _get(catalog_item_type["id"], {}, options)
|
541
|
+
end
|
542
|
+
end
|
543
|
+
|
456
544
|
def remove(args)
|
457
545
|
options = {}
|
458
546
|
params = {}
|
@@ -547,11 +547,7 @@ class Morpheus::Cli::Clusters
|
|
547
547
|
available_layouts = layouts_for_dropdown(cloud['id'], cluster_type['id'])
|
548
548
|
|
549
549
|
if !available_layouts.empty?
|
550
|
-
|
551
|
-
layout_id = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'layout', 'type' => 'select', 'fieldLabel' => 'Layout', 'selectOptions' => available_layouts, 'required' => true, 'description' => 'Select Layout.'}],options[:options],@api_client,{})['layout']
|
552
|
-
else
|
553
|
-
layout_id = available_layouts.first['id']
|
554
|
-
end
|
550
|
+
layout_id = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'layout', 'type' => 'select', 'fieldLabel' => 'Layout', 'selectOptions' => available_layouts, 'required' => true, 'description' => 'Select Layout.'}],options[:options],@api_client,{})['layout']
|
555
551
|
layout = find_layout_by_name_or_id(layout_id)
|
556
552
|
end
|
557
553
|
end
|
@@ -560,17 +556,25 @@ class Morpheus::Cli::Clusters
|
|
560
556
|
|
561
557
|
# Provision Type
|
562
558
|
provision_type = (layout && layout['provisionType'] ? layout['provisionType'] : nil) || get_provision_type_for_zone_type(cloud['zoneType']['id'])
|
559
|
+
provision_type = @provision_types_interface.get(provision_type['id'])['provisionType'] if !provision_type.nil?
|
563
560
|
|
564
561
|
api_params = {zoneId: cloud['id'], siteId: group['id'], layoutId: layout['id'], groupTypeId: cluster_type['id'], provisionType: provision_type['code'], provisionTypeId: provision_type['id']}
|
565
562
|
|
566
563
|
# Controller type
|
567
|
-
server_types = @server_types_interface.list({
|
564
|
+
server_types = @server_types_interface.list({computeTypeId: cluster_type['controllerTypes'].first['id'], zoneTypeId: cloud['zoneType']['id'], useZoneProvisionTypes: true})['serverTypes'].reject {|it| it['provisionType']['code'] == 'manual'}
|
568
565
|
controller_provision_type = nil
|
569
566
|
resource_pool = nil
|
570
567
|
|
571
568
|
if !server_types.empty?
|
572
569
|
controller_type = server_types.first
|
573
|
-
|
570
|
+
|
571
|
+
if controller_type['provisionType']
|
572
|
+
if provision_type && provision_type['id'] == controller_type['provisionType']['id']
|
573
|
+
controller_provision_type = provision_type
|
574
|
+
else
|
575
|
+
controller_provision_type = @provision_types_interface.get(controller_type['provisionType']['id'])['provisionType'] rescue nil
|
576
|
+
end
|
577
|
+
end
|
574
578
|
|
575
579
|
if controller_provision_type && resource_pool = prompt_resource_pool(group, cloud, nil, controller_provision_type, options)
|
576
580
|
server_payload['config']['resourcePoolId'] = resource_pool['id']
|
@@ -585,21 +589,23 @@ class Morpheus::Cli::Clusters
|
|
585
589
|
service_plan = prompt_service_plan(api_params, options)
|
586
590
|
|
587
591
|
if service_plan
|
588
|
-
server_payload['plan'] = {'id' => service_plan['id'], 'code' => service_plan['code'], 'options' => prompt_service_plan_options(service_plan, options)}
|
592
|
+
server_payload['plan'] = {'id' => service_plan['id'], 'code' => service_plan['code'], 'options' => prompt_service_plan_options(service_plan, provision_type, options)}
|
589
593
|
api_params['planId'] = service_plan['id']
|
590
594
|
end
|
591
595
|
|
592
596
|
# Multi-disk / prompt for volumes
|
593
|
-
|
594
|
-
|
595
|
-
|
596
|
-
|
597
|
+
if provision_type['hasVolumes']
|
598
|
+
volumes = options[:volumes] || prompt_volumes(service_plan, options.merge({'defaultAddFirstDataVolume': true}), @api_client, api_params)
|
599
|
+
if !volumes.empty?
|
600
|
+
server_payload['volumes'] = volumes
|
601
|
+
end
|
597
602
|
end
|
598
603
|
|
599
604
|
# Options / Custom Config
|
600
605
|
option_type_list =
|
601
|
-
((controller_type['optionTypes'].reject { |type| !type['enabled'] || type['fieldComponent'] } rescue []) +
|
602
|
-
|
606
|
+
((controller_type.nil? ? [] : controller_type['optionTypes'].reject { |type| !type['enabled'] || type['fieldComponent'] } rescue []) +
|
607
|
+
layout['optionTypes'] +
|
608
|
+
(cluster_type['optionTypes'].reject { |type| !type['enabled'] || !type['creatable'] || type['fieldComponent'] } rescue []))
|
603
609
|
|
604
610
|
# KLUDGE: google zone required for network selection
|
605
611
|
if option_type = option_type_list.find {|type| type['code'] == 'computeServerType.googleLinux.googleZoneId'}
|
@@ -625,11 +631,13 @@ class Morpheus::Cli::Clusters
|
|
625
631
|
cluster_payload.deep_merge!(Morpheus::Cli::OptionTypes.prompt(load_layout_options(cluster_payload), options[:options], @api_client, api_params, options[:no_prompt], true))
|
626
632
|
|
627
633
|
# Server options
|
628
|
-
server_payload.deep_merge!(Morpheus::Cli::OptionTypes.prompt(option_type_list, options[:options], @api_client, api_params, options[:no_prompt], true))
|
634
|
+
server_payload.deep_merge!(Morpheus::Cli::OptionTypes.prompt(option_type_list, options[:options].deep_merge({:context_map => {'domain' => ''}}), @api_client, api_params, options[:no_prompt], true))
|
629
635
|
|
630
636
|
# Worker count
|
631
|
-
|
632
|
-
|
637
|
+
if !['manual', 'external'].include?(provision_type['code'])
|
638
|
+
default_node_count = layout['computeServers'] ? (layout['computeServers'].find {|it| it['nodeType'] == 'worker'} || {'nodeCount' => 3})['nodeCount'] : 3
|
639
|
+
server_payload['config']['nodeCount'] = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => "config.nodeCount", 'type' => 'number', 'fieldLabel' => "#{['docker-cluster', 'kvm-cluster'].include?(cluster_type['code']) ? 'Host' : 'Worker'} Count", 'required' => true, 'defaultValue' => default_node_count > 0 ? default_node_count : 3}], options[:options], @api_client, api_params, options[:no_prompt])['config']['nodeCount']
|
640
|
+
end
|
633
641
|
|
634
642
|
# Create User
|
635
643
|
if !options[:createUser].nil?
|
@@ -657,10 +665,12 @@ class Morpheus::Cli::Clusters
|
|
657
665
|
server_payload['hostname'] = options[:hostname] || Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'hostname', 'fieldLabel' => 'Hostname', 'type' => 'text', 'required' => true, 'description' => 'Hostname', 'defaultValue' => resourceName}], options[:options], @api_client, api_params)['hostname']
|
658
666
|
|
659
667
|
# Workflow / Automation
|
660
|
-
|
668
|
+
if provision_type['code'] != 'manual' && controller_type && controller_type['hasAutomation']
|
669
|
+
task_set_id = options[:taskSetId] || Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'taskSet', 'fieldLabel' => 'Workflow', 'type' => 'select', 'required' => false, 'optionSource' => 'taskSets'}], options[:options], @api_client, api_params.merge({'phase' => 'postProvision'}))['taskSet']
|
661
670
|
|
662
|
-
|
663
|
-
|
671
|
+
if !task_set_id.nil?
|
672
|
+
server_payload['taskSet'] = {'id' => task_set_id}
|
673
|
+
end
|
664
674
|
end
|
665
675
|
|
666
676
|
cluster_payload['server'] = server_payload
|
@@ -1172,7 +1182,7 @@ class Morpheus::Cli::Clusters
|
|
1172
1182
|
service_plan = prompt_service_plan({zoneId: cloud_id, siteId: cluster['site']['id'], provisionTypeId: server_type['provisionType']['id'], groupTypeId: cluster_type['id'], }, options)
|
1173
1183
|
|
1174
1184
|
if service_plan
|
1175
|
-
server_payload['plan'] = {'code' => service_plan['code'], 'options' => prompt_service_plan_options(service_plan, options)}
|
1185
|
+
server_payload['plan'] = {'code' => service_plan['code'], 'options' => prompt_service_plan_options(service_plan, nil, options)}
|
1176
1186
|
end
|
1177
1187
|
|
1178
1188
|
if resource_pool = prompt_resource_pool(cluster, cloud, service_plan, server_type['provisionType'], options)
|
@@ -3713,34 +3723,37 @@ class Morpheus::Cli::Clusters
|
|
3713
3723
|
service_plan
|
3714
3724
|
end
|
3715
3725
|
|
3716
|
-
def prompt_service_plan_options(service_plan, options)
|
3726
|
+
def prompt_service_plan_options(service_plan, provision_type, options)
|
3717
3727
|
plan_options = {}
|
3718
|
-
|
3719
|
-
|
3720
|
-
if
|
3721
|
-
|
3722
|
-
|
3723
|
-
|
3724
|
-
|
3725
|
-
|
3728
|
+
hide_custom_options = provision_type && provision_type['code'] == 'manual'
|
3729
|
+
|
3730
|
+
if !hide_custom_options
|
3731
|
+
# custom max memory
|
3732
|
+
if service_plan['customMaxMemory']
|
3733
|
+
if !options[:maxMemory]
|
3734
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'maxMemory', 'type' => 'number', 'fieldLabel' => 'Max Memory (MB)', 'required' => false, 'description' => 'This will override any memory requirement set on the virtual image', 'defaultValue' => service_plan['maxMemory'] ? service_plan['maxMemory'] / (1024 * 1024) : 10 }], options[:options])
|
3735
|
+
plan_options['maxMemory'] = v_prompt['maxMemory'] * 1024 * 1024 if v_prompt['maxMemory']
|
3736
|
+
else
|
3737
|
+
plan_options['maxMemory'] = options[:maxMemory]
|
3738
|
+
end
|
3726
3739
|
end
|
3727
|
-
end
|
3728
3740
|
|
3729
|
-
|
3730
|
-
|
3731
|
-
|
3732
|
-
|
3733
|
-
|
3734
|
-
|
3735
|
-
|
3736
|
-
|
3737
|
-
|
3738
|
-
|
3739
|
-
|
3740
|
-
|
3741
|
-
|
3742
|
-
|
3743
|
-
|
3741
|
+
# custom cores: max cpu, max cores, cores per socket
|
3742
|
+
if service_plan['customCores']
|
3743
|
+
if options[:cpuCount].empty?
|
3744
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'cpuCount', 'type' => 'number', 'fieldLabel' => 'CPU Count', 'required' => false, 'description' => 'Set CPU Count', 'defaultValue' => service_plan['maxCpu'] ? service_plan['maxCpu'] : 1 }], options[:options])
|
3745
|
+
plan_options['cpuCount'] = v_prompt['cpuCount'] if v_prompt['cpuCount']
|
3746
|
+
else
|
3747
|
+
plan_options['cpuCount']
|
3748
|
+
end
|
3749
|
+
if options[:coreCount].empty?
|
3750
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'coreCount', 'type' => 'number', 'fieldLabel' => 'Core Count', 'required' => false, 'description' => 'Set Core Count', 'defaultValue' => service_plan['maxCores'] ? service_plan['maxCores'] : 1 }], options[:options])
|
3751
|
+
plan_options['coreCount'] = v_prompt['coreCount'] if v_prompt['coreCount']
|
3752
|
+
end
|
3753
|
+
if options[:coresPerSocket].empty? && service_plan['coresPerSocket']
|
3754
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'coresPerSocket', 'type' => 'number', 'fieldLabel' => 'Cores Per Socket', 'required' => false, 'description' => 'Set Core Per Socket', 'defaultValue' => service_plan['coresPerSocket']}], options[:options])
|
3755
|
+
plan_options['coresPerSocket'] = v_prompt['coresPerSocket'] if v_prompt['coresPerSocket']
|
3756
|
+
end
|
3744
3757
|
end
|
3745
3758
|
end
|
3746
3759
|
plan_options
|
@@ -878,6 +878,12 @@ class Morpheus::Cli::Hosts
|
|
878
878
|
payload['volumes'] = volumes
|
879
879
|
end
|
880
880
|
|
881
|
+
# plan customizations
|
882
|
+
plan_opts = prompt_service_plan_options(service_plan, options, @api_client, {})
|
883
|
+
if plan_opts && !plan_opts.empty?
|
884
|
+
payload['servicePlanOptions'] = plan_opts
|
885
|
+
end
|
886
|
+
|
881
887
|
# prompt for network interfaces (if supported)
|
882
888
|
if server_type["provisionType"] && server_type["provisionType"]["id"] && server_type["provisionType"]["hasNetworks"]
|
883
889
|
begin
|
@@ -1252,6 +1258,12 @@ class Morpheus::Cli::Hosts
|
|
1252
1258
|
payload[:volumes] = volumes
|
1253
1259
|
end
|
1254
1260
|
|
1261
|
+
# plan customizations
|
1262
|
+
plan_opts = prompt_service_plan_options(service_plan, options, @api_client, {}, server)
|
1263
|
+
if plan_opts && !plan_opts.empty?
|
1264
|
+
payload['servicePlanOptions'] = plan_opts
|
1265
|
+
end
|
1266
|
+
|
1255
1267
|
# todo: reconfigure networks
|
1256
1268
|
# need to get provision_type_id for network info
|
1257
1269
|
# prompt for network interfaces (if supported)
|