1
1
package cli
2
2
3
3
import (
4
+ "context"
4
5
"fmt"
5
6
"regexp"
6
7
@@ -13,12 +14,6 @@ import (
13
14
14
15
const defaultGroupDisplay = "-"
15
16
16
- type workspaceShareRow struct {
17
- User string `table:"user"`
18
- Group string `table:"group,default_sort"`
19
- Role codersdk.WorkspaceRole `table:"role"`
20
- }
21
-
22
17
func (r * RootCmd ) sharing () * serpent.Command {
23
18
orgContext := NewOrganizationContext ()
24
19
@@ -29,26 +24,59 @@ func (r *RootCmd) sharing() *serpent.Command {
29
24
Handler : func (inv * serpent.Invocation ) error {
30
25
return inv .Command .HelpHandler (inv )
31
26
},
32
- Children : []* serpent.Command {r .shareWorkspace (orgContext )},
33
- Hidden : true ,
27
+ Children : []* serpent.Command {
28
+ r .shareWorkspace (orgContext ),
29
+ r .statusWorkspaceSharing (),
30
+ },
31
+ Hidden : true ,
34
32
}
35
33
36
34
orgContext .AttachOptions (cmd )
37
35
return cmd
38
36
}
39
37
38
+ func (r * RootCmd ) statusWorkspaceSharing () * serpent.Command {
39
+ client := new (codersdk.Client )
40
+
41
+ cmd := & serpent.Command {
42
+ Use : "status <workspace>" ,
43
+ Short : "List all users and groups the given Workspace is shared with." ,
44
+ Aliases : []string {"list" },
45
+ Middleware : serpent .Chain (
46
+ r .InitClient (client ),
47
+ serpent .RequireNArgs (1 ),
48
+ ),
49
+ Handler : func (inv * serpent.Invocation ) error {
50
+ workspace , err := namedWorkspace (inv .Context (), client , inv .Args [0 ])
51
+ if err != nil {
52
+ return xerrors .Errorf ("unable to fetch Workspace %s: %w" , inv .Args [0 ], err )
53
+ }
54
+
55
+ acl , err := client .WorkspaceACL (inv .Context (), workspace .ID )
56
+ if err != nil {
57
+ return xerrors .Errorf ("unable to fetch ACL for Workspace: %w" , err )
58
+ }
59
+
60
+ out , err := workspaceACLToTable (inv .Context (), & acl )
61
+ if err != nil {
62
+ return err
63
+ }
64
+
65
+ _ , err = fmt .Fprintln (inv .Stdout , out )
66
+ return err
67
+ },
68
+ }
69
+
70
+ return cmd
71
+ }
72
+
40
73
func (r * RootCmd ) shareWorkspace (orgContext * OrganizationContext ) * serpent.Command {
41
74
var (
42
75
// Username regex taken from codersdk/name.go
43
76
nameRoleRegex = regexp .MustCompile (`(^[a-zA-Z0-9]+(?:-[a-zA-Z0-9]+)*)+(?::([A-Za-z0-9-]+))?` )
44
77
client = new (codersdk.Client )
45
78
users []string
46
79
groups []string
47
- formatter = cliui .NewOutputFormatter (
48
- cliui .TableFormat (
49
- []workspaceShareRow {}, []string {"User" , "Group" , "Role" }),
50
- cliui .JSONFormat (),
51
- )
52
80
)
53
81
54
82
cmd := & serpent.Command {
@@ -175,37 +203,12 @@ func (r *RootCmd) shareWorkspace(orgContext *OrganizationContext) *serpent.Comma
175
203
return err
176
204
}
177
205
178
- workspaceACL , err := client .WorkspaceACL (inv .Context (), workspace .ID )
206
+ acl , err := client .WorkspaceACL (inv .Context (), workspace .ID )
179
207
if err != nil {
180
208
return xerrors .Errorf ("could not fetch current workspace ACL after sharing %w" , err )
181
209
}
182
210
183
- outputRows := make ([]workspaceShareRow , 0 )
184
- for _ , user := range workspaceACL .Users {
185
- if user .Role == codersdk .WorkspaceRoleDeleted {
186
- continue
187
- }
188
-
189
- outputRows = append (outputRows , workspaceShareRow {
190
- User : user .Username ,
191
- Group : defaultGroupDisplay ,
192
- Role : user .Role ,
193
- })
194
- }
195
- for _ , group := range workspaceACL .Groups {
196
- if group .Role == codersdk .WorkspaceRoleDeleted {
197
- continue
198
- }
199
-
200
- for _ , user := range group .Members {
201
- outputRows = append (outputRows , workspaceShareRow {
202
- User : user .Username ,
203
- Group : group .Name ,
204
- Role : group .Role ,
205
- })
206
- }
207
- }
208
- out , err := formatter .Format (inv .Context (), outputRows )
211
+ out , err := workspaceACLToTable (inv .Context (), & acl )
209
212
if err != nil {
210
213
return err
211
214
}
@@ -229,3 +232,48 @@ func stringToWorkspaceRole(role string) (codersdk.WorkspaceRole, error) {
229
232
role , codersdk .WorkspaceRoleAdmin , codersdk .WorkspaceRoleUse )
230
233
}
231
234
}
235
+
236
+ func workspaceACLToTable (ctx context.Context , acl * codersdk.WorkspaceACL ) (string , error ) {
237
+ type workspaceShareRow struct {
238
+ User string `table:"user"`
239
+ Group string `table:"group,default_sort"`
240
+ Role codersdk.WorkspaceRole `table:"role"`
241
+ }
242
+
243
+ formatter := cliui .NewOutputFormatter (
244
+ cliui .TableFormat (
245
+ []workspaceShareRow {}, []string {"User" , "Group" , "Role" }),
246
+ cliui .JSONFormat ())
247
+
248
+ outputRows := make ([]workspaceShareRow , 0 )
249
+ for _ , user := range acl .Users {
250
+ if user .Role == codersdk .WorkspaceRoleDeleted {
251
+ continue
252
+ }
253
+
254
+ outputRows = append (outputRows , workspaceShareRow {
255
+ User : user .Username ,
256
+ Group : defaultGroupDisplay ,
257
+ Role : user .Role ,
258
+ })
259
+ }
260
+ for _ , group := range acl .Groups {
261
+ if group .Role == codersdk .WorkspaceRoleDeleted {
262
+ continue
263
+ }
264
+
265
+ for _ , user := range group .Members {
266
+ outputRows = append (outputRows , workspaceShareRow {
267
+ User : user .Username ,
268
+ Group : group .Name ,
269
+ Role : group .Role ,
270
+ })
271
+ }
272
+ }
273
+ out , err := formatter .Format (ctx , outputRows )
274
+ if err != nil {
275
+ return "" , err
276
+ }
277
+
278
+ return out , nil
279
+ }
0 commit comments