rhc 1.22.5 → 1.23.7

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.
@@ -10,9 +10,9 @@ _rhc()
10
10
  if [[ "$cur" == -* ]]; then
11
11
  opts="--always-prefix --clean --config --debug --insecure --limit --mock --noprompt --password --raw --rhlogin --server --ssl-ca-file --ssl-client-cert-file --ssl-version --timeout --token"
12
12
  elif [ -z $cur ]; then
13
- opts="account alias alias-add alias-delete-cert alias-list alias-remove alias-update-cert app app-configure app-create app-delete app-deploy app-force-stop app-reload app-restart app-scale-down app-scale-up app-show app-start app-stop app-tidy apps authorization authorization-add authorization-delete authorization-delete-all authorization-list cartridge cartridge-add cartridge-list cartridge-reload cartridge-remove cartridge-restart cartridge-scale cartridge-show cartridge-start cartridge-status cartridge-stop cartridge-storage deployment deployment-activate deployment-list deployment-show domain domain-configure domain-create domain-delete domain-leave domain-list domain-rename domain-show env env-list env-set env-show env-unset git-clone logout member member-add member-list member-remove port-forward scp server setup snapshot snapshot-restore snapshot-save ssh sshkey sshkey-add sshkey-list sshkey-remove sshkey-show tail threaddump"
13
+ opts="account alias alias-add alias-delete-cert alias-list alias-remove alias-update-cert app app-configure app-create app-delete app-deploy app-force-stop app-reload app-restart app-scale-down app-scale-up app-show app-start app-stop app-tidy apps authorization authorization-add authorization-delete authorization-delete-all authorization-list cartridge cartridge-add cartridge-list cartridge-reload cartridge-remove cartridge-restart cartridge-scale cartridge-show cartridge-start cartridge-status cartridge-stop cartridge-storage deployment deployment-activate deployment-list deployment-show domain domain-configure domain-create domain-delete domain-leave domain-list domain-rename domain-show env env-list env-set env-show env-unset git-clone logout member member-add member-list member-remove member-update port-forward scp server setup snapshot snapshot-restore snapshot-save ssh sshkey sshkey-add sshkey-list sshkey-remove sshkey-show tail threaddump"
14
14
  else
15
- opts="account account-logout activate-deployment add-alias add-authorization add-cartridge add-member add-sshkey alias alias-add alias-delete-cert alias-list alias-remove alias-update-cert aliases app app-configure app-create app-delete app-deploy app-env app-force-stop app-reload app-restart app-scale-down app-scale-up app-scp app-show app-snapshot app-ssh app-start app-stop app-tidy apps authorization authorization-add authorization-delete authorization-delete-all authorization-list authorizations cartridge cartridge-add cartridge-list cartridge-reload cartridge-remove cartridge-restart cartridge-scale cartridge-show cartridge-start cartridge-status cartridge-stop cartridge-storage cartridges configure-app configure-domain create-app create-domain delete-all-authorization delete-app delete-authorization delete-cert-alias delete-domain deploy deploy-app deployment deployment-activate deployment-list deployment-show deployments domain domain-configure domain-create domain-delete domain-leave domain-list domain-rename domain-show domains env env-add env-list env-remove env-set env-show env-unset force-stop-app git-clone leave-domain list-alias list-authorization list-cartridge list-deployment list-domain list-env list-member list-sshkey logout member member-add member-list member-remove members port-forward reload-app reload-cartridge remove-alias remove-cartridge remove-member remove-sshkey rename-domain restart-app restart-cartridge restore-snapshot save-snapshot scale-cartridge scale-down-app scale-up-app scp server set-env setup show-app show-cartridge show-deployment show-domain show-env show-sshkey snapshot snapshot-restore snapshot-save ssh sshkey sshkey-add sshkey-list sshkey-remove sshkey-show start-app start-cartridge status-cartridge stop-app stop-cartridge storage-cartridge tail threaddump tidy-app unset-env update-cert-alias"
15
+ opts="account account-logout activate-deployment add-alias add-authorization add-cartridge add-member add-sshkey alias alias-add alias-delete-cert alias-list alias-remove alias-update-cert aliases app app-configure app-create app-delete app-deploy app-env app-force-stop app-reload app-restart app-scale-down app-scale-up app-scp app-show app-snapshot app-ssh app-start app-stop app-tidy apps authorization authorization-add authorization-delete authorization-delete-all authorization-list authorizations cartridge cartridge-add cartridge-list cartridge-reload cartridge-remove cartridge-restart cartridge-scale cartridge-show cartridge-start cartridge-status cartridge-stop cartridge-storage cartridges configure-app configure-domain create-app create-domain delete-all-authorization delete-app delete-authorization delete-cert-alias delete-domain deploy deploy-app deployment deployment-activate deployment-list deployment-show deployments domain domain-configure domain-create domain-delete domain-leave domain-list domain-rename domain-show domains env env-add env-list env-remove env-set env-show env-unset force-stop-app git-clone leave-domain list-alias list-authorization list-cartridge list-deployment list-domain list-env list-member list-sshkey logout member member-add member-list member-remove member-update members port-forward reload-app reload-cartridge remove-alias remove-cartridge remove-member remove-sshkey rename-domain restart-app restart-cartridge restore-snapshot save-snapshot scale-cartridge scale-down-app scale-up-app scp server set-env setup show-app show-cartridge show-deployment show-domain show-env show-sshkey snapshot snapshot-restore snapshot-save ssh sshkey sshkey-add sshkey-list sshkey-remove sshkey-show start-app start-cartridge status-cartridge stop-app stop-cartridge storage-cartridge tail threaddump tidy-app unset-env update-cert-alias update-member"
16
16
  fi
