diff --git a/cli/organization_test.go b/cli/organization_test.go index 658498883ece8..91ecc166d5dcc 100644 --- a/cli/organization_test.go +++ b/cli/organization_test.go @@ -42,4 +42,35 @@ func TestCurrentOrganization(t *testing.T) { require.NoError(t, <-errC) pty.ExpectMatch(first.OrganizationID.String()) }) + + t.Run("UsingFlag", func(t *testing.T) { + t.Parallel() + ownerClient := coderdtest.New(t, nil) + first := coderdtest.CreateFirstUser(t, ownerClient) + // Owner is required to make orgs + client, _ := coderdtest.CreateAnotherUser(t, ownerClient, first.OrganizationID, rbac.RoleOwner()) + + ctx := testutil.Context(t, testutil.WaitMedium) + orgs := map[string]codersdk.Organization{ + "foo": {}, + "bar": {}, + } + for orgName := range orgs { + org, err := client.CreateOrganization(ctx, codersdk.CreateOrganizationRequest{ + Name: orgName, + }) + require.NoError(t, err) + orgs[orgName] = org + } + + inv, root := clitest.New(t, "organizations", "show", "current", "--only-id", "-z=bar") + clitest.SetupConfig(t, client, root) + pty := ptytest.New(t).Attach(inv) + errC := make(chan error) + go func() { + errC <- inv.Run() + }() + require.NoError(t, <-errC) + pty.ExpectMatch(orgs["bar"].ID.String()) + }) } diff --git a/cli/root.go b/cli/root.go index 4d78575c75c1e..3f97937cd8dcf 100644 --- a/cli/root.go +++ b/cli/root.go @@ -51,20 +51,21 @@ var ( ) const ( - varURL = "url" - varToken = "token" - varAgentToken = "agent-token" - varAgentTokenFile = "agent-token-file" - varAgentURL = "agent-url" - varHeader = "header" - varHeaderCommand = "header-command" - varNoOpen = "no-open" - varNoVersionCheck = "no-version-warning" - varNoFeatureWarning = "no-feature-warning" - varForceTty = "force-tty" - varVerbose = "verbose" - varDisableDirect = "disable-direct-connections" - notLoggedInMessage = "You are not logged in. Try logging in using 'coder login '." + varURL = "url" + varToken = "token" + varAgentToken = "agent-token" + varAgentTokenFile = "agent-token-file" + varAgentURL = "agent-url" + varHeader = "header" + varHeaderCommand = "header-command" + varNoOpen = "no-open" + varNoVersionCheck = "no-version-warning" + varNoFeatureWarning = "no-feature-warning" + varForceTty = "force-tty" + varVerbose = "verbose" + varOrganizationSelect = "organization" + varDisableDirect = "disable-direct-connections" + notLoggedInMessage = "You are not logged in. Try logging in using 'coder login '." envNoVersionCheck = "CODER_NO_VERSION_WARNING" envNoFeatureWarning = "CODER_NO_FEATURE_WARNING" @@ -434,6 +435,14 @@ func (r *RootCmd) Command(subcommands []*clibase.Cmd) (*clibase.Cmd, error) { Value: clibase.StringOf(&r.globalConfig), Group: globalGroup, }, + { + Flag: varOrganizationSelect, + FlagShorthand: "z", + Env: "CODER_ORGANIZATION", + Description: "Select which organization (uuid or name) to use This overrides what is present in the config file.", + Value: clibase.StringOf(&r.organizationSelect), + Group: globalGroup, + }, { Flag: "version", // This was requested by a customer to assist with their migration. @@ -455,20 +464,21 @@ func (r *RootCmd) Command(subcommands []*clibase.Cmd) (*clibase.Cmd, error) { // RootCmd contains parameters and helpers useful to all commands. type RootCmd struct { - clientURL *url.URL - token string - globalConfig string - header []string - headerCommand string - agentToken string - agentTokenFile string - agentURL *url.URL - forceTTY bool - noOpen bool - verbose bool - versionFlag bool - disableDirect bool - debugHTTP bool + clientURL *url.URL + token string + globalConfig string + header []string + headerCommand string + agentToken string + agentTokenFile string + agentURL *url.URL + forceTTY bool + noOpen bool + verbose bool + organizationSelect string + versionFlag bool + disableDirect bool + debugHTTP bool noVersionCheck bool noFeatureWarning bool @@ -701,8 +711,8 @@ func (r *RootCmd) createAgentClient() (*agentsdk.Client, error) { // CurrentOrganization returns the currently active organization for the authenticated user. func CurrentOrganization(r *RootCmd, inv *clibase.Invocation, client *codersdk.Client) (codersdk.Organization, error) { conf := r.createConfig() - selected := "" - if conf.Organization().Exists() { + selected := r.organizationSelect + if selected == "" && conf.Organization().Exists() { org, err := conf.Organization().Read() if err != nil { return codersdk.Organization{}, fmt.Errorf("read selected organization from config file %q: %w", conf.Organization(), err) diff --git a/cli/testdata/coder_--help.golden b/cli/testdata/coder_--help.golden index 501a336915128..fc0785ee92814 100644 --- a/cli/testdata/coder_--help.golden +++ b/cli/testdata/coder_--help.golden @@ -82,6 +82,10 @@ variables or flags. --no-version-warning bool, $CODER_NO_VERSION_WARNING Suppress warning when client and server versions do not match. + -z, --organization string, $CODER_ORGANIZATION + Select which organization (uuid or name) to use This overrides what is + present in the config file. + --token string, $CODER_SESSION_TOKEN Specify an authentication token. For security reasons setting CODER_SESSION_TOKEN is preferred. diff --git a/docs/cli.md b/docs/cli.md index 8e1d2c56c74c9..def4fc62bce19 100644 --- a/docs/cli.md +++ b/docs/cli.md @@ -130,6 +130,16 @@ Suppress warnings about unlicensed features. Suppress warning when client and server versions do not match. +### -z, --organization + +| | | +| ----------- | -------------------------------- | +| Type | string | +| Environment | $CODER_ORGANIZATION | + +Select which organization (uuid or name) to use This overrides what is present +in the config file. + ### --token | | | diff --git a/enterprise/cli/testdata/coder_--help.golden b/enterprise/cli/testdata/coder_--help.golden index 7c2ff5c835dff..c8612392972f0 100644 --- a/enterprise/cli/testdata/coder_--help.golden +++ b/enterprise/cli/testdata/coder_--help.golden @@ -48,6 +48,10 @@ variables or flags. --no-version-warning bool, $CODER_NO_VERSION_WARNING Suppress warning when client and server versions do not match. + -z, --organization string, $CODER_ORGANIZATION + Select which organization (uuid or name) to use This overrides what is + present in the config file. + --token string, $CODER_SESSION_TOKEN Specify an authentication token. For security reasons setting CODER_SESSION_TOKEN is preferred.