4
4
"encoding/json"
5
5
"fmt"
6
6
"io"
7
- "os"
8
7
"slices"
9
8
"strings"
10
9
@@ -114,7 +113,8 @@ func (r *RootCmd) editOrganizationRole() *serpent.Command {
114
113
)
115
114
116
115
var (
117
- dryRun bool
116
+ dryRun bool
117
+ jsonInput bool
118
118
)
119
119
120
120
client := new (codersdk.Client )
@@ -135,6 +135,12 @@ func (r *RootCmd) editOrganizationRole() *serpent.Command {
135
135
Flag :"dry-run" ,
136
136
Value :serpent .BoolOf (& dryRun ),
137
137
},
138
+ {
139
+ Name :"stdin" ,
140
+ Description :"Reads stdin for the json role definition to upload." ,
141
+ Flag :"stdin" ,
142
+ Value :serpent .BoolOf (& jsonInput ),
143
+ },
138
144
},
139
145
Middleware :serpent .Chain (
140
146
serpent .RequireRangeArgs (0 ,1 ),
@@ -148,10 +154,9 @@ func (r *RootCmd) editOrganizationRole() *serpent.Command {
148
154
}
149
155
150
156
var customRole codersdk.Role
151
- fi ,_ := os .Stdin .Stat ()
152
- if (fi .Mode ()& os .ModeCharDevice )== 0 {
157
+ if jsonInput {
153
158
// JSON Upload mode
154
- bytes ,err := io .ReadAll (os .Stdin )
159
+ bytes ,err := io .ReadAll (inv .Stdin )
155
160
if err != nil {
156
161
return xerrors .Errorf ("reading stdin: %w" ,err )
157
162
}
@@ -170,6 +175,10 @@ func (r *RootCmd) editOrganizationRole() *serpent.Command {
170
175
return xerrors .Errorf ("json input does not appear to be a valid role" )
171
176
}
172
177
}else {
178
+ if len (inv .Args )== 0 {
179
+ return xerrors .Errorf ("missing role name argument, usage:\" coder organizations roles edit <role_name>\" " )
180
+ }
181
+
173
182
interactiveRole ,err := interactiveOrgRoleEdit (inv ,org .ID ,client )
174
183
if err != nil {
175
184
return xerrors .Errorf ("editing role: %w" ,err )
@@ -182,7 +191,7 @@ func (r *RootCmd) editOrganizationRole() *serpent.Command {
182
191
for _ ,o := range customRole .OrganizationPermissions {
183
192
totalOrg += len (o )
184
193
}
185
- preview := fmt .Sprintf ("perms : %d site, %d over %d orgs, %d user" ,
194
+ preview := fmt .Sprintf ("permissions : %d site, %d over %d orgs, %d user" ,
186
195
len (customRole .SitePermissions ),totalOrg ,len (customRole .OrganizationPermissions ),len (customRole .UserPermissions ))
187
196
_ ,err = cliui .Prompt (inv , cliui.PromptOptions {
188
197
Text :"Are you sure you wish to update the role? " + preview ,
@@ -276,7 +285,7 @@ customRoleLoop:
276
285
for {
277
286
selected ,err := cliui .Select (inv , cliui.SelectOptions {
278
287
Message :"Select which resources to edit permissions" ,
279
- Options :append (permissionPreviews (role ,allowedResources ),done ,abort ),
288
+ Options :append (permissionPreviews (role ,orgID , allowedResources ),done ,abort ),
280
289
})
281
290
if err != nil {
282
291
return role ,xerrors .Errorf ("selecting resource: %w" ,err )
@@ -293,7 +302,7 @@ customRoleLoop:
293
302
actions ,err := cliui .MultiSelect (inv , cliui.MultiSelectOptions {
294
303
Message :fmt .Sprintf ("Select actions to allow across the whole deployment for resources=%q" ,resource ),
295
304
Options :slice .ToStrings (codersdk .RBACResourceActions [codersdk .RBACResource (resource )]),
296
- Defaults :defaultActions (role ,resource ),
305
+ Defaults :defaultActions (role ,orgID , resource ),
297
306
})
298
307
if err != nil {
299
308
return role ,xerrors .Errorf ("selecting actions for resource %q: %w" ,resource ,err )
@@ -309,6 +318,10 @@ customRoleLoop:
309
318
}
310
319
311
320
func applyOrgResourceActions (role * codersdk.Role ,orgID uuid.UUID ,resource string ,actions []string ) {
321
+ if role .OrganizationPermissions == nil {
322
+ role .OrganizationPermissions = map [string ][]codersdk.Permission {}
323
+ }
324
+
312
325
if _ ,ok := role .OrganizationPermissions [orgID .String ()];! ok {
313
326
role .OrganizationPermissions [orgID .String ()]= []codersdk.Permission {}
314
327
}
@@ -334,27 +347,35 @@ func applyOrgResourceActions(role *codersdk.Role, orgID uuid.UUID, resource stri
334
347
role .OrganizationPermissions [orgID .String ()]= keep
335
348
}
336
349
337
- func defaultActions (role * codersdk.Role ,resource string ) []string {
350
+ func defaultActions (role * codersdk.Role ,orgID uuid.UUID ,resource string ) []string {
351
+ if role .OrganizationPermissions == nil {
352
+ role .OrganizationPermissions = map [string ][]codersdk.Permission {}
353
+ }
354
+
338
355
defaults := make ([]string ,0 )
339
- for _ ,perm := range role .SitePermissions {
356
+ for _ ,perm := range role .OrganizationPermissions [ orgID . String ()] {
340
357
if string (perm .ResourceType )== resource {
341
358
defaults = append (defaults ,string (perm .Action ))
342
359
}
343
360
}
344
361
return defaults
345
362
}
346
363
347
- func permissionPreviews (role * codersdk.Role ,resources []codersdk.RBACResource ) []string {
364
+ func permissionPreviews (role * codersdk.Role ,orgID uuid. UUID , resources []codersdk.RBACResource ) []string {
348
365
previews := make ([]string ,0 ,len (resources ))
349
366
for _ ,resource := range resources {
350
- previews = append (previews ,permissionPreview (role ,resource ))
367
+ previews = append (previews ,permissionPreview (role ,orgID , resource ))
351
368
}
352
369
return previews
353
370
}
354
371
355
- func permissionPreview (role * codersdk.Role ,resource codersdk.RBACResource )string {
372
+ func permissionPreview (role * codersdk.Role ,orgID uuid.UUID ,resource codersdk.RBACResource )string {
373
+ if role .OrganizationPermissions == nil {
374
+ role .OrganizationPermissions = map [string ][]codersdk.Permission {}
375
+ }
376
+
356
377
count := 0
357
- for _ ,perm := range role .SitePermissions {
378
+ for _ ,perm := range role .OrganizationPermissions [ orgID . String ()] {
358
379
if perm .ResourceType == resource {
359
380
count ++
360
381
}
@@ -377,8 +398,12 @@ func orgPermissionString(perms map[string][]codersdk.Permission) string {
377
398
for _ ,o := range perms {
378
399
totalOrg += len (o )
379
400
}
380
- return fmt .Sprintf ("%d over %d organizations" ,
381
- totalOrg ,len (perms ))
401
+ plural := ""
402
+ if len (perms )> 1 {
403
+ plural = "s"
404
+ }
405
+ return fmt .Sprintf ("%d over %d organization%s" ,
406
+ totalOrg ,len (perms ),plural )
382
407
}
383
408
384
409
type roleTableRow struct {