Skip to content

Commit 9200779

Browse files
committed
Merge remote-tracking branch 'origin/main' into stevenmasley/soft_delete_versions
2 parents 3e5f91d + 2d6c4fe commit 9200779

File tree

111 files changed

+2722
-1398
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

111 files changed

+2722
-1398
lines changed

cli/agent.go

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -199,9 +199,19 @@ func (r *RootCmd) workspaceAgent() *clibase.Cmd {
199199
var exchangeToken func(context.Context) (agentsdk.AuthenticateResponse, error)
200200
switch auth {
201201
case "token":
202-
token, err := inv.ParsedFlags().GetString(varAgentToken)
203-
if err != nil {
204-
return xerrors.Errorf("CODER_AGENT_TOKEN must be set for token auth: %w", err)
202+
token, _ := inv.ParsedFlags().GetString(varAgentToken)
203+
if token == "" {
204+
tokenFile, _ := inv.ParsedFlags().GetString(varAgentTokenFile)
205+
if tokenFile != "" {
206+
tokenBytes, err := os.ReadFile(tokenFile)
207+
if err != nil {
208+
return xerrors.Errorf("read token file %q: %w", tokenFile, err)
209+
}
210+
token = strings.TrimSpace(string(tokenBytes))
211+
}
212+
}
213+
if token == "" {
214+
return xerrors.Errorf("CODER_AGENT_TOKEN or CODER_AGENT_TOKEN_FILE must be set for token auth")
205215
}
206216
client.SetSessionToken(token)
207217
case "google-instance-identity":

cli/clibase/option.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -262,6 +262,15 @@ func (optSet *OptionSet) ParseEnv(vs []EnvVar) error {
262262
}
263263

264264
envVal, ok := envs[opt.Env]
265+
if !ok {
266+
// Homebrew strips all environment variables that do not start with `HOMEBREW_`.
267+
// This prevented using brew to invoke the Coder agent, because the environment
268+
// variables to not get passed down.
269+
//
270+
// A customer wanted to use their custom tap inside a workspace, which was failing
271+
// because the agent lacked the environment variables to authenticate with Git.
272+
envVal, ok = envs[`HOMEBREW_`+opt.Env]
273+
}
265274
// Currently, empty values are treated as if the environment variable is
266275
// unset. This behavior is technically not correct as there is now no
267276
// way for a user to change a Default value to an empty string from

cli/clibase/option_test.go

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,26 @@ func TestOptionSet_ParseEnv(t *testing.T) {
206206
require.NoError(t, err)
207207
require.EqualValues(t, expected, actual.Value)
208208
})
209+
210+
t.Run("Homebrew", func(t *testing.T) {
211+
t.Parallel()
212+
213+
var agentToken clibase.String
214+
215+
os := clibase.OptionSet{
216+
clibase.Option{
217+
Name: "Agent Token",
218+
Value: &agentToken,
219+
Env: "AGENT_TOKEN",
220+
},
221+
}
222+
223+
err := os.ParseEnv([]clibase.EnvVar{
224+
{Name: "HOMEBREW_AGENT_TOKEN", Value: "foo"},
225+
})
226+
require.NoError(t, err)
227+
require.EqualValues(t, "foo", agentToken)
228+
})
209229
}
210230

211231
func TestOptionSet_JsonMarshal(t *testing.T) {

cli/root.go

Lines changed: 38 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ const (
5555
varURL = "url"
5656
varToken = "token"
5757
varAgentToken = "agent-token"
58+
varAgentTokenFile = "agent-token-file"
5859
varAgentURL = "agent-url"
5960
varHeader = "header"
6061
varHeaderCommand = "header-command"
@@ -71,7 +72,9 @@ const (
7172
envSessionToken = "CODER_SESSION_TOKEN"
7273
//nolint:gosec
7374
envAgentToken = "CODER_AGENT_TOKEN"
74-
envURL = "CODER_URL"
75+
//nolint:gosec
76+
envAgentTokenFile = "CODER_AGENT_TOKEN_FILE"
77+
envURL = "CODER_URL"
7578
)
7679

7780
var errUnauthenticated = xerrors.New(notLoggedInMessage)
@@ -159,6 +162,9 @@ func (r *RootCmd) Command(subcommands []*clibase.Cmd) (*clibase.Cmd, error) {
159162
},
160163
),
161164
Handler: func(i *clibase.Invocation) error {
165+
if r.versionFlag {
166+
return r.version(defaultVersionInfo).Handler(i)
167+
}
162168
// The GIT_ASKPASS environment variable must point at
163169
// a binary with no arguments. To prevent writing
164170
// cross-platform scripts to invoke the Coder binary
@@ -325,6 +331,14 @@ func (r *RootCmd) Command(subcommands []*clibase.Cmd) (*clibase.Cmd, error) {
325331
Hidden: true,
326332
Group: globalGroup,
327333
},
334+
{
335+
Flag: varAgentTokenFile,
336+
Env: envAgentTokenFile,
337+
Description: "A file containing an agent authentication token.",
338+
Value: clibase.StringOf(&r.agentTokenFile),
339+
Hidden: true,
340+
Group: globalGroup,
341+
},
328342
{
329343
Flag: varAgentURL,
330344
Env: "CODER_AGENT_URL",
@@ -407,6 +421,15 @@ func (r *RootCmd) Command(subcommands []*clibase.Cmd) (*clibase.Cmd, error) {
407421
Value: clibase.StringOf(&r.globalConfig),
408422
Group: globalGroup,
409423
},
424+
{
425+
Flag: "version",
426+
// This was requested by a customer to assist with their migration.
427+
// They have two Coder CLIs, and want to tell the difference by running
428+
// the same base command.
429+
Description: "Run the version command. Useful for v1 customers migrating to v2.",
430+
Value: clibase.BoolOf(&r.versionFlag),
431+
Hidden: true,
432+
},
410433
}
411434

412435
err := cmd.PrepareAll()
@@ -434,18 +457,20 @@ func LoggerFromContext(ctx context.Context) (slog.Logger, bool) {
434457

435458
// RootCmd contains parameters and helpers useful to all commands.
436459
type RootCmd struct {
437-
clientURL *url.URL
438-
token string
439-
globalConfig string
440-
header []string
441-
headerCommand string
442-
agentToken string
443-
agentURL *url.URL
444-
forceTTY bool
445-
noOpen bool
446-
verbose bool
447-
disableDirect bool
448-
debugHTTP bool
460+
clientURL *url.URL
461+
token string
462+
globalConfig string
463+
header []string
464+
headerCommand string
465+
agentToken string
466+
agentTokenFile string
467+
agentURL *url.URL
468+
forceTTY bool
469+
noOpen bool
470+
verbose bool
471+
versionFlag bool
472+
disableDirect bool
473+
debugHTTP bool
449474

450475
noVersionCheck bool
451476
noFeatureWarning bool

cli/server.go

Lines changed: 22 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -938,7 +938,7 @@ func (r *RootCmd) Server(newAPI func(context.Context, *coderd.Options) (*coderd.
938938
autobuildTicker := time.NewTicker(vals.AutobuildPollInterval.Value())
939939
defer autobuildTicker.Stop()
940940
autobuildExecutor := autobuild.NewExecutor(
941-
ctx, options.Database, options.Pubsub, coderAPI.TemplateScheduleStore, logger, autobuildTicker.C)
941+
ctx, options.Database, options.Pubsub, coderAPI.TemplateScheduleStore, &coderAPI.Auditor, logger, autobuildTicker.C)
942942
autobuildExecutor.Run()
943943

944944
hangDetectorTicker := time.NewTicker(vals.JobHangDetectorInterval.Value())
@@ -1875,45 +1875,49 @@ func BuildLogger(inv *clibase.Invocation, cfg *codersdk.DeploymentValues) (slog.
18751875
}, nil
18761876
}
18771877

1878-
func ConnectToPostgres(ctx context.Context, logger slog.Logger, driver string, dbURL string) (*sql.DB, error) {
1878+
func ConnectToPostgres(ctx context.Context, logger slog.Logger, driver string, dbURL string) (sqlDB *sql.DB, err error) {
18791879
logger.Debug(ctx, "connecting to postgresql")
18801880

18811881
// Try to connect for 30 seconds.
18821882
ctx, cancel := context.WithTimeout(ctx, 30*time.Second)
18831883
defer cancel()
18841884

1885-
var (
1886-
sqlDB *sql.DB
1887-
err error
1888-
ok = false
1889-
tries int
1890-
)
1885+
defer func() {
1886+
if err == nil {
1887+
return
1888+
}
1889+
if sqlDB != nil {
1890+
_ = sqlDB.Close()
1891+
sqlDB = nil
1892+
}
1893+
logger.Error(ctx, "connect to postgres failed", slog.Error(err))
1894+
}()
1895+
1896+
var tries int
18911897
for r := retry.New(time.Second, 3*time.Second); r.Wait(ctx); {
18921898
tries++
18931899

18941900
sqlDB, err = sql.Open(driver, dbURL)
18951901
if err != nil {
1896-
logger.Warn(ctx, "connect to postgres; retrying", slog.Error(err), slog.F("try", tries))
1902+
logger.Warn(ctx, "connect to postgres: retrying", slog.Error(err), slog.F("try", tries))
18971903
continue
18981904
}
18991905

19001906
err = pingPostgres(ctx, sqlDB)
19011907
if err != nil {
1902-
logger.Warn(ctx, "ping postgres; retrying", slog.Error(err), slog.F("try", tries))
1908+
logger.Warn(ctx, "ping postgres: retrying", slog.Error(err), slog.F("try", tries))
1909+
_ = sqlDB.Close()
1910+
sqlDB = nil
19031911
continue
19041912
}
19051913

19061914
break
19071915
}
1908-
// Make sure we close the DB in case it opened but the ping failed for some
1909-
// reason.
1910-
defer func() {
1911-
if !ok && sqlDB != nil {
1912-
_ = sqlDB.Close()
1913-
}
1914-
}()
1916+
if err == nil {
1917+
err = ctx.Err()
1918+
}
19151919
if err != nil {
1916-
return nil, xerrors.Errorf("connect to postgres; tries %d; last error: %w", tries, err)
1920+
return nil, xerrors.Errorf("unable to connect after %d tries; last error: %w", tries, err)
19171921
}
19181922

19191923
// Ensure the PostgreSQL version is >=13.0.0!
@@ -1958,7 +1962,6 @@ func ConnectToPostgres(ctx context.Context, logger slog.Logger, driver string, d
19581962
// of connection churn.
19591963
sqlDB.SetMaxIdleConns(3)
19601964

1961-
ok = true
19621965
return sqlDB, nil
19631966
}
19641967

cli/templatecreate.go

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -47,16 +47,6 @@ func (r *RootCmd) templateCreate() *clibase.Cmd {
4747
),
4848
Handler: func(inv *clibase.Invocation) error {
4949
if failureTTL != 0 || inactivityTTL != 0 || maxTTL != 0 {
50-
// This call can be removed when workspace_actions is no longer experimental
51-
experiments, exErr := client.Experiments(inv.Context())
52-
if exErr != nil {
53-
return xerrors.Errorf("get experiments: %w", exErr)
54-
}
55-
56-
if !experiments.Enabled(codersdk.ExperimentWorkspaceActions) {
57-
return xerrors.Errorf("--failure-ttl and --inactivityTTL are experimental features. Use the workspace_actions CODER_EXPERIMENTS flag to set these configuration values.")
58-
}
59-
6050
entitlements, err := client.Entitlements(inv.Context())
6151
var sdkErr *codersdk.Error
6252
if xerrors.As(err, &sdkErr) && sdkErr.StatusCode() == http.StatusNotFound {

cli/templateedit.go

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -41,18 +41,6 @@ func (r *RootCmd) templateEdit() *clibase.Cmd {
4141
),
4242
Short: "Edit the metadata of a template by name.",
4343
Handler: func(inv *clibase.Invocation) error {
44-
// This clause can be removed when workspace_actions is no longer experimental
45-
if failureTTL != 0 || inactivityTTL != 0 {
46-
experiments, exErr := client.Experiments(inv.Context())
47-
if exErr != nil {
48-
return xerrors.Errorf("get experiments: %w", exErr)
49-
}
50-
51-
if !experiments.Enabled(codersdk.ExperimentWorkspaceActions) {
52-
return xerrors.Errorf("--failure-ttl and --inactivityTTL are experimental features. Use the workspace_actions CODER_EXPERIMENTS flag to set these configuration values.")
53-
}
54-
}
55-
5644
unsetAutostopRequirementDaysOfWeek := len(autostopRequirementDaysOfWeek) == 1 && autostopRequirementDaysOfWeek[0] == "none"
5745
requiresEntitlement := (len(autostopRequirementDaysOfWeek) > 0 && !unsetAutostopRequirementDaysOfWeek) ||
5846
autostopRequirementWeeks > 0 ||

coderd/apidoc/docs.go

Lines changed: 4 additions & 4 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

coderd/apidoc/swagger.json

Lines changed: 4 additions & 4 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)