Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings
This repository was archived by the owner on Aug 30, 2024. It is now read-only.
/coder-v1-cliPublic archive

Commitd75e755

Browse files
committed
Abstract env resource grouping and label properly
1 parent26b8ecc commitd75e755

File tree

1 file changed

+111
-23
lines changed

1 file changed

+111
-23
lines changed

‎internal/cmd/resourcemanager.go

Lines changed: 111 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ func makeResourceCmd() *cobra.Command {
2323
}
2424

2525
funcresourceTop()*cobra.Command {
26+
vargroupstring
2627
cmd:=&cobra.Command{
2728
Use:"top",
2829
RunE:func(cmd*cobra.Command,args []string)error {
@@ -34,69 +35,136 @@ func resourceTop() *cobra.Command {
3435

3536
// NOTE: it's not worth parrallelizing these calls yet given that this specific endpoint
3637
// takes about 20x times longer than the other two
37-
envs,err:=client.Environments(ctx)
38+
allEnvs,err:=client.Environments(ctx)
3839
iferr!=nil {
3940
returnxerrors.Errorf("get environments %w",err)
4041
}
41-
42-
userEnvs:=make(map[string][]coder.Environment)
43-
for_,e:=rangeenvs {
44-
userEnvs[e.UserID]=append(userEnvs[e.UserID],e)
42+
// only include environments whose last status was "ON"
43+
envs:=make([]coder.Environment,0)
44+
for_,e:=rangeallEnvs {
45+
ife.LatestStat.ContainerStatus==coder.EnvironmentOn {
46+
envs=append(envs,e)
47+
}
4548
}
4649

4750
users,err:=client.Users(ctx)
4851
iferr!=nil {
4952
returnxerrors.Errorf("get users: %w",err)
5053
}
5154

52-
orgIDMap:=make(map[string]coder.Organization)
53-
orglist,err:=client.Organizations(ctx)
55+
orgs,err:=client.Organizations(ctx)
5456
iferr!=nil {
5557
returnxerrors.Errorf("get organizations: %w",err)
5658
}
57-
for_,o:=rangeorglist {
58-
orgIDMap[o.ID]=o
59+
60+
vargroups []groupable
61+
varlabelerenvLabeler
62+
switchgroup {
63+
case"user":
64+
userEnvs:=make(map[string][]coder.Environment,len(users))
65+
for_,e:=rangeenvs {
66+
userEnvs[e.UserID]=append(userEnvs[e.UserID],e)
67+
}
68+
for_,u:=rangeusers {
69+
groups=append(groups,userGrouping{user:u,envs:userEnvs[u.ID]})
70+
}
71+
orgIDMap:=make(map[string]coder.Organization)
72+
for_,o:=rangeorgs {
73+
orgIDMap[o.ID]=o
74+
}
75+
labeler=orgLabeler{orgIDMap}
76+
case"org":
77+
orgEnvs:=make(map[string][]coder.Environment,len(orgs))
78+
for_,e:=rangeenvs {
79+
orgEnvs[e.OrganizationID]=append(orgEnvs[e.OrganizationID],e)
80+
}
81+
for_,o:=rangeorgs {
82+
groups=append(groups,orgGrouping{org:o,envs:orgEnvs[o.ID]})
83+
}
84+
userIDMap:=make(map[string]coder.User)
85+
for_,u:=rangeusers {
86+
userIDMap[u.ID]=u
87+
}
88+
labeler=userLabeler{userIDMap}
89+
default:
90+
returnxerrors.Errorf("unknown --group %q",group)
5991
}
6092

61-
printResourceTop(os.Stdout,users,orgIDMap,userEnvs)
93+
printResourceTop(os.Stdout,groups,labeler)
6294
returnnil
6395
},
6496
}
97+
cmd.Flags().StringVar(&group,"group","user","the grouping parameter (user|org)")
6598

6699
returncmd
67100
}
68101

69-
funcprintResourceTop(writer io.Writer,users []coder.User,orgIDMapmap[string]coder.Organization,userEnvsmap[string][]coder.Environment) {
102+
// groupable specifies a structure capable of being an aggregation group of environments (user, org, all)
103+
typegroupableinterface {
104+
header()string
105+
environments() []coder.Environment
106+
}
107+
108+
typeuserGroupingstruct {
109+
user coder.User
110+
envs []coder.Environment
111+
}
112+
113+
func (uuserGrouping)environments() []coder.Environment {
114+
returnu.envs
115+
}
116+
117+
func (uuserGrouping)header()string {
118+
returnfmt.Sprintf("%s\t(%s)",truncate(u.user.Name,20,"..."),u.user.Email)
119+
}
120+
121+
typeorgGroupingstruct {
122+
org coder.Organization
123+
envs []coder.Environment
124+
}
125+
126+
func (oorgGrouping)environments() []coder.Environment {
127+
returno.envs
128+
}
129+
130+
func (oorgGrouping)header()string {
131+
plural:="s"
132+
iflen(o.org.Members)<2 {
133+
plural=""
134+
}
135+
returnfmt.Sprintf("%s\t(%v member%s)",truncate(o.org.Name,20,"..."),len(o.org.Members),plural)
136+
}
137+
138+
funcprintResourceTop(writer io.Writer,groups []groupable,labelerenvLabeler) {
70139
tabwriter:=tabwriter.NewWriter(writer,0,0,4,' ',0)
71140
deferfunc() {_=tabwriter.Flush() }()
72141

73-
varuserResources []aggregatedUser
74-
for_,u:=rangeusers {
142+
varuserResources []aggregatedResources
143+
for_,group:=rangegroups {
75144
// truncate user names to ensure tabwriter doesn't push our entire table too far
76-
u.Name=truncate(u.Name,20,"...")
77-
userResources=append(userResources,aggregatedUser{User:u,resources:aggregateEnvResources(userEnvs[u.ID])})
145+
userResources=append(userResources,aggregatedResources{groupable:group,resources:aggregateEnvResources(group.environments())})
78146
}
79147
sort.Slice(userResources,func(i,jint)bool {
80148
returnuserResources[i].cpuAllocation>userResources[j].cpuAllocation
81149
})
82150

83151
for_,u:=rangeuserResources {
84-
_,_=fmt.Fprintf(tabwriter,"%s\t(%s)\t%s",u.Name,u.Email,u.resources)
152+
_,_=fmt.Fprintf(tabwriter,"%s\t%s",u.header(),u.resources)
85153
ifverbose {
86-
iflen(userEnvs[u.ID])>0 {
154+
iflen(u.environments())>0 {
87155
_,_=fmt.Fprintf(tabwriter,"\f")
88156
}
89-
for_,env:=rangeuserEnvs[u.ID] {
157+
for_,env:=rangeu.environments() {
90158
_,_=fmt.Fprintf(tabwriter,"\t")
91-
_,_=fmt.Fprintln(tabwriter,fmtEnvResources(env,orgIDMap))
159+
_,_=fmt.Fprintln(tabwriter,fmtEnvResources(env,labeler))
92160
}
93161
}
94162
_,_=fmt.Fprint(tabwriter,"\n")
95163
}
96164
}
97165

98-
typeaggregatedUserstruct {
99-
coder.User
166+
typeaggregatedResourcesstruct {
167+
groupable
100168
resources
101169
}
102170

@@ -109,8 +177,28 @@ func resourcesFromEnv(env coder.Environment) resources {
109177
}
110178
}
111179

112-
funcfmtEnvResources(env coder.Environment,orgsmap[string]coder.Organization)string {
113-
returnfmt.Sprintf("%s\t%s\t[org: %s]",env.Name,resourcesFromEnv(env),orgs[env.OrganizationID].Name)
180+
funcfmtEnvResources(env coder.Environment,labelerenvLabeler)string {
181+
returnfmt.Sprintf("%s\t%s\t%s",env.Name,resourcesFromEnv(env),labeler.label(env))
182+
}
183+
184+
typeenvLabelerinterface {
185+
label(coder.Environment)string
186+
}
187+
188+
typeorgLabelerstruct {
189+
orgMapmap[string]coder.Organization
190+
}
191+
192+
func (oorgLabeler)label(e coder.Environment)string {
193+
returnfmt.Sprintf("[org: %s]",o.orgMap[e.OrganizationID].Name)
194+
}
195+
196+
typeuserLabelerstruct {
197+
userMapmap[string]coder.User
198+
}
199+
200+
func (uuserLabeler)label(e coder.Environment)string {
201+
returnfmt.Sprintf("[user: %s]",u.userMap[e.UserID].Email)
114202
}
115203

116204
funcaggregateEnvResources(envs []coder.Environment)resources {

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp