Skip to content
Merged
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
3 changes: 3 additions & 0 deletions cli/cliui/output.go
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,9 @@ var _ OutputFormat = &tableFormat{}
//
// defaultColumns is optional and specifies the default columns to display. If
// not specified, all columns are displayed by default.
//
// If the data is empty, an empty string is returned. Callers should check for
// this and provide an appropriate message to the user.
func TableFormat(out any, defaultColumns []string) OutputFormat {
v := reflect.Indirect(reflect.ValueOf(out))
if v.Kind() != reflect.Slice {
Expand Down
6 changes: 6 additions & 0 deletions cli/cliui/table.go
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,12 @@ func DisplayTable(out any, sort string, filterColumns []string) (string, error)
func renderTable(out any, sort string, headers table.Row, filterColumns []string) (string, error) {
v := reflect.Indirect(reflect.ValueOf(out))

// Return empty string for empty data. Callers should check for this
// and provide an appropriate message to the user.
if v.Kind() == reflect.Slice && v.Len() == 0 {
return "", nil
}

headers = filterHeaders(headers, filterColumns)
columnConfigs := createColumnConfigs(headers, filterColumns)

Expand Down
9 changes: 9 additions & 0 deletions cli/cliui/table_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -472,6 +472,15 @@ alice 1
require.NoError(t, err)
compareTables(t, expected, out)
})

t.Run("Empty", func(t *testing.T) {
t.Parallel()

var in []tableTest4
out, err := cliui.DisplayTable(in, "", nil)
require.NoError(t, err)
require.Empty(t, out)
})
}

// compareTables normalizes the incoming table lines
Expand Down
12 changes: 6 additions & 6 deletions cli/list.go
Original file line number Diff line number Diff line change
Expand Up @@ -139,19 +139,19 @@ func (r *RootCmd) list() *serpent.Command {
return err
}

if len(res) == 0 && formatter.FormatID() != cliui.JSONFormat().ID() {
out, err := formatter.Format(inv.Context(), res)
if err != nil {
return err
}

if out == "" {
pretty.Fprintf(inv.Stderr, cliui.DefaultStyles.Prompt, "No workspaces found! Create one:\n")
_, _ = fmt.Fprintln(inv.Stderr)
_, _ = fmt.Fprintln(inv.Stderr, " "+pretty.Sprint(cliui.DefaultStyles.Code, "coder create <name>"))
_, _ = fmt.Fprintln(inv.Stderr)
return nil
}

out, err := formatter.Format(inv.Context(), res)
if err != nil {
return err
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
5 changes: 5 additions & 0 deletions cli/organizationmembers.go
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,11 @@ func (r *RootCmd) listOrganizationMembers(orgContext *OrganizationContext) *serp
return err
}

if out == "" {
cliui.Infof(inv.Stderr, "No organization members found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
5 changes: 5 additions & 0 deletions cli/organizationroles.go
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,11 @@ func (r *RootCmd) showOrganizationRoles(orgContext *OrganizationContext) *serpen
return err
}

if out == "" {
cliui.Infof(inv.Stderr, "No organization roles found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
5 changes: 5 additions & 0 deletions cli/provisionerjobs.go
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,11 @@ func (r *RootCmd) provisionerJobsList() *serpent.Command {
return xerrors.Errorf("display provisioner daemons: %w", err)
}

if out == "" {
cliui.Infof(inv.Stderr, "No provisioner jobs found.")
return nil
}

_, _ = fmt.Fprintln(inv.Stdout, out)

return nil
Expand Down
10 changes: 5 additions & 5 deletions cli/provisioners.go
Original file line number Diff line number Diff line change
Expand Up @@ -74,11 +74,6 @@ func (r *RootCmd) provisionerList() *serpent.Command {
return xerrors.Errorf("list provisioner daemons: %w", err)
}

if len(daemons) == 0 {
_, _ = fmt.Fprintln(inv.Stdout, "No provisioner daemons found")
return nil
}

var rows []provisionerDaemonRow
for _, daemon := range daemons {
rows = append(rows, provisionerDaemonRow{
Expand All @@ -92,6 +87,11 @@ func (r *RootCmd) provisionerList() *serpent.Command {
return xerrors.Errorf("display provisioner daemons: %w", err)
}

if out == "" {
cliui.Infof(inv.Stderr, "No provisioner daemons found.")
return nil
}

_, _ = fmt.Fprintln(inv.Stdout, out)

return nil
Expand Down
5 changes: 5 additions & 0 deletions cli/schedule.go
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,11 @@ func (r *RootCmd) scheduleShow() *serpent.Command {
return err
}

if out == "" {
cliui.Infof(inv.Stderr, "No schedules found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
10 changes: 4 additions & 6 deletions cli/task_list.go
Original file line number Diff line number Diff line change
Expand Up @@ -157,12 +157,6 @@ func (r *RootCmd) taskList() *serpent.Command {
return nil
}

// If no rows and not JSON, show a friendly message.
if len(tasks) == 0 && formatter.FormatID() != cliui.JSONFormat().ID() {
_, _ = fmt.Fprintln(inv.Stderr, "No tasks found.")
return nil
}

rows := make([]taskListRow, len(tasks))
now := time.Now()
for i := range tasks {
Expand All @@ -173,6 +167,10 @@ func (r *RootCmd) taskList() *serpent.Command {
if err != nil {
return xerrors.Errorf("format tasks: %w", err)
}
if out == "" {
cliui.Infof(inv.Stderr, "No tasks found.")
return nil
}
_, _ = fmt.Fprintln(inv.Stdout, out)
return nil
},
Expand Down
5 changes: 5 additions & 0 deletions cli/task_logs.go
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,11 @@ func (r *RootCmd) taskLogs() *serpent.Command {
return xerrors.Errorf("format task logs: %w", err)
}

if out == "" {
cliui.Infof(inv.Stderr, "No task logs found.")
return nil
}

_, _ = fmt.Fprintln(inv.Stdout, out)
return nil
},
Expand Down
12 changes: 6 additions & 6 deletions cli/templatelist.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,18 +30,18 @@ func (r *RootCmd) templateList() *serpent.Command {
return err
}

if len(templates) == 0 {
_, _ = fmt.Fprintf(inv.Stderr, "%s No templates found! Create one:\n\n", Caret)
_, _ = fmt.Fprintln(inv.Stderr, color.HiMagentaString(" $ coder templates push <directory>\n"))
return nil
}

rows := templatesToRows(templates...)
out, err := formatter.Format(inv.Context(), rows)
if err != nil {
return err
}

if out == "" {
_, _ = fmt.Fprintf(inv.Stderr, "%s No templates found! Create one:\n\n", Caret)
_, _ = fmt.Fprintln(inv.Stderr, color.HiMagentaString(" $ coder templates push <directory>\n"))
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
9 changes: 7 additions & 2 deletions cli/templatepresets.go
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@ func (r *RootCmd) templatePresetsList() *serpent.Command {
if len(presets) == 0 {
cliui.Infof(
inv.Stdout,
"No presets found for template %q and template-version %q.\n", template.Name, version.Name,
"No presets found for template %q and template-version %q.", template.Name, version.Name,
)
return nil
}
Expand All @@ -115,7 +115,7 @@ func (r *RootCmd) templatePresetsList() *serpent.Command {
if formatter.FormatID() == "table" {
cliui.Infof(
inv.Stdout,
"Showing presets for template %q and template version %q.\n", template.Name, version.Name,
"Showing presets for template %q and template version %q.", template.Name, version.Name,
)
}
rows := templatePresetsToRows(presets...)
Expand All @@ -124,6 +124,11 @@ func (r *RootCmd) templatePresetsList() *serpent.Command {
return xerrors.Errorf("render table: %w", err)
}

if out == "" {
cliui.Infof(inv.Stderr, "No template presets found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
5 changes: 5 additions & 0 deletions cli/templateversions.go
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,11 @@ func (r *RootCmd) templateVersionsList() *serpent.Command {
return xerrors.Errorf("render table: %w", err)
}

if out == "" {
cliui.Infof(inv.Stderr, "No template versions found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
12 changes: 5 additions & 7 deletions cli/tokens.go
Original file line number Diff line number Diff line change
Expand Up @@ -246,13 +246,6 @@ func (r *RootCmd) listTokens() *serpent.Command {
return xerrors.Errorf("list tokens: %w", err)
}

if len(tokens) == 0 {
cliui.Infof(
inv.Stdout,
"No tokens found.\n",
)
}

displayTokens = make([]tokenListRow, len(tokens))

for i, token := range tokens {
Expand All @@ -264,6 +257,11 @@ func (r *RootCmd) listTokens() *serpent.Command {
return err
}

if out == "" {
cliui.Info(inv.Stderr, "No tokens found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
1 change: 1 addition & 0 deletions cli/tokens_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ func TestTokens(t *testing.T) {
clitest.SetupConfig(t, client, root)
buf := new(bytes.Buffer)
inv.Stdout = buf
inv.Stderr = buf
err := inv.WithContext(ctx).Run()
require.NoError(t, err)
res := buf.String()
Expand Down
5 changes: 5 additions & 0 deletions cli/userlist.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,11 @@ func (r *RootCmd) userList() *serpent.Command {
return err
}

if out == "" {
cliui.Infof(inv.Stderr, "No users found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
13 changes: 7 additions & 6 deletions enterprise/cli/externalworkspaces.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"github.com/coder/coder/v2/cli/cliui"
"github.com/coder/coder/v2/codersdk"
"github.com/coder/pretty"

"github.com/coder/serpent"
)

Expand Down Expand Up @@ -197,19 +198,19 @@ func (r *RootCmd) externalWorkspaceList() *serpent.Command {
return err
}

if len(res) == 0 && formatter.FormatID() != cliui.JSONFormat().ID() {
out, err := formatter.Format(inv.Context(), res)
if err != nil {
return err
}

if out == "" {
pretty.Fprintf(inv.Stderr, cliui.DefaultStyles.Prompt, "No workspaces found! Create one:\n")
_, _ = fmt.Fprintln(inv.Stderr)
_, _ = fmt.Fprintln(inv.Stderr, " "+pretty.Sprint(cliui.DefaultStyles.Code, "coder external-workspaces create <name>"))
_, _ = fmt.Fprintln(inv.Stderr)
return nil
}

out, err := formatter.Format(inv.Context(), res)
if err != nil {
return err
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
12 changes: 6 additions & 6 deletions enterprise/cli/grouplist.go
Original file line number Diff line number Diff line change
Expand Up @@ -43,18 +43,18 @@ func (r *RootCmd) groupList() *serpent.Command {
return xerrors.Errorf("get groups: %w", err)
}

if len(groups) == 0 {
_, _ = fmt.Fprintf(inv.Stderr, "%s No groups found in %s! Create one:\n\n", agpl.Caret, color.HiWhiteString(org.Name))
_, _ = fmt.Fprintln(inv.Stderr, color.HiMagentaString(" $ coder groups create <name>\n"))
return nil
}

rows := groupsToRows(groups...)
out, err := formatter.Format(inv.Context(), rows)
if err != nil {
return xerrors.Errorf("display groups: %w", err)
}

if out == "" {
_, _ = fmt.Fprintf(inv.Stderr, "%s No groups found in %s! Create one:\n\n", agpl.Caret, color.HiWhiteString(org.Name))
_, _ = fmt.Fprintln(inv.Stderr, color.HiMagentaString(" $ coder groups create <name>\n"))
return nil
}

_, _ = fmt.Fprintln(inv.Stdout, out)
return nil
},
Expand Down
5 changes: 5 additions & 0 deletions enterprise/cli/licenses.go
Original file line number Diff line number Diff line change
Expand Up @@ -166,6 +166,11 @@ func (r *RootCmd) licensesList() *serpent.Command {
return err
}

if out == "" {
cliui.Infof(inv.Stderr, "No licenses found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, out)
return err
},
Expand Down
10 changes: 5 additions & 5 deletions enterprise/cli/provisionerkeys.go
Original file line number Diff line number Diff line change
Expand Up @@ -126,16 +126,16 @@ func (r *RootCmd) provisionerKeysList() *serpent.Command {
return xerrors.Errorf("list provisioner keys: %w", err)
}

if len(keys) == 0 {
_, _ = fmt.Fprintln(inv.Stdout, "No provisioner keys found")
return nil
}

out, err := formatter.Format(inv.Context(), keys)
if err != nil {
return xerrors.Errorf("display provisioner keys: %w", err)
}

if out == "" {
cliui.Infof(inv.Stderr, "No provisioner keys found.")
return nil
}

_, _ = fmt.Fprintln(inv.Stdout, out)

return nil
Expand Down
1 change: 1 addition & 0 deletions enterprise/cli/provisionerkeys_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,7 @@ func TestProvisionerKeys(t *testing.T) {
)
pty = ptytest.New(t)
inv.Stdout = pty.Output()
inv.Stderr = pty.Output()
clitest.SetupConfig(t, orgAdminClient, conf)

err = inv.WithContext(ctx).Run()
Expand Down
5 changes: 5 additions & 0 deletions enterprise/cli/workspaceproxy.go
Original file line number Diff line number Diff line change
Expand Up @@ -392,6 +392,11 @@ func (r *RootCmd) listProxies() *serpent.Command {
return err
}

if output == "" {
cliui.Infof(inv.Stderr, "No workspace proxies found.")
return nil
}

_, err = fmt.Fprintln(inv.Stdout, output)
return err
},
Expand Down
Loading