Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 19 additions & 1 deletion cli/logout.go
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,25 @@ func (r *RootCmd) logout() *serpent.Command {
errorString := strings.TrimRight(errorStringBuilder.String(), "\n")
return xerrors.New("Failed to log out.\n" + errorString)
}
_, _ = fmt.Fprint(inv.Stdout, Caret+"You are no longer logged in. You can log in using 'coder login <url>'.\n")
// Check for environment variables to customize the message
envURLValue := inv.Environ.Get(envURL)
binaryPathValue := inv.Environ.Get("CODER_SSH_CONFIG_BINARY_PATH")

// Set defaults
urlPlaceholder := "<url>"
binaryPath := "coder"

// Override with environment variables if available
if envURLValue != "" {
urlPlaceholder = envURLValue
}
if binaryPathValue != "" {
binaryPath = binaryPathValue
}

loginMessage := fmt.Sprintf("You are no longer logged in. You can log in using '%s login %s'.\n",
binaryPath, urlPlaceholder)
_, _ = fmt.Fprint(inv.Stdout, Caret+loginMessage)
return nil
},
}
Expand Down
6 changes: 3 additions & 3 deletions cli/logout_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ func TestLogout(t *testing.T) {

pty.ExpectMatch("Are you sure you want to log out?")
pty.WriteLine("yes")
pty.ExpectMatch("You are no longer logged in. You can log in using 'coder login <url>'.")
pty.ExpectMatch("You are no longer logged in. You can log in using")
<-logoutChan
})
t.Run("SkipPrompt", func(t *testing.T) {
Expand All @@ -67,7 +67,7 @@ func TestLogout(t *testing.T) {
assert.NoFileExists(t, string(config.Session()))
}()

pty.ExpectMatch("You are no longer logged in. You can log in using 'coder login <url>'.")
pty.ExpectMatch("You are no longer logged in. You can log in using")
<-logoutChan
})
t.Run("NoURLFile", func(t *testing.T) {
Expand All @@ -92,7 +92,7 @@ func TestLogout(t *testing.T) {
go func() {
defer close(logoutChan)
err := logout.Run()
assert.ErrorContains(t, err, "You are not logged in. Try logging in using 'coder login <url>'.")
assert.ErrorContains(t, err, "You are not logged in. Try logging in using")
}()

<-logoutChan
Expand Down
22 changes: 20 additions & 2 deletions cli/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,9 @@ const (
varDisableDirect = "disable-direct-connections"
varDisableNetworkTelemetry = "disable-network-telemetry"

notLoggedInMessage = "You are not logged in. Try logging in using 'coder login <url>'."
// This message is used when the user is not logged in.
// The resulting hint will respect environment variables.
notLoggedInMessageTemplate = "You are not logged in. Try logging in using '%s login %s'."

envNoVersionCheck = "CODER_NO_VERSION_WARNING"
envNoFeatureWarning = "CODER_NO_FEATURE_WARNING"
Expand Down Expand Up @@ -534,7 +536,23 @@ func (r *RootCmd) InitClient(client *codersdk.Client) serpent.MiddlewareFunc {
rawURL, err := conf.URL().Read()
// If the configuration files are absent, the user is logged out
if os.IsNotExist(err) {
return xerrors.New(notLoggedInMessage)
// Check for environment variables to customize error message
envURLValue := inv.Environ.Get(envURL)
binaryPathValue := inv.Environ.Get("CODER_SSH_CONFIG_BINARY_PATH")

// Set defaults for binary path and URL
urlPlaceholder := "<url>"
binaryPath := "coder"

// Override with environment variables if available
if envURLValue != "" {
urlPlaceholder = envURLValue
}
if binaryPathValue != "" {
binaryPath = binaryPathValue
}

return xerrors.New(fmt.Sprintf(notLoggedInMessageTemplate, binaryPath, urlPlaceholder))
}
if err != nil {
return err
Expand Down
4 changes: 2 additions & 2 deletions cli/userlist_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ func TestUserList(t *testing.T) {

inv, _ := clitest.New(t, "users", "list")
err := inv.Run()
require.Contains(t, err.Error(), "Try logging in using 'coder login <url>'.")
require.Contains(t, err.Error(), "Try logging in using")
})
t.Run("SessionAuthErrorHasHelperText", func(t *testing.T) {
t.Parallel()
Expand All @@ -84,7 +84,7 @@ func TestUserList(t *testing.T) {

var apiErr *codersdk.Error
require.ErrorAs(t, err, &apiErr)
require.Contains(t, err.Error(), "Try logging in using 'coder login'.")
require.Contains(t, err.Error(), "Try logging in using")
})
}

Expand Down
17 changes: 16 additions & 1 deletion codersdk/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"net/http"
"net/http/httputil"
"net/url"
"os"
"strings"
"sync"

Expand Down Expand Up @@ -404,7 +405,21 @@ func ReadBodyAsError(res *http.Response) error {
if res.StatusCode == http.StatusUnauthorized {
// 401 means the user is not logged in
// 403 would mean that the user is not authorized
helpMessage = "Try logging in using 'coder login'."
// Check environment variables to customize the help message
url := os.Getenv("CODER_URL")
binaryPath := os.Getenv("CODER_SSH_CONFIG_BINARY_PATH")

// Default to 'coder' if binary path is not specified
coderBinary := "coder"
if binaryPath != "" {
coderBinary = binaryPath
}

if url != "" {
helpMessage = fmt.Sprintf("Try logging in using '%s login %s'.", coderBinary, url)
} else {
helpMessage = fmt.Sprintf("Try logging in using '%s login'.", coderBinary)
}
}

resp, err := io.ReadAll(res.Body)
Expand Down
Loading