17
17
  else
18
18
  prev="${COMP_WORDS[@]:0:COMP_CWORD}"
@@ -78,7 +78,7 @@ _rhc()
78
78
 
79
79
  "rhc add-member")
80
80
  if [[ "$cur" == -* ]]; then
81
- opts="--ids --namespace --role"
81
+ opts="--global --ids --namespace --role --type"
82
82
  else
83
83
  opts=""
84
84
  fi
@@ -192,7 +192,7 @@ _rhc()
192
192
  if [[ "$cur" == -* ]]; then
193
193
  opts=""
194
194
  else
195
- opts="create delete start stop scale-up scale-down force-stop restart reload tidy show deploy configure env snapshot"
195
+ opts="env snapshot create delete start stop scale-up scale-down force-stop restart reload tidy show deploy configure"
196
196
  fi
197
197
  ;;
198
198
 
@@ -1206,7 +1206,7 @@ _rhc()
1206
1206
 
1207
1207
  "rhc list-member")
1208
1208
  if [[ "$cur" == -* ]]; then
1209
- opts="--app --ids --namespace --target"
1209
+ opts="--all --app --ids --namespace --target"
1210
1210
  else
1211
1211
  opts=""
1212
1212
  fi
@@ -1232,13 +1232,13 @@ _rhc()
1232
1232
  if [[ "$cur" == -* ]]; then
1233
1233
  opts=""
1234
1234
  else
1235
- opts="list add remove"
1235
+ opts="list add update remove"
1236
1236
  fi
1237
1237
  ;;
1238
1238
 
1239
1239
  "rhc member add")
1240
1240
  if [[ "$cur" == -* ]]; then
1241
- opts="--ids --namespace --role"
1241
+ opts="--global --ids --namespace --role --type"
1242
1242
  else
1243
1243
  opts=""
1244
1244
  fi
@@ -1246,7 +1246,7 @@ _rhc()
1246
1246
 
1247
1247
  "rhc member list")
1248
1248
  if [[ "$cur" == -* ]]; then
1249
- opts="--app --ids --namespace --target"
1249
+ opts="--all --app --ids --namespace --target"
1250
1250
  else
1251
1251
  opts=""
1252
1252
  fi
@@ -1254,7 +1254,15 @@ _rhc()
1254
1254
 
1255
1255
  "rhc member remove")
1256
1256
  if [[ "$cur" == -* ]]; then
1257
- opts="--all --ids --namespace"
1257
+ opts="--all --ids --namespace --type"
1258
+ else
1259
+ opts=""
1260
+ fi
1261
+ ;;
1262
+
1263
+ "rhc member update")
1264
+ if [[ "$cur" == -* ]]; then
1265
+ opts="--ids --namespace --role --type"
1258
1266
  else
1259
1267
  opts=""
1260
1268
  fi
@@ -1262,7 +1270,7 @@ _rhc()
1262
1270
 
1263
1271
  "rhc member-add")
1264
1272
  if [[ "$cur" == -* ]]; then
1265
- opts="--ids --namespace --role"
1273
+ opts="--global --ids --namespace --role --type"
1266
1274
  else
1267
1275
  opts=""
1268
1276
  fi
@@ -1270,7 +1278,7 @@ _rhc()
1270
1278
 
1271
1279
  "rhc member-list")
1272
1280
  if [[ "$cur" == -* ]]; then
1273
- opts="--app --ids --namespace --target"
1281
+ opts="--all --app --ids --namespace --target"
1274
1282
  else
1275
1283
  opts=""
1276
1284
  fi
@@ -1278,7 +1286,15 @@ _rhc()
1278
1286
 
1279
1287
  "rhc member-remove")
1280
1288
  if [[ "$cur" == -* ]]; then
1281
- opts="--all --ids --namespace"
1289
+ opts="--all --ids --namespace --type"
1290
+ else
1291
+ opts=""
1292
+ fi
1293
+ ;;
1294
+
1295
+ "rhc member-update")
1296
+ if [[ "$cur" == -* ]]; then
1297
+ opts="--ids --namespace --role --type"
1282
1298
  else
1283
1299
  opts=""
1284
1300
  fi
@@ -1286,7 +1302,7 @@ _rhc()
1286
1302
 
1287
1303
  "rhc members")
1288
1304
  if [[ "$cur" == -* ]]; then
1289
- opts="--app --ids --namespace --target"
1305
+ opts="--all --app --ids --namespace --target"
1290
1306
  else
1291
1307
  opts=""
1292
1308
  fi
@@ -1334,7 +1350,7 @@ _rhc()
1334
1350
 
1335
1351
  "rhc remove-member")
1336
1352
  if [[ "$cur" == -* ]]; then
1337
- opts="--all --ids --namespace"
1353
+ opts="--all --ids --namespace --type"
1338
1354
  else
1339
1355
  opts=""
1340
1356
  fi
@@ -1700,6 +1716,14 @@ _rhc()
1700
1716
  fi
1701
1717
  ;;
1702
1718
 
1719
+ "rhc update-member")
1720
+ if [[ "$cur" == -* ]]; then
1721
+ opts="--ids --namespace --role --type"
1722
+ else
1723
+ opts=""
1724
+ fi
1725
+ ;;
1726
+
1703
1727
  esac
1704
1728
  IFS=$SAVE_IFS
1705
1729
  fi
@@ -50,6 +50,7 @@ describe "rhc core scenarios" do
50
50
  context "when creating an app" do
51
51
  when_running 'create-app', 'test1', a_web_cartridge
52
52
  before{ no_applications }
53
+ after { no_applications }
53
54
  it "returns the proper info and is in the rest api" do
54
55
  status.should == 0
55
56
  output.should match "Your application 'test1' is now available"
@@ -69,6 +70,7 @@ describe "rhc core scenarios" do
69
70
  standard_config
70
71
  @app = has_an_application
71
72
  end
73
+ after(:all){ @app.destroy }
72
74
 
73
75
  let(:app){ @app }
74
76
 
@@ -149,8 +149,9 @@ module RHC::Commands
149
149
  domain = rest_client.find_domain(namespace)
150
150
 
151
151
  say "Leaving domain ... "
152
- domain.leave
152
+ result = domain.leave
153
153
  success "done"
154
+ result.messages.each{ |s| paragraph{ say s } }
154
155
 
155
156
  0
156
157
  end
@@ -5,7 +5,7 @@ module RHC::Commands
5
5
  summary "Manage membership on domains"
