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

Commitfad97a1

Browse files
authored
fix(cli): allow generating partial support bundles with no workspace or agent (#12933)
* fix(cli): allow generating partial support bundles with no workspace or agent* nolint control flag
1 parenta231b5a commitfad97a1

File tree

2 files changed

+142
-46
lines changed

2 files changed

+142
-46
lines changed

‎cli/support.go

Lines changed: 33 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313
"text/tabwriter"
1414
"time"
1515

16+
"github.com/google/uuid"
1617
"golang.org/x/xerrors"
1718

1819
"cdr.dev/slog"
@@ -114,31 +115,40 @@ func (r *RootCmd) supportBundle() *serpent.Command {
114115
client.URL=u
115116
}
116117

117-
iflen(inv.Args)==0 {
118-
returnxerrors.Errorf("must specify workspace name")
119-
}
120-
ws,err:=namedWorkspace(inv.Context(),client,inv.Args[0])
121-
iferr!=nil {
122-
returnxerrors.Errorf("invalid workspace: %w",err)
123-
}
124-
cliLog.Debug(inv.Context(),"found workspace",
125-
slog.F("workspace_name",ws.Name),
126-
slog.F("workspace_id",ws.ID),
118+
var (
119+
wsID uuid.UUID
120+
agtID uuid.UUID
127121
)
128122

129-
agentName:=""
130-
iflen(inv.Args)>1 {
131-
agentName=inv.Args[1]
132-
}
123+
iflen(inv.Args)==0 {
124+
cliLog.Warn(inv.Context(),"no workspace specified")
125+
_,_=fmt.Fprintln(inv.Stderr,"Warning: no workspace specified. This will result in incomplete information.")
126+
}else {
127+
ws,err:=namedWorkspace(inv.Context(),client,inv.Args[0])
128+
iferr!=nil {
129+
returnxerrors.Errorf("invalid workspace: %w",err)
130+
}
131+
cliLog.Debug(inv.Context(),"found workspace",
132+
slog.F("workspace_name",ws.Name),
133+
slog.F("workspace_id",ws.ID),
134+
)
135+
wsID=ws.ID
136+
agentName:=""
137+
iflen(inv.Args)>1 {
138+
agentName=inv.Args[1]
139+
}
133140

134-
agt,found:=findAgent(agentName,ws.LatestBuild.Resources)
135-
if!found {
136-
returnxerrors.Errorf("could not find agent named %q for workspace",agentName)
141+
agt,found:=findAgent(agentName,ws.LatestBuild.Resources)
142+
if!found {
143+
cliLog.Warn(inv.Context(),"could not find agent in workspace",slog.F("agent_name",agentName))
144+
}else {
145+
cliLog.Debug(inv.Context(),"found workspace agent",
146+
slog.F("agent_name",agt.Name),
147+
slog.F("agent_id",agt.ID),
148+
)
149+
agtID=agt.ID
150+
}
137151
}
138-
cliLog.Debug(inv.Context(),"found workspace agent",
139-
slog.F("agent_name",agt.Name),
140-
slog.F("agent_id",agt.ID),
141-
)
142152

143153
ifoutputPath=="" {
144154
cwd,err:=filepath.Abs(".")
@@ -165,8 +175,8 @@ func (r *RootCmd) supportBundle() *serpent.Command {
165175
Client:client,
166176
// Support adds a sink so we don't need to supply one ourselves.
167177
Log:clientLog,
168-
WorkspaceID:ws.ID,
169-
AgentID:agt.ID,
178+
WorkspaceID:wsID,
179+
AgentID:agtID,
170180
}
171181

172182
bun,err:=support.Run(inv.Context(),&deps)

‎cli/support_test.go

Lines changed: 109 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -95,33 +95,50 @@ func TestSupportBundle(t *testing.T) {
9595
clitest.SetupConfig(t,client,root)
9696
err=inv.Run()
9797
require.NoError(t,err)
98-
assertBundleContents(t,path,secretValue)
98+
assertBundleContents(t,path,true,true, []string{secretValue})
9999
})
100100

101101
t.Run("NoWorkspace",func(t*testing.T) {
102102
t.Parallel()
103-
client:=coderdtest.New(t,nil)
103+
vardc codersdk.DeploymentConfig
104+
secretValue:=uuid.NewString()
105+
seedSecretDeploymentOptions(t,&dc,secretValue)
106+
client:=coderdtest.New(t,&coderdtest.Options{
107+
DeploymentValues:dc.Values,
108+
})
104109
_=coderdtest.CreateFirstUser(t,client)
105-
inv,root:=clitest.New(t,"support","bundle","--yes")
110+
111+
d:=t.TempDir()
112+
path:=filepath.Join(d,"bundle.zip")
113+
inv,root:=clitest.New(t,"support","bundle","--output-file",path,"--yes")
106114
//nolint: gocritic // requires owner privilege
107115
clitest.SetupConfig(t,client,root)
108116
err:=inv.Run()
109-
require.ErrorContains(t,err,"must specify workspace name")
117+
require.NoError(t,err)
118+
assertBundleContents(t,path,false,false, []string{secretValue})
110119
})
111120

112121
t.Run("NoAgent",func(t*testing.T) {
113122
t.Parallel()
114-
client,db:=coderdtest.NewWithDatabase(t,nil)
123+
vardc codersdk.DeploymentConfig
124+
secretValue:=uuid.NewString()
125+
seedSecretDeploymentOptions(t,&dc,secretValue)
126+
client,db:=coderdtest.NewWithDatabase(t,&coderdtest.Options{
127+
DeploymentValues:dc.Values,
128+
})
115129
admin:=coderdtest.CreateFirstUser(t,client)
116130
r:=dbfake.WorkspaceBuild(t,db, database.Workspace{
117131
OrganizationID:admin.OrganizationID,
118132
OwnerID:admin.UserID,
119133
}).Do()// without agent!
120-
inv,root:=clitest.New(t,"support","bundle",r.Workspace.Name,"--yes")
134+
d:=t.TempDir()
135+
path:=filepath.Join(d,"bundle.zip")
136+
inv,root:=clitest.New(t,"support","bundle",r.Workspace.Name,"--output-file",path,"--yes")
121137
//nolint: gocritic // requires owner privilege
122138
clitest.SetupConfig(t,client,root)
123139
err:=inv.Run()
124-
require.ErrorContains(t,err,"could not find agent")
140+
require.NoError(t,err)
141+
assertBundleContents(t,path,true,false, []string{secretValue})
125142
})
126143

127144
t.Run("NoPrivilege",func(t*testing.T) {
@@ -140,7 +157,8 @@ func TestSupportBundle(t *testing.T) {
140157
})
141158
}
142159

143-
funcassertBundleContents(t*testing.T,pathstring,badValues...string) {
160+
// nolint:revive // It's a control flag, but this is just a test.
161+
funcassertBundleContents(t*testing.T,pathstring,wantWorkspacebool,wantAgentbool,badValues []string) {
144162
t.Helper()
145163
r,err:=zip.OpenReader(path)
146164
require.NoError(t,err,"open zip file")
@@ -173,64 +191,132 @@ func assertBundleContents(t *testing.T, path string, badValues ...string) {
173191
case"network/netcheck.json":
174192
varv workspacesdk.AgentConnectionInfo
175193
decodeJSONFromZip(t,f,&v)
194+
if!wantAgent||!wantWorkspace {
195+
require.Empty(t,v,"expected connection info to be empty")
196+
continue
197+
}
176198
require.NotEmpty(t,v,"connection info should not be empty")
177199
case"workspace/workspace.json":
178200
varv codersdk.Workspace
179201
decodeJSONFromZip(t,f,&v)
202+
if!wantWorkspace {
203+
require.Empty(t,v,"expected workspace to be empty")
204+
continue
205+
}
180206
require.NotEmpty(t,v,"workspace should not be empty")
181207
case"workspace/build_logs.txt":
182208
bs:=readBytesFromZip(t,f)
209+
if!wantWorkspace||!wantAgent {
210+
require.Empty(t,bs,"expected workspace build logs to be empty")
211+
continue
212+
}
183213
require.Contains(t,string(bs),"provision done")
214+
case"workspace/template.json":
215+
varv codersdk.Template
216+
decodeJSONFromZip(t,f,&v)
217+
if!wantWorkspace {
218+
require.Empty(t,v,"expected workspace template to be empty")
219+
continue
220+
}
221+
require.NotEmpty(t,v,"workspace template should not be empty")
222+
case"workspace/template_version.json":
223+
varv codersdk.TemplateVersion
224+
decodeJSONFromZip(t,f,&v)
225+
if!wantWorkspace {
226+
require.Empty(t,v,"expected workspace template version to be empty")
227+
continue
228+
}
229+
require.NotEmpty(t,v,"workspace template version should not be empty")
230+
case"workspace/parameters.json":
231+
varv []codersdk.WorkspaceBuildParameter
232+
decodeJSONFromZip(t,f,&v)
233+
if!wantWorkspace {
234+
require.Empty(t,v,"expected workspace parameters to be empty")
235+
continue
236+
}
237+
require.NotNil(t,v,"workspace parameters should not be nil")
238+
case"workspace/template_file.zip":
239+
bs:=readBytesFromZip(t,f)
240+
if!wantWorkspace {
241+
require.Empty(t,bs,"expected template file to be empty")
242+
continue
243+
}
244+
require.NotNil(t,bs,"template file should not be nil")
184245
case"agent/agent.json":
185246
varv codersdk.WorkspaceAgent
186247
decodeJSONFromZip(t,f,&v)
248+
if!wantAgent {
249+
require.Empty(t,v,"expected agent to be empty")
250+
continue
251+
}
187252
require.NotEmpty(t,v,"agent should not be empty")
188253
case"agent/listening_ports.json":
189254
varv codersdk.WorkspaceAgentListeningPortsResponse
190255
decodeJSONFromZip(t,f,&v)
256+
if!wantAgent {
257+
require.Empty(t,v,"expected agent listening ports to be empty")
258+
continue
259+
}
191260
require.NotEmpty(t,v,"agent listening ports should not be empty")
192261
case"agent/logs.txt":
193262
bs:=readBytesFromZip(t,f)
263+
if!wantAgent {
264+
require.Empty(t,bs,"expected agent logs to be empty")
265+
continue
266+
}
194267
require.NotEmpty(t,bs,"logs should not be empty")
195268
case"agent/agent_magicsock.html":
196269
bs:=readBytesFromZip(t,f)
270+
if!wantAgent {
271+
require.Empty(t,bs,"expected agent magicsock to be empty")
272+
continue
273+
}
197274
require.NotEmpty(t,bs,"agent magicsock should not be empty")
198275
case"agent/client_magicsock.html":
199276
bs:=readBytesFromZip(t,f)
277+
if!wantAgent {
278+
require.Empty(t,bs,"expected client magicsock to be empty")
279+
continue
280+
}
200281
require.NotEmpty(t,bs,"client magicsock should not be empty")
201282
case"agent/manifest.json":
202283
varv agentsdk.Manifest
203284
decodeJSONFromZip(t,f,&v)
285+
if!wantAgent {
286+
require.Empty(t,v,"expected agent manifest to be empty")
287+
continue
288+
}
204289
require.NotEmpty(t,v,"agent manifest should not be empty")
205290
case"agent/peer_diagnostics.json":
206291
varv*tailnet.PeerDiagnostics
207292
decodeJSONFromZip(t,f,&v)
293+
if!wantAgent {
294+
require.Empty(t,v,"expected peer diagnostics to be empty")
295+
continue
296+
}
208297
require.NotEmpty(t,v,"peer diagnostics should not be empty")
209298
case"agent/ping_result.json":
210299
varv*ipnstate.PingResult
211300
decodeJSONFromZip(t,f,&v)
301+
if!wantAgent {
302+
require.Empty(t,v,"expected ping result to be empty")
303+
continue
304+
}
212305
require.NotEmpty(t,v,"ping result should not be empty")
213306
case"agent/prometheus.txt":
214307
bs:=readBytesFromZip(t,f)
308+
if!wantAgent {
309+
require.Empty(t,bs,"expected agent prometheus metrics to be empty")
310+
continue
311+
}
215312
require.NotEmpty(t,bs,"agent prometheus metrics should not be empty")
216313
case"agent/startup_logs.txt":
217314
bs:=readBytesFromZip(t,f)
315+
if!wantAgent {
316+
require.Empty(t,bs,"expected agent startup logs to be empty")
317+
continue
318+
}
218319
require.Contains(t,string(bs),"started up")
219-
case"workspace/template.json":
220-
varv codersdk.Template
221-
decodeJSONFromZip(t,f,&v)
222-
require.NotEmpty(t,v,"workspace template should not be empty")
223-
case"workspace/template_version.json":
224-
varv codersdk.TemplateVersion
225-
decodeJSONFromZip(t,f,&v)
226-
require.NotEmpty(t,v,"workspace template version should not be empty")
227-
case"workspace/parameters.json":
228-
varv []codersdk.WorkspaceBuildParameter
229-
decodeJSONFromZip(t,f,&v)
230-
require.NotNil(t,v,"workspace parameters should not be nil")
231-
case"workspace/template_file.zip":
232-
bs:=readBytesFromZip(t,f)
233-
require.NotNil(t,bs,"template file should not be nil")
234320
case"logs.txt":
235321
bs:=readBytesFromZip(t,f)
236322
require.NotEmpty(t,bs,"logs should not be empty")

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp