morpheus-cli 4.2.14 → 4.2.19
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/README.md +8 -6
- data/lib/morpheus/api/api_client.rb +32 -14
- data/lib/morpheus/api/auth_interface.rb +4 -2
- data/lib/morpheus/api/backup_jobs_interface.rb +9 -0
- data/lib/morpheus/api/backups_interface.rb +16 -0
- data/lib/morpheus/api/deploy_interface.rb +25 -56
- data/lib/morpheus/api/deployments_interface.rb +44 -55
- data/lib/morpheus/api/doc_interface.rb +57 -0
- data/lib/morpheus/api/instances_interface.rb +5 -0
- data/lib/morpheus/api/rest_interface.rb +40 -0
- data/lib/morpheus/api/user_sources_interface.rb +0 -15
- data/lib/morpheus/api/users_interface.rb +2 -3
- data/lib/morpheus/benchmarking.rb +2 -2
- data/lib/morpheus/cli.rb +4 -1
- data/lib/morpheus/cli/access_token_command.rb +27 -10
- data/lib/morpheus/cli/apps.rb +21 -15
- data/lib/morpheus/cli/backup_jobs_command.rb +276 -0
- data/lib/morpheus/cli/backups_command.rb +271 -0
- data/lib/morpheus/cli/blueprints_command.rb +27 -61
- data/lib/morpheus/cli/boot_scripts_command.rb +1 -1
- data/lib/morpheus/cli/cli_command.rb +183 -45
- data/lib/morpheus/cli/cli_registry.rb +3 -0
- data/lib/morpheus/cli/clouds.rb +7 -10
- data/lib/morpheus/cli/clusters.rb +0 -18
- data/lib/morpheus/cli/commands/standard/benchmark_command.rb +23 -20
- data/lib/morpheus/cli/commands/standard/man_command.rb +1 -1
- data/lib/morpheus/cli/credentials.rb +13 -9
- data/lib/morpheus/cli/deploy.rb +374 -0
- data/lib/morpheus/cli/deployments.rb +521 -197
- data/lib/morpheus/cli/deploys.rb +271 -126
- data/lib/morpheus/cli/doc.rb +182 -0
- data/lib/morpheus/cli/error_handler.rb +23 -8
- data/lib/morpheus/cli/errors.rb +3 -2
- data/lib/morpheus/cli/image_builder_command.rb +2 -2
- data/lib/morpheus/cli/instances.rb +136 -17
- data/lib/morpheus/cli/invoices_command.rb +339 -225
- data/lib/morpheus/cli/jobs_command.rb +2 -2
- data/lib/morpheus/cli/library_layouts_command.rb +1 -1
- data/lib/morpheus/cli/library_option_lists_command.rb +61 -125
- data/lib/morpheus/cli/library_option_types_command.rb +32 -37
- data/lib/morpheus/cli/login.rb +9 -3
- data/lib/morpheus/cli/mixins/accounts_helper.rb +158 -100
- data/lib/morpheus/cli/mixins/backups_helper.rb +115 -0
- data/lib/morpheus/cli/mixins/deployments_helper.rb +135 -0
- data/lib/morpheus/cli/mixins/library_helper.rb +32 -0
- data/lib/morpheus/cli/mixins/option_source_helper.rb +1 -1
- data/lib/morpheus/cli/mixins/print_helper.rb +149 -84
- data/lib/morpheus/cli/mixins/provisioning_helper.rb +2 -2
- data/lib/morpheus/cli/mixins/whoami_helper.rb +19 -6
- data/lib/morpheus/cli/network_routers_command.rb +1 -1
- data/lib/morpheus/cli/option_parser.rb +48 -5
- data/lib/morpheus/cli/option_types.rb +46 -10
- data/lib/morpheus/cli/price_sets_command.rb +1 -1
- data/lib/morpheus/cli/projects_command.rb +7 -7
- data/lib/morpheus/cli/remote.rb +3 -2
- data/lib/morpheus/cli/roles.rb +49 -92
- data/lib/morpheus/cli/security_groups.rb +7 -1
- data/lib/morpheus/cli/service_plans_command.rb +10 -10
- data/lib/morpheus/cli/setup.rb +1 -1
- data/lib/morpheus/cli/shell.rb +7 -6
- data/lib/morpheus/cli/subnets_command.rb +1 -1
- data/lib/morpheus/cli/tasks.rb +24 -10
- data/lib/morpheus/cli/tenants_command.rb +133 -163
- data/lib/morpheus/cli/user_groups_command.rb +20 -65
- data/lib/morpheus/cli/user_settings_command.rb +115 -13
- data/lib/morpheus/cli/user_sources_command.rb +57 -24
- data/lib/morpheus/cli/users.rb +210 -186
- data/lib/morpheus/cli/version.rb +1 -1
- data/lib/morpheus/cli/whitelabel_settings_command.rb +29 -5
- data/lib/morpheus/cli/whoami.rb +113 -6
- data/lib/morpheus/cli/workflows.rb +11 -8
- data/lib/morpheus/ext/hash.rb +21 -0
- data/lib/morpheus/formatters.rb +7 -19
- data/lib/morpheus/terminal.rb +1 -0
- metadata +12 -3
- data/lib/morpheus/cli/auth_command.rb +0 -105
data/lib/morpheus/cli/users.rb
CHANGED
@@ -16,9 +16,6 @@ class Morpheus::Cli::Users
|
|
16
16
|
alias_subcommand :details, :get
|
17
17
|
set_default_subcommand :list
|
18
18
|
|
19
|
-
#todo: TOO_SIMPL_REGEX = //i
|
20
|
-
# TOO_SIMPLE_ERROR = "Password too simple. Password must contain at least one uppercase letter, one lowercase letter, a number, and a symbol."
|
21
|
-
|
22
19
|
def initialize()
|
23
20
|
# @appliance_name, @appliance_url = Morpheus::Cli::Remote.active_appliance
|
24
21
|
end
|
@@ -35,57 +32,74 @@ class Morpheus::Cli::Users
|
|
35
32
|
end
|
36
33
|
|
37
34
|
def list(args)
|
35
|
+
params = {}
|
38
36
|
options = {}
|
39
37
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
40
38
|
opts.banner = subcommand_usage()
|
41
|
-
|
39
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
40
|
+
options[:global] = true
|
41
|
+
end
|
42
|
+
opts.on('--role AUTHORITY', String, "Role Name (authority)") do |val|
|
43
|
+
params['role'] ||= []
|
44
|
+
val.split(",").collect {|s| s.strip }.select {|s| !s.to_s.empty? }.each do |v|
|
45
|
+
params['role'] << v
|
46
|
+
end
|
47
|
+
end
|
48
|
+
opts.on('--role-id ID', String, "Role ID") do |val|
|
49
|
+
params['roleId'] ||= []
|
50
|
+
val.split(",").collect {|s| s.strip }.select {|s| !s.to_s.empty? }.each do |v|
|
51
|
+
params['roleId'] << v
|
52
|
+
end
|
53
|
+
end
|
54
|
+
build_standard_list_options(opts, options, [:account])
|
42
55
|
opts.footer = "List users."
|
43
56
|
end
|
44
57
|
optparse.parse!(args)
|
58
|
+
# verify_args!(args:args, optparse:optparse, count:0)
|
59
|
+
options[:phrase] = args.join(" ") if args.count > 0
|
45
60
|
connect(options)
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
end
|
58
|
-
json_response = @users_interface.list(account_id, params)
|
59
|
-
render_result = render_with_format(json_response, options, 'users')
|
60
|
-
return 0 if render_result
|
61
|
+
account = find_account_from_options(options)
|
62
|
+
account_id = account ? account['id'] : nil
|
63
|
+
params['global'] = true if options[:global]
|
64
|
+
params.merge!(parse_list_options(options))
|
65
|
+
@users_interface.setopts(options)
|
66
|
+
if options[:dry_run]
|
67
|
+
print_dry_run @users_interface.dry.list(account_id, params)
|
68
|
+
return 0, nil
|
69
|
+
end
|
70
|
+
json_response = @users_interface.list(account_id, params)
|
71
|
+
render_response(json_response, options, "users") do
|
61
72
|
users = json_response['users']
|
62
|
-
|
63
73
|
title = "Morpheus Users"
|
64
74
|
subtitles = []
|
65
75
|
if account
|
66
|
-
subtitles << "
|
76
|
+
subtitles << "Tenant: #{account['name']}".strip
|
77
|
+
end
|
78
|
+
if params['global'] && json_response['global']
|
79
|
+
subtitles << "(All Tenants)"
|
67
80
|
end
|
68
81
|
subtitles += parse_list_subtitles(options)
|
69
82
|
print_h1 title, subtitles, options
|
70
83
|
if users.empty?
|
71
84
|
print cyan,"No users found.",reset,"\n"
|
72
85
|
else
|
73
|
-
|
86
|
+
print cyan
|
87
|
+
print as_pretty_table(users, list_user_column_definitions, options)
|
74
88
|
print_results_pagination(json_response)
|
75
89
|
end
|
76
90
|
print reset,"\n"
|
77
|
-
return 0
|
78
|
-
|
79
|
-
rescue RestClient::Exception => e
|
80
|
-
print_rest_exception(e, options)
|
81
|
-
return 1
|
82
91
|
end
|
92
|
+
return 0, nil
|
83
93
|
end
|
84
94
|
|
85
95
|
def count(args)
|
96
|
+
params = {}
|
86
97
|
options = {}
|
87
98
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
88
99
|
opts.banner = subcommand_usage("[options]")
|
100
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
101
|
+
options[:global] = true
|
102
|
+
end
|
89
103
|
build_common_options(opts, options, [:account, :query, :remote, :dry_run])
|
90
104
|
opts.footer = "Get the number of users."
|
91
105
|
end
|
@@ -94,7 +108,7 @@ class Morpheus::Cli::Users
|
|
94
108
|
begin
|
95
109
|
account = find_account_from_options(options)
|
96
110
|
account_id = account ? account['id'] : nil
|
97
|
-
params =
|
111
|
+
params['global'] = true if options[:global]
|
98
112
|
params.merge!(parse_list_options(options))
|
99
113
|
@users_interface.setopts(options)
|
100
114
|
if options[:dry_run]
|
@@ -118,7 +132,10 @@ class Morpheus::Cli::Users
|
|
118
132
|
options = {}
|
119
133
|
params = {}
|
120
134
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
121
|
-
opts.banner = subcommand_usage("[
|
135
|
+
opts.banner = subcommand_usage("[user]")
|
136
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
137
|
+
options[:global] = true
|
138
|
+
end
|
122
139
|
opts.on('-p','--permissions', "Display Permissions") do |val|
|
123
140
|
options[:include_features_access] = true
|
124
141
|
params['includeAccess'] = true
|
@@ -155,82 +172,51 @@ class Morpheus::Cli::Users
|
|
155
172
|
opts.on('-i', '--include-none-access', "Include Items with 'None' Access in Access List") do
|
156
173
|
options[:display_none_access] = true
|
157
174
|
end
|
158
|
-
|
159
|
-
opts.footer =
|
160
|
-
|
175
|
+
build_standard_get_options(opts, options, [:account])
|
176
|
+
opts.footer = <<-EOT
|
177
|
+
Get details about a user.
|
178
|
+
[user] is required. This is the username or id of a user. Supports 1-N arguments.
|
179
|
+
EOT
|
161
180
|
end
|
162
181
|
optparse.parse!(args)
|
163
|
-
|
164
|
-
if args.count < 1
|
165
|
-
puts optparse
|
166
|
-
return 1
|
167
|
-
end
|
168
|
-
|
182
|
+
verify_args!(args:args, optparse:optparse, min:1)
|
169
183
|
connect(options)
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
if args[0].to_s =~ /\A\d{1,}\Z/
|
176
|
-
print_dry_run @users_interface.dry.get(account_id, args[0].to_i, params)
|
177
|
-
else
|
178
|
-
print_dry_run @users_interface.dry.get(account_id, {username: args[0]}, params)
|
179
|
-
end
|
180
|
-
return
|
181
|
-
end
|
184
|
+
id_list = parse_id_list(args)
|
185
|
+
return run_command_for_each_arg(id_list) do |arg|
|
186
|
+
_get(arg, params, options)
|
187
|
+
end
|
188
|
+
end
|
182
189
|
|
190
|
+
def _get(id, params, options={})
|
191
|
+
args = [id] # heh
|
192
|
+
account = find_account_from_options(options)
|
193
|
+
account_id = account ? account['id'] : nil
|
194
|
+
params['global'] = true if options[:global]
|
195
|
+
@users_interface.setopts(options)
|
196
|
+
if options[:dry_run]
|
183
197
|
if args[0].to_s =~ /\A\d{1,}\Z/
|
184
|
-
|
198
|
+
print_dry_run @users_interface.dry.get(account_id, args[0].to_i, params)
|
185
199
|
else
|
186
|
-
|
187
|
-
|
188
|
-
if user.nil?
|
189
|
-
print_red_alert "User #{args[0]} not found"
|
190
|
-
exit 1
|
191
|
-
end
|
192
|
-
user_id = user['id']
|
193
|
-
end
|
194
|
-
|
195
|
-
user = @users_interface.get(account_id, user_id, params)['user']
|
196
|
-
|
197
|
-
if user.nil?
|
198
|
-
print_red_alert "User #{args[0]} not found"
|
199
|
-
exit 1
|
200
|
+
print_dry_run @users_interface.dry.list(account_id, params.merge({username: args[0]}))
|
200
201
|
end
|
202
|
+
return
|
203
|
+
end
|
201
204
|
|
205
|
+
if args[0].to_s =~ /\A\d{1,}\Z/
|
206
|
+
user_id = args[0].to_i
|
207
|
+
else
|
208
|
+
user = find_user_by_username(account_id, args[0], params)
|
209
|
+
return 1 if user.nil?
|
210
|
+
user_id = user['id']
|
211
|
+
end
|
212
|
+
# always get by id, index does not return 'access'
|
213
|
+
json_response = @users_interface.get(account_id, user_id, params)
|
214
|
+
user = json_response['user']
|
215
|
+
render_response(json_response, options, "user") do
|
202
216
|
is_tenant_account = current_account['id'] != user['account']['id']
|
203
|
-
|
204
|
-
json_response = {'user' => user}
|
205
|
-
|
206
|
-
if options[:json]
|
207
|
-
puts as_json(json_response, options, "user")
|
208
|
-
return 0
|
209
|
-
elsif options[:yaml]
|
210
|
-
puts as_yaml(json_response, options, "user")
|
211
|
-
return 0
|
212
|
-
elsif options[:csv]
|
213
|
-
puts records_as_csv([user], options)
|
214
|
-
return 0
|
215
|
-
end
|
216
|
-
|
217
217
|
print_h1 "User Details", options
|
218
218
|
print cyan
|
219
|
-
|
220
|
-
"ID" => 'id',
|
221
|
-
"Account" => lambda {|it| it['account'] ? it['account']['name'] : '' },
|
222
|
-
"First Name" => 'firstName',
|
223
|
-
"Last Name" => 'lastName',
|
224
|
-
# "Name" => 'displayName',
|
225
|
-
#"Name" => lambda {|it| it['firstName'] ? it['displayName'] : '' },
|
226
|
-
"Username" => 'username',
|
227
|
-
"Email" => 'email',
|
228
|
-
"Notifications" => lambda {|it| it['receiveNotifications'].nil? ? '' : format_boolean(it['receiveNotifications']) },
|
229
|
-
"Role" => lambda {|it| format_user_role_names(it) },
|
230
|
-
"Created" => lambda {|it| format_local_dt(it['dateCreated']) },
|
231
|
-
"Updated" => lambda {|it| format_local_dt(it['lastUpdated']) }
|
232
|
-
}
|
233
|
-
print_description_list(description_cols, user)
|
219
|
+
print_description_list(user_column_definitions, user)
|
234
220
|
|
235
221
|
# backward compatibility
|
236
222
|
if user['access'].nil? && options[:include_features_access]
|
@@ -288,24 +274,25 @@ class Morpheus::Cli::Users
|
|
288
274
|
end
|
289
275
|
end
|
290
276
|
end
|
291
|
-
print cyan
|
292
277
|
print reset,"\n"
|
293
|
-
rescue RestClient::Exception => e
|
294
|
-
print_rest_exception(e, options)
|
295
|
-
return 1
|
296
278
|
end
|
279
|
+
return 0
|
297
280
|
end
|
298
281
|
|
299
282
|
def permissions(args)
|
283
|
+
params = {}
|
300
284
|
options = {}
|
301
285
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
302
|
-
opts.banner = subcommand_usage("[
|
286
|
+
opts.banner = subcommand_usage("[user]")
|
287
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
288
|
+
options[:global] = true
|
289
|
+
end
|
303
290
|
build_common_options(opts, options, [:account, :json, :yaml, :csv, :fields, :dry_run, :remote])
|
304
291
|
opts.on('-i', '--include-none-access', "Include Items with 'None' Access in Access List") do
|
305
292
|
options[:display_none_access] = true
|
306
293
|
end
|
307
294
|
opts.footer = "Display Access for a user." + "\n" +
|
308
|
-
"[
|
295
|
+
"[user] is required. This is the username or id of a user."
|
309
296
|
end
|
310
297
|
optparse.parse!(args)
|
311
298
|
verify_args!(args:args, optparse:optparse, count:1)
|
@@ -314,7 +301,8 @@ class Morpheus::Cli::Users
|
|
314
301
|
begin
|
315
302
|
account = find_account_from_options(options)
|
316
303
|
account_id = account ? account['id'] : nil
|
317
|
-
|
304
|
+
params['global'] = true if options[:global]
|
305
|
+
user = find_user_by_username_or_id(account_id, args[0], params)
|
318
306
|
return 1 if user.nil?
|
319
307
|
@users_interface.setopts(options)
|
320
308
|
if options[:dry_run]
|
@@ -414,10 +402,11 @@ class Morpheus::Cli::Users
|
|
414
402
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
415
403
|
opts.banner = subcommand_usage("[username] [email] [first] [last] [options]")
|
416
404
|
build_option_type_options(opts, options, add_user_option_types)
|
405
|
+
build_option_type_options(opts, options, add_user_advanced_option_types)
|
417
406
|
build_common_options(opts, options, [:account, :options, :payload, :json, :dry_run])
|
418
407
|
opts.footer = <<-EOT
|
419
408
|
Create a new user.
|
420
|
-
[
|
409
|
+
[user] is required. Username of the new user
|
421
410
|
[email] is required. Email address
|
422
411
|
[first] is optional. First Name
|
423
412
|
[last] is optional. Last Name
|
@@ -429,6 +418,9 @@ EOT
|
|
429
418
|
options[:options]['email'] = args[1] if args[1]
|
430
419
|
options[:options]['firstName'] = args[2] if args[2]
|
431
420
|
options[:options]['lastName'] = args[3] if args[3]
|
421
|
+
if options[:options]['password']
|
422
|
+
options[:options]['passwordConfirmation'] = options[:options]['password']
|
423
|
+
end
|
432
424
|
connect(options)
|
433
425
|
begin
|
434
426
|
|
@@ -438,24 +430,27 @@ EOT
|
|
438
430
|
payload = {}
|
439
431
|
if options[:payload]
|
440
432
|
payload = options[:payload]
|
441
|
-
payload.deep_merge!(parse_passed_options(options))
|
433
|
+
payload.deep_merge!({'user' => parse_passed_options(options)})
|
442
434
|
else
|
443
|
-
|
444
|
-
payload.deep_merge!(parse_passed_options(options))
|
435
|
+
payload.deep_merge!({'user' => parse_passed_options(options)})
|
445
436
|
# remove role option_type, it is just for help display, the role prompt is separate down below
|
446
|
-
prompt_option_types = add_user_option_types().reject {|it| '
|
437
|
+
prompt_option_types = add_user_option_types().reject {|it| 'roles' == it['fieldName'] }
|
447
438
|
v_prompt = Morpheus::Cli::OptionTypes.prompt(prompt_option_types, options[:options], @api_client, options[:params])
|
448
439
|
params.deep_merge!(v_prompt)
|
449
|
-
|
440
|
+
# do not prompt for advanced options
|
441
|
+
advanced_config = Morpheus::Cli::OptionTypes.no_prompt(add_user_advanced_option_types, options[:options], @api_client, options[:params])
|
442
|
+
advanced_config.deep_compact!
|
443
|
+
params.deep_merge!(advanced_config)
|
450
444
|
# prompt for roles
|
451
445
|
selected_roles = []
|
452
|
-
selected_roles +=
|
453
|
-
selected_roles +=
|
446
|
+
selected_roles += payload['user'].delete('roleId').split(',').collect {|r| r.strip.empty? ? nil : r.strip}.uniq if payload['user']['roleId']
|
447
|
+
selected_roles += payload['user'].delete('role').split(',').collect {|r| r.strip.empty? ? nil : r.strip}.uniq if payload['user']['role']
|
448
|
+
selected_roles += payload['user'].delete('roles').split(',').collect {|r| r.strip.empty? ? nil : r.strip}.uniq if payload['user']['roles']
|
454
449
|
roles = prompt_user_roles(account_id, nil, selected_roles, options)
|
455
450
|
if !roles.empty?
|
456
451
|
params['roles'] = roles.collect {|r| {id: r['id']} }
|
457
|
-
end
|
458
|
-
payload
|
452
|
+
end
|
453
|
+
payload['user'].deep_merge!(params)
|
459
454
|
end
|
460
455
|
if options[:dry_run] && options[:json]
|
461
456
|
puts as_json(payload, options)
|
@@ -471,21 +466,16 @@ EOT
|
|
471
466
|
print JSON.pretty_generate(json_response)
|
472
467
|
print "\n"
|
473
468
|
else
|
474
|
-
|
475
|
-
|
476
|
-
|
477
|
-
|
478
|
-
|
479
|
-
|
480
|
-
|
481
|
-
|
482
|
-
|
483
|
-
details_options.push "--account-id", account['id'].to_s
|
469
|
+
user = json_response['user']
|
470
|
+
username = "" # json_response['user']['username']
|
471
|
+
username = user['username'] if user
|
472
|
+
if account
|
473
|
+
print_green_success "Added user #{username} to account #{account['name']}"
|
474
|
+
else
|
475
|
+
print_green_success "Added user #{username}"
|
476
|
+
end
|
477
|
+
return _get(user['id'], {}, options)
|
484
478
|
end
|
485
|
-
get(details_options + (options[:remote] ? ["-r",options[:remote]] : []))
|
486
|
-
end
|
487
|
-
|
488
|
-
|
489
479
|
rescue RestClient::Exception => e
|
490
480
|
print_rest_exception(e, options)
|
491
481
|
return 1
|
@@ -497,8 +487,12 @@ EOT
|
|
497
487
|
params = {}
|
498
488
|
payload = {}
|
499
489
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
500
|
-
opts.banner = subcommand_usage("[
|
490
|
+
opts.banner = subcommand_usage("[user] [options]")
|
491
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
492
|
+
options[:global] = true
|
493
|
+
end
|
501
494
|
build_option_type_options(opts, options, update_user_option_types)
|
495
|
+
build_option_type_options(opts, options, update_user_advanced_option_types)
|
502
496
|
build_common_options(opts, options, [:account, :options, :payload, :json, :dry_run])
|
503
497
|
end
|
504
498
|
optparse.parse!(args)
|
@@ -508,26 +502,38 @@ EOT
|
|
508
502
|
|
509
503
|
account = find_account_from_options(options)
|
510
504
|
account_id = account ? account['id'] : nil
|
511
|
-
|
512
|
-
user = find_user_by_username_or_id(account_id, args[0])
|
505
|
+
params['global'] = true if options[:global]
|
506
|
+
user = find_user_by_username_or_id(account_id, args[0], params)
|
513
507
|
return 1 if user.nil?
|
514
508
|
|
515
509
|
# use --payload
|
510
|
+
payload = {}
|
516
511
|
if options[:payload]
|
517
512
|
payload = options[:payload]
|
518
|
-
payload.deep_merge!(parse_passed_options(options))
|
513
|
+
payload.deep_merge!({'user' => parse_passed_options(options)})
|
519
514
|
else
|
520
|
-
|
521
|
-
|
522
|
-
|
523
|
-
|
515
|
+
payload.deep_merge!({'user' => parse_passed_options(options)})
|
516
|
+
|
517
|
+
# remove role option_type, it is just for help display, the role prompt is separate down below
|
518
|
+
prompt_option_types = update_user_option_types().reject {|it| 'roles' == it['fieldName'] }
|
519
|
+
v_prompt = Morpheus::Cli::OptionTypes.no_prompt(prompt_option_types, options[:options], @api_client, options[:params])
|
520
|
+
v_prompt.deep_compact!
|
521
|
+
params.deep_merge!(v_prompt)
|
522
|
+
# do not prompt for advanced options
|
523
|
+
advanced_config = Morpheus::Cli::OptionTypes.no_prompt(update_user_advanced_option_types, options[:options], @api_client, options[:params])
|
524
|
+
advanced_config.deep_compact!
|
525
|
+
params.deep_merge!(advanced_config)
|
526
|
+
|
524
527
|
selected_roles = []
|
525
|
-
selected_roles +=
|
526
|
-
selected_roles +=
|
527
|
-
|
528
|
-
|
529
|
-
|
530
|
-
|
528
|
+
selected_roles += payload['user'].delete('roleId').to_s.split(',').collect {|r| r.strip.empty? ? nil : r.strip}.uniq if payload['user']['roleId']
|
529
|
+
selected_roles += payload['user'].delete('role').to_s.split(',').collect {|r| r.strip.empty? ? nil : r.strip}.uniq if payload['user']['role']
|
530
|
+
selected_roles += payload['user'].delete('roles').to_s.split(',').collect {|r| r.strip.empty? ? nil : r.strip}.uniq if payload['user']['roles']
|
531
|
+
if !selected_roles.empty?
|
532
|
+
roles = prompt_user_roles(account_id, user['id'], selected_roles, options.merge(no_prompt: true))
|
533
|
+
# should it allow [] (no roles) ?
|
534
|
+
if !roles.empty?
|
535
|
+
params['roles'] = roles.collect {|r| {id: r['id']} }
|
536
|
+
end
|
531
537
|
end
|
532
538
|
payload.deep_merge!({'user' => params})
|
533
539
|
if payload['user'].empty? # || options[:no_prompt]
|
@@ -541,7 +547,7 @@ EOT
|
|
541
547
|
return
|
542
548
|
end
|
543
549
|
json_response = @users_interface.update(account_id, user['id'], payload)
|
544
|
-
|
550
|
+
user = json_response['user']
|
545
551
|
if options[:json]
|
546
552
|
print JSON.pretty_generate(json_response)
|
547
553
|
print "\n"
|
@@ -551,13 +557,13 @@ EOT
|
|
551
557
|
username = payload['user']['username']
|
552
558
|
end
|
553
559
|
print_green_success "Updated user #{username}"
|
554
|
-
details_options = [username]
|
555
|
-
if account
|
556
|
-
|
557
|
-
end
|
558
|
-
get(details_options + (options[:remote] ? ["-r",options[:remote]] : []))
|
560
|
+
# details_options = [username]
|
561
|
+
# if account
|
562
|
+
# details_options.push "--account-id", account['id'].to_s
|
563
|
+
# end
|
564
|
+
# get(details_options + (options[:remote] ? ["-r",options[:remote]] : []))
|
565
|
+
return _get(user["id"], {}, options)
|
559
566
|
end
|
560
|
-
|
561
567
|
rescue RestClient::Exception => e
|
562
568
|
print_rest_exception(e, options)
|
563
569
|
return 1
|
@@ -565,26 +571,30 @@ EOT
|
|
565
571
|
end
|
566
572
|
|
567
573
|
def change_password(args)
|
574
|
+
params = {}
|
568
575
|
options = {}
|
569
576
|
new_password = nil
|
570
577
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
571
|
-
opts.banner = subcommand_usage("[
|
578
|
+
opts.banner = subcommand_usage("[user] [password] [options]")
|
579
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
580
|
+
options[:global] = true
|
581
|
+
end
|
572
582
|
# opts.on('--password VALUE', String, "New password") do |val|
|
573
583
|
# new_password = val
|
574
584
|
# end
|
575
585
|
build_standard_update_options(opts, options, [:account])
|
576
586
|
end
|
577
587
|
optparse.parse!(args)
|
578
|
-
verify_args!(args:args, optparse:optparse, min:1,max:2) # [
|
588
|
+
verify_args!(args:args, optparse:optparse, min:1,max:2) # [user] [password]
|
579
589
|
connect(options)
|
580
590
|
exit_code, err = 0, nil
|
581
591
|
|
582
592
|
# user can be scoped to account (tenant)
|
583
593
|
account = find_account_from_options(options)
|
584
594
|
account_id = account ? account['id'] : nil
|
585
|
-
|
595
|
+
params['global'] = true if options[:global]
|
586
596
|
# fetch the user to update
|
587
|
-
user = find_user_by_username_or_id(account_id, args[0])
|
597
|
+
user = find_user_by_username_or_id(account_id, args[0], params)
|
588
598
|
return 1 if user.nil?
|
589
599
|
|
590
600
|
new_password = args[1] if args[1]
|
@@ -644,10 +654,14 @@ EOT
|
|
644
654
|
end
|
645
655
|
|
646
656
|
def remove(args)
|
657
|
+
params = {}
|
647
658
|
options = {}
|
648
659
|
optparse = Morpheus::Cli::OptionParser.new do |opts|
|
649
|
-
opts.banner = subcommand_usage("[
|
650
|
-
|
660
|
+
opts.banner = subcommand_usage("[user]")
|
661
|
+
opts.on('-g','--global', "Global (All Tenants). Find users across all tenants. Default is your own tenant only.") do
|
662
|
+
options[:global] = true
|
663
|
+
end
|
664
|
+
build_standard_remove_options(opts, options, [:account])
|
651
665
|
end
|
652
666
|
optparse.parse!(args)
|
653
667
|
|
@@ -658,19 +672,18 @@ EOT
|
|
658
672
|
|
659
673
|
connect(options)
|
660
674
|
begin
|
661
|
-
|
662
675
|
account = find_account_from_options(options)
|
663
676
|
account_id = account ? account['id'] : nil
|
664
|
-
|
665
|
-
user = find_user_by_username_or_id(account_id, args[0])
|
677
|
+
params['global'] = true if options[:global]
|
678
|
+
user = find_user_by_username_or_id(account_id, args[0], params)
|
666
679
|
return 1 if user.nil?
|
667
680
|
unless options[:yes] || Morpheus::Cli::OptionTypes.confirm("Are you sure you want to delete the user #{user['username']}?")
|
668
|
-
exit
|
681
|
+
exit 9, "arborted"
|
669
682
|
end
|
670
683
|
@users_interface.setopts(options)
|
671
684
|
if options[:dry_run]
|
672
685
|
print_dry_run @users_interface.dry.destroy(account_id, user['id'])
|
673
|
-
return
|
686
|
+
return 0
|
674
687
|
end
|
675
688
|
json_response = @users_interface.destroy(account_id, user['id'])
|
676
689
|
|
@@ -697,19 +710,33 @@ EOT
|
|
697
710
|
{'fieldName' => 'email', 'fieldLabel' => 'Email', 'type' => 'text', 'required' => true, 'displayOrder' => 4},
|
698
711
|
{'fieldName' => 'password', 'fieldLabel' => 'Password', 'type' => 'password', 'required' => true, 'displayOrder' => 5},
|
699
712
|
{'fieldName' => 'passwordConfirmation', 'fieldLabel' => 'Confirm Password', 'type' => 'password', 'required' => true, 'displayOrder' => 6},
|
700
|
-
{'fieldName' => '
|
701
|
-
{'fieldName' => 'receiveNotifications', 'fieldLabel' => 'Receive Notifications?', 'type' => 'checkbox', 'required' => false, 'defaultValue' => true, 'displayOrder' =>
|
713
|
+
{'fieldName' => 'roles', 'fieldLabel' => 'Roles', 'type' => 'text', 'description' => "Role authorities or IDs (comma separated)", 'displayOrder' => 7},
|
714
|
+
{'fieldName' => 'receiveNotifications', 'fieldLabel' => 'Receive Notifications?', 'type' => 'checkbox', 'required' => false, 'defaultValue' => true, 'displayOrder' => 8}
|
715
|
+
]
|
716
|
+
end
|
717
|
+
|
718
|
+
def add_user_advanced_option_types
|
719
|
+
[
|
702
720
|
{'fieldName' => 'linuxUsername', 'fieldLabel' => 'Linux Username', 'type' => 'text', 'required' => false, 'displayOrder' => 9},
|
703
|
-
|
704
|
-
{'fieldName' => '
|
705
|
-
|
706
|
-
|
721
|
+
{'fieldName' => 'linuxPassword', 'fieldLabel' => 'Linux Password', 'type' => 'password', 'required' => false, 'displayOrder' => 10},
|
722
|
+
{'fieldName' => 'linuxKeyPairId', 'fieldLabel' => 'SSH Key', 'type' => 'select', 'optionSource' => 'keyPairs', 'required' => false, 'displayOrder' => 11},
|
723
|
+
{'fieldName' => 'windowsUsername', 'fieldLabel' => 'Windows Username', 'type' => 'text', 'required' => false, 'displayOrder' => 12},
|
724
|
+
{'fieldName' => 'windowsPassword', 'fieldLabel' => 'Windows Password', 'type' => 'text', 'required' => false, 'displayOrder' => 13},
|
707
725
|
]
|
708
726
|
end
|
709
727
|
|
710
728
|
def update_user_option_types
|
711
729
|
add_user_option_types.collect {|it|
|
712
|
-
it
|
730
|
+
it.delete('required')
|
731
|
+
it.delete('defaultValue')
|
732
|
+
it
|
733
|
+
}
|
734
|
+
end
|
735
|
+
|
736
|
+
def update_user_advanced_option_types
|
737
|
+
add_user_advanced_option_types.collect {|it|
|
738
|
+
it.delete('required')
|
739
|
+
it.delete('defaultValue')
|
713
740
|
it
|
714
741
|
}
|
715
742
|
end
|
@@ -732,7 +759,7 @@ EOT
|
|
732
759
|
|
733
760
|
if available_roles.empty?
|
734
761
|
print_red_alert "No available roles found."
|
735
|
-
|
762
|
+
exit 1
|
736
763
|
end
|
737
764
|
role_options = available_roles.collect {|role|
|
738
765
|
{'name' => role['authority'], 'value' => role['id']}
|
@@ -754,30 +781,27 @@ EOT
|
|
754
781
|
print_red_alert "Invalid Roles: #{invalid_role_names.join(', ')}"
|
755
782
|
exit 1
|
756
783
|
end
|
757
|
-
|
758
|
-
|
759
|
-
if roles.empty?
|
784
|
+
else
|
760
785
|
no_prompt = (options[:no_prompt] || (options[:options] && options[:options][:no_prompt]))
|
761
|
-
|
762
|
-
|
763
|
-
|
764
|
-
|
765
|
-
|
766
|
-
|
767
|
-
|
768
|
-
|
769
|
-
|
770
|
-
|
771
|
-
|
772
|
-
roles << available_roles.find {|r| r['id'].to_i == role_id.to_i }
|
773
|
-
end
|
774
|
-
end
|
786
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'roles', 'fieldLabel' => 'Role', 'type' => 'select', 'selectOptions' => role_options, 'required' => true}], options[:options])
|
787
|
+
role_id = v_prompt['roles']
|
788
|
+
roles << available_roles.find {|r| r['id'].to_i == role_id.to_i }
|
789
|
+
add_another_role = !no_prompt
|
790
|
+
while add_another_role do
|
791
|
+
v_prompt = Morpheus::Cli::OptionTypes.prompt([{'fieldName' => 'roles', 'fieldLabel' => 'Another Role', 'type' => 'select', 'selectOptions' => role_options, 'required' => false}], options[:options])
|
792
|
+
if v_prompt['roles'].to_s.empty?
|
793
|
+
add_another_role = false
|
794
|
+
else
|
795
|
+
role_id = v_prompt['roles']
|
796
|
+
roles << available_roles.find {|r| r['id'].to_i == role_id.to_i }
|
775
797
|
end
|
776
798
|
end
|
777
|
-
|
778
|
-
roles = roles.compact
|
779
|
-
return roles
|
780
|
-
|
799
|
+
|
781
800
|
end
|
782
801
|
|
802
|
+
roles = roles.compact
|
803
|
+
return roles
|
804
|
+
|
783
805
|
end
|
806
|
+
|
807
|
+
end
|