6
6
  syntax "<action>"
7
7
  description <<-DESC
8
- Teams of developers can collaborate on applications by adding people to
8
+ Developers can collaborate on applications by adding people or teams to
9
9
  domains as members: each member has a role (admin, editor, or viewer),
10
10
  and those roles determine what the user can do with the domain and the
11
11
  applications contained within.
@@ -32,7 +32,7 @@ module RHC::Commands
32
32
  default_action :help
33
33
 
34
34
  summary "List members of a domain or application"
35
- syntax "<domain_or_app_name> [-n DOMAIN_NAME] [-a APP_NAME]"
35
+ syntax "<domain_or_app_name> [-n DOMAIN_NAME] [-a APP_NAME] [--all]"
36
36
  description <<-DESC
37
37
  Show the existing members of a domain or application - you can pass the name
38
38
  of your domain with '-n', the name of your application with '-a', or combine
@@ -44,33 +44,67 @@ module RHC::Commands
44
44
  '--ids'.
45
45
  DESC
46
46
  option ['--ids'], "Display the IDs of each member", :optional => true
47
+ option ['--all'], "Display all members, including members of teams", :optional => true
47
48
  takes_application_or_domain :argument => true
48
49
  alias_action :members, :root_command => true
49
50
  def list(path)
50
51
  target = find_app_or_domain(path)
51
- members = target.members.sort_by{ |m| [m.owner? ? 0 : 1, m.role_weight, m.name] }
52
- show_name = members.any?{ |m| m.name && m.name != m.login }
53
- members.map! do |m|
54
- [
55
- ((m.name || "") if show_name),
56
- m.login || "",
57
- m.owner? ? "#{m.role} (owner)" : m.role,
58
- (m.id if options.ids)
59
- ].compact
52
+
53
+ members = target.members
54
+ if options.all
55
+ show_members = members.sort
56
+ else
57
+ show_members = members.select do |m|
58
+ if m.owner?
59
+ true
60
+ elsif m.explicit_role?
61
+ true
62
+ elsif m.from.any? {|f| f["type"] != "team" }
63
+ true
64
+ else
65
+ false
66
+ end
67
+ end.sort
68
+ end
69
+ show_name = show_members.any?{ |m| m.name.presence && m.name != m.login }
70
+ show_login = show_members.any?{ |m| m.login.presence }
71
+
72
+ if show_members.present?
73
+ say table(show_members.map do |member|
74
+ [
75
+ ((member.name || "") if show_name),
76
+ ((member.login || "") if show_login),
77
+ role_description(member, member.teams(members)),
78
+ (member.id if options.ids),
79
+ member.type
80
+ ].compact
81
+ end, :header => [
82
+ ('Name' if show_name),
83
+ ('Login' if show_login),
84
+ 'Role',
85
+ ("ID" if options.ids),
86
+ "Type"
87
+ ].compact)
88
+ else
89
+ info "The #{target.class.model_name.downcase} #{target.name} does not have any members."
90
+ end
91
+
92
+ if show_members.count < members.count
93
+ paragraph do
94
+ info "Pass --all to display all members, including members of teams."
95
+ end
60
96
  end
61
- say table(members, :header => [('Name' if show_name), 'Login', 'Role', ("ID" if options.ids)].compact)
62
97
 
63
98
  0
64
99
  end
65
100
 
66
- summary "Add or update a member on a domain"
67
- syntax "<login> [<login>...] [-n DOMAIN_NAME] [--role view|edit|admin] [--ids]"
101
+ summary "Add a member on a domain"
102
+ syntax "(<login>... | <team name>... | <id>...) [-n DOMAIN_NAME] [--role view|edit|admin] [--ids] [--type user|team] [--global]"
68
103
  description <<-DESC
69
- Adds or updates members on a domain by passing one or more login
70
- or ids for other people on OpenShift. The login and ID values for each
71
- account are displayed in 'rhc account'. To change the role for a user, simply
72
- call the add-member command with the new role. You cannot change the role of
73
- the owner.
104
+ Adds members on a domain by passing a user login, team name, or ID for each
105
+ member. The login and ID for each account are displayed in 'rhc account'.
106
+ To change the role for an existing domain member, use the 'rhc member update'
107
+ command.
74
108
 
75
109
  Roles
76
110
  view - able to see information about the domain and its apps,
@@ -89,26 +123,89 @@ module RHC::Commands
89
123
  rhc add-member bob@example.com --role admin -n mydomain
90
124
  Gives the account with login 'bob@example.com' admin access on mydomain
91
125
 
126
+ rhc add-member team1 --type team --role admin -n mydomain
127
+ Gives your team named 'team1' admin access on mydomain
128
+
92
129
  DESC
93
130
  takes_domain
94
131
  option ['--ids'], "Treat the arguments as a list of IDs", :optional => true
95
- option ['-r', '--role ROLE'], "The role to give to each member - view, edit, or admin (default 'edit')", :type => Role, :optional => true
96
- argument :members, "A list of members logins to add. Pass --ids to treat this as a list of IDs.", [], :type => :list
132
+ option ['-r', '--role ROLE'], "The role to give to each member - view, edit, or admin (default is 'edit')", :type => Role, :optional => true
133
+ option ['--type TYPE'], "Type of argument(s) being passed. Accepted values are either 'team' or 'user' (default is 'user').", :optional => true
134
+ option ['--global'], "Use global-scoped teams. Must be used with '--type team'.", :optional => true
135
+ argument :members, "A list of members (user logins, team names, or IDs) to add. Pass --ids to treat this as a list of IDs.", [], :type => :list
97
136
  def add(members)
98
137
  target = find_domain
99
- role = options.role || 'edit'
100
- raise ArgumentError, 'You must pass one or more logins or ids to this command' unless members.present?
138
+ role = get_role_option(options)
139
+ type = get_type_option(options)
140
+ global = !!options.global
141
+
142
+ raise ArgumentError, 'You must pass at least one user login, team name, or ID to this command.' unless members.present?
143
+ raise ArgumentError, "The --global option can only be used with '--type team'." if global && !team?(type)
144
+
101
145
  say "Adding #{pluralize(members.length, role_name(role))} to #{target.class.model_name.downcase} ... "
102
- target.update_members(changes_for(members, role))
146
+
147
+ members = search_teams(members, global).map{|member| member.id} if team?(type) && !options.ids
148
+ target.update_members(changes_for(members, role, type))
149
+
150
+ success "done"
151
+
152
+ 0
153
+ end
154
+
155
+ summary "Update a member on a domain"
156
+ syntax "(<login>... | <team name>... | <id>...) --role view|edit|admin [-n DOMAIN_NAME] [--ids] [--type user|team]"
157
+ description <<-DESC
158
+ Updates members on a domain by passing a user login, team name, or ID for
159
+ each member. You can use the 'rhc members' command to list the existing
160
+ members of your domain. You cannot change the role of the owner.
161
+
162
+ Roles
163
+ view - able to see information about the domain and its apps,
164
+ but not make any changes
165
+ edit - create, update, and delete applications, and has Git
166
+ and SSH access
167
+ admin - can update membership of a domain
168
+
169
+ The default role granted to members when added is 'edit' - use the '--role'
170
+ argument for 'view' or 'admin'.
171
+
172
+ Examples
173
+ rhc update-member bob@example.com --role view -n mydomain
174
+ Adds or updates the member with login 'bob@example.com' to 'admin' role on mydomain
175
+
176
+ rhc update-member team1 --type team --role admin -n mydomain
177
+ Updates the team member with name 'team1' to the 'admin' role on mydomain
178
+
179
+ rhc update-member team1_id --type team --role admin -n mydomain --ids
180
+ Adds or updates the team with ID 'team1_id' to the 'admin' role on mydomain
181
+
182
+ DESC
183
+ takes_domain
184
+ option ['--ids'], "Treat the arguments as a list of IDs", :optional => true
185
+ option ['-r', '--role ROLE'], "The role to give to each member - view, edit, or admin (default is 'edit')", :type => Role, :optional => true
186
+ option ['--type TYPE'], "Type of argument(s) being passed. Accepted values are either 'team' or 'user' (default is 'user').", :optional => true
187
+ argument :members, "A list of members (user logins, team names, or IDs) to update. Pass --ids to treat this as a list of IDs.", [], :type => :list
188
+ def update(members)
189
+ target = find_domain
190
+ role = get_role_option(options)
191
+ type = get_type_option(options)
192
+
193
+ raise ArgumentError, 'You must pass at least one user login, team name, or ID to this command.' unless members.present?
194
+
195
+ say "Updating #{pluralize(members.length, role_name(role))} to #{target.class.model_name.downcase} ... "
196
+
197
+ members = search_team_members(target.members, members).map{|member| member.id} if team?(type) && !options.ids
198
+ target.update_members(changes_for(members, role, type))
199
+
103
200
  success "done"
104
201
 
105
202
  0
106
203
  end
107
204
 
108
205
  summary "Remove a member from a domain"
109
- syntax "<login> [<login>...] [-n DOMAIN_NAME] [--ids]"
206
+ syntax "(<login>... | <team name>... | <id>...) [-n DOMAIN_NAME] [--ids] [--type user|team]"
110
207
  description <<-DESC
111
- Remove members on a domain by passing one or more login or ids for each
208
+ Remove members from a domain by passing a user login, team name, or ID for each
112
209
  member you wish to remove. View the list of existing members with
113
210
  'rhc members <domain_name>'.
114
211
 
@@ -117,9 +214,11 @@ module RHC::Commands
117
214
  takes_domain
118
215
  option ['--ids'], "Treat the arguments as a list of IDs"
119
216
  option ['--all'], "Remove all members from this domain."
120
- argument :members, "Member logins to remove from the domain. Pass --ids to treat this as a list of IDs.", [], :type => :list
217
+ option ['--type TYPE'], "Type of argument(s) being passed. Accepted values are either 'team' or 'user' (default is 'user').", :optional => true
218
+ argument :members, "A list of members (user logins, team names, or IDs) to remove from the domain. Pass --ids to treat this as a list of IDs.", [], :type => :list
121
219
  def remove(members)
122
220
  target = find_domain
221
+ type = get_type_option(options)
123
222
 
124
223
  if options.all
125
224
  say "Removing all members from #{target.class.model_name.downcase} ... "
@@ -127,9 +226,13 @@ module RHC::Commands
127
226
  success "done"
128
227
 
129
228
  else
130
- raise ArgumentError, 'You must pass one or more logins or ids to this command' unless members.present?
229
+ raise ArgumentError, 'You must pass at least one user login, team name, or ID to this command.' unless members.present?
230
+
131
231
  say "Removing #{pluralize(members.length, 'member')} from #{target.class.model_name.downcase} ... "
132
- target.update_members(changes_for(members, 'none'))
232
+
233
+ members = search_team_members(target.members, members).map{|member| member.id} if team?(type) && !options.ids
234
+ target.update_members(changes_for(members, 'none', type))
235
+
133
236
  success "done"
134
237
  end
135
238
 
@@ -137,12 +240,131 @@ module RHC::Commands
137
240
  end
138
241
 
139
242
  protected
140
- def changes_for(members, role)
243
+ def get_role_option(options, default_value='edit')
244
+ options.role || default_value
245
+ end
246
+
247
+ def get_type_option(options, default_value='user')
248
+ type = options.__hash__[:type]
249
+ case type
250
+ when 'team'
251
+ type
252
+ when 'user'
253
+ type
254
+ when nil
255
+ default_value
256
+ else
257
+ raise ArgumentError, "The type '#{type}' is not valid. Type must be 'user' or 'team'."
258
+ end
259
+ end
260
+
261
+ def changes_for(members, role, type)
141
262
  members.map do |m|
142
- h = {:role => role}
143
- h[options.ids ? :id : :login] = m
263
+ h = {:role => role, :type => type}
264
+ h[options.ids || team?(type) ? :id : :login] = m
144
265
  h
145
266
  end
146
267
  end
268
+
269
+ def team?(type)
270
+ type == 'team'
271
+ end
272
+
273
+ def search_teams(team_names, global=false)
274
+ r = []
275
+ team_names.each do |team_name|
276
+ teams_for_name =
277
+ global ?
278
+ rest_client.search_teams(team_name, global) :
279
+ rest_client.search_owned_teams(team_name)
280
+
281
+ team_for_name = nil
282
+ suggestions = nil
283
+
284
+ if (exact_matches = teams_for_name.select {|t| t.name == team_name }).present?
285
+ if exact_matches.length == 1
286
+ team_for_name = exact_matches.first
287
+ else
288
+ raise RHC::TeamNotFoundException.new("There is more than one team named '#{team_name}'. " +
289
+ "Please use the --ids flag and specify the exact id of the team you want to manage.")
290
+ end
291
+
292
+ elsif (case_insensitive_matches = teams_for_name.select {|t| t.name =~ /^#{Regexp.escape(team_name)}$/i }).present?
293
+ if case_insensitive_matches.length == 1
294
+ team_for_name = case_insensitive_matches.first
295
+ else
296
+ suggestions = case_insensitive_matches
297
+ end
298
+
299
+ else
300
+ suggestions = teams_for_name
301
+ end
302
+
303
+
304
+ if team_for_name
305
+ r << team_for_name
306
+ elsif suggestions.present?
307
+ msg = global ? "No global team found with the name '#{team_name}'." : "You do not have a team named '#{team_name}'."
308
+ raise RHC::TeamNotFoundException.new(msg + " Did you mean one of the following?\n#{suggestions[0..50].map(&:name).join(", ")}")
309
+ else
310
+ msg = global ? "No global team found with the name '#{team_name}'." : "You do not have a team named '#{team_name}'."
311
+ raise RHC::TeamNotFoundException.new(msg)
312
+ end
313
+
314
+ end
315
+ r.flatten
316
+ end
317
+
318
+ def search_team_members(members, names)
319
+ r = []
320
+ team_members = members.select(&:team?)
321
+ names.each do |name|
322
+
323
+ team_for_name = nil
324
+ suggestions = nil
325
+
326
+ if (exact_matches = team_members.select{|team| team.name == name }).present?
327
+ if exact_matches.length == 1
328
+ team_for_name = exact_matches.first
329
+ else
330
+ raise RHC::MemberNotFoundException.new("There is more than one member team named '#{name}'. " +
331
+ "Please use the --ids flag and specify the exact id of the team you want to manage.")
332
+ end
333
+
334
+ elsif (case_insensitive_matches = team_members.select{|team| team.name =~ /^#{Regexp.escape(name)}$/i}).present?
335
+ if case_insensitive_matches.length == 1
336
+ team_for_name = case_insensitive_matches.first
337
+ else
338
+ suggestions = case_insensitive_matches
339
+ end
340
+
341
+ else
342
+ suggestions = team_members.select{|t| t.name =~ /#{Regexp.escape(name)}/i}
343
+ end
344
+
345
+ if team_for_name
346
+ r << team_for_name
347
+ elsif suggestions.present?
348
+ raise RHC::MemberNotFoundException.new("No member team found with the name '#{name}'. " +
349
+ "Did you mean one of the following?\n#{suggestions[0..50].map(&:name).join(", ")}")
350
+ else
351
+ raise RHC::MemberNotFoundException.new("No member team found with the name '#{name}'.")
352
+ end
353
+
354
+ end
355
+ r.flatten
356
+ end
357
+
358
+ def role_description(member, teams=[])
359
+ if member.owner?
360
+ "#{member.role} (owner)"
361
+ elsif member.explicit_role != member.role && member.from.all? {|f| f['type'] == 'domain'}
362
+ "#{member.role} (via domain)"
363
+ elsif member.explicit_role != member.role && teams.present? && (teams_with_role = teams.select{|t| t.role == member.role }).present?
364
+ "#{member.role} (via #{teams_with_role.map(&:name).sort.join(', ')})"
365
+ else
366
+ member.role
367
+ end
368
+ end
147
369
  end
148
- end
370
+ end