Implement completion for "kops get"

This commit is contained in:
John Gardiner Myers 2021-07-13 20:42:07 -07:00
parent 14d58a4e87
commit c312c19dcb
14 changed files with 50 additions and 79 deletions

View File

@ -39,10 +39,7 @@ var (
Display one or many resources.` + validResources)) Display one or many resources.` + validResources))
getExample = templates.Examples(i18n.T(` getExample = templates.Examples(i18n.T(`
# Get all clusters in a state store # Get a cluster and its instance groups
kops get clusters
# Get a cluster and its instancegroups
kops get k8s-cluster.example.com kops get k8s-cluster.example.com
# Get a cluster and its instancegroups' YAML desired configuration # Get a cluster and its instancegroups' YAML desired configuration
@ -50,19 +47,14 @@ var (
# Save a cluster and its instancegroups' desired configuration to YAML file # Save a cluster and its instancegroups' desired configuration to YAML file
kops get k8s-cluster.example.com -o yaml > cluster-desired-config.yaml kops get k8s-cluster.example.com -o yaml > cluster-desired-config.yaml
`))
# Get a secret
kops get secrets kube -oplaintext
# Get the admin password for a cluster
kops get secrets admin -oplaintext`))
getShort = i18n.T(`Get one or many resources.`) getShort = i18n.T(`Get one or many resources.`)
) )
type GetOptions struct { type GetOptions struct {
output string ClusterName string
clusterName string Output string
} }
const ( const (
@ -73,38 +65,26 @@ const (
func NewCmdGet(f *util.Factory, out io.Writer) *cobra.Command { func NewCmdGet(f *util.Factory, out io.Writer) *cobra.Command {
options := &GetOptions{ options := &GetOptions{
output: OutputTable, Output: OutputTable,
} }
cmd := &cobra.Command{ cmd := &cobra.Command{
Use: "get", Use: "get",
SuggestFor: []string{"list"}, SuggestFor: []string{"list"},
Short: getShort, Short: getShort,
Long: getLong, Long: getLong,
Example: getExample, Example: getExample,
Run: func(cmd *cobra.Command, args []string) { Args: rootCommand.clusterNameArgs(&options.ClusterName),
ctx := context.TODO() ValidArgsFunction: commandutils.CompleteClusterName(&rootCommand, true),
RunE: func(cmd *cobra.Command, args []string) error {
if len(args) != 0 { return RunGet(context.TODO(), &rootCommand, out, options)
options.clusterName = args[0]
}
if rootCommand.clusterName != "" {
if len(args) != 0 {
exitWithError(fmt.Errorf("cannot mix --name for cluster with positional arguments"))
}
options.clusterName = rootCommand.clusterName
}
err := RunGet(ctx, &rootCommand, os.Stdout, options)
if err != nil {
exitWithError(err)
}
}, },
} }
cmd.PersistentFlags().StringVarP(&options.output, "output", "o", options.output, "output format. One of: table, yaml, json") cmd.PersistentFlags().StringVarP(&options.Output, "output", "o", options.Output, "output format. One of: table, yaml, json")
cmd.RegisterFlagCompletionFunc("output", func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
return []string{"table", "json", "yaml"}, cobra.ShellCompDirectiveNoFileComp
})
// create subcommands // create subcommands
cmd.AddCommand(NewCmdGetAssets(f, out, options)) cmd.AddCommand(NewCmdGetAssets(f, out, options))
@ -124,7 +104,7 @@ func RunGet(ctx context.Context, f commandutils.Factory, out io.Writer, options
return err return err
} }
cluster, err := client.GetCluster(ctx, options.clusterName) cluster, err := client.GetCluster(ctx, options.ClusterName)
if err != nil { if err != nil {
return err return err
} }
@ -148,14 +128,14 @@ func RunGet(ctx context.Context, f commandutils.Factory, out io.Writer, options
} }
var obj []runtime.Object var obj []runtime.Object
if options.output != OutputTable { if options.Output != OutputTable {
obj = append(obj, cluster) obj = append(obj, cluster)
for _, group := range instancegroups { for _, group := range instancegroups {
obj = append(obj, group) obj = append(obj, group)
} }
} }
switch options.output { switch options.Output {
case OutputYaml: case OutputYaml:
if err := fullOutputYAML(out, obj...); err != nil { if err := fullOutputYAML(out, obj...); err != nil {
return fmt.Errorf("error writing cluster yaml to stdout: %v", err) return fmt.Errorf("error writing cluster yaml to stdout: %v", err)
@ -170,19 +150,19 @@ func RunGet(ctx context.Context, f commandutils.Factory, out io.Writer, options
return nil return nil
case OutputTable: case OutputTable:
fmt.Fprintf(os.Stdout, "Cluster\n") fmt.Fprintf(out, "Cluster\n")
err = clusterOutputTable([]*api.Cluster{cluster}, out) err = clusterOutputTable([]*api.Cluster{cluster}, out)
if err != nil { if err != nil {
return err return err
} }
fmt.Fprintf(os.Stdout, "\nInstance Groups\n") fmt.Fprintf(out, "\nInstance Groups\n")
err = igOutputTable(cluster, instancegroups, out) err = igOutputTable(cluster, instancegroups, out)
if err != nil { if err != nil {
return err return err
} }
default: default:
return fmt.Errorf("Unknown output format: %q", options.output) return fmt.Errorf("Unknown output format: %q", options.Output)
} }
return nil return nil

View File

@ -99,7 +99,7 @@ func NewCmdGetAssets(f *util.Factory, out io.Writer, getOptions *GetOptions) *co
func RunGetAssets(ctx context.Context, f *util.Factory, out io.Writer, options *GetAssetsOptions) error { func RunGetAssets(ctx context.Context, f *util.Factory, out io.Writer, options *GetAssetsOptions) error {
clusterName := rootCommand.ClusterName(true) clusterName := rootCommand.ClusterName(true)
options.clusterName = clusterName options.ClusterName = clusterName
if clusterName == "" { if clusterName == "" {
return fmt.Errorf("--name is required") return fmt.Errorf("--name is required")
} }
@ -150,7 +150,7 @@ func RunGetAssets(ctx context.Context, f *util.Factory, out io.Writer, options *
} }
} }
switch options.output { switch options.Output {
case OutputTable: case OutputTable:
if err = imageOutputTable(result.Images, out); err != nil { if err = imageOutputTable(result.Images, out); err != nil {
return err return err
@ -173,7 +173,7 @@ func RunGetAssets(ctx context.Context, f *util.Factory, out io.Writer, options *
return fmt.Errorf("error writing to output: %v", err) return fmt.Errorf("error writing to output: %v", err)
} }
default: default:
return fmt.Errorf("unsupported output format: %q", options.output) return fmt.Errorf("unsupported output format: %q", options.Output)
} }
return nil return nil

View File

@ -168,13 +168,13 @@ func RunGetClusters(ctx context.Context, f commandutils.Factory, out io.Writer,
} }
var obj []runtime.Object var obj []runtime.Object
if options.output != OutputTable { if options.Output != OutputTable {
for _, c := range clusters { for _, c := range clusters {
obj = append(obj, c) obj = append(obj, c)
} }
} }
switch options.output { switch options.Output {
case OutputTable: case OutputTable:
return clusterOutputTable(clusters, out) return clusterOutputTable(clusters, out)
case OutputYaml: case OutputYaml:
@ -182,7 +182,7 @@ func RunGetClusters(ctx context.Context, f commandutils.Factory, out io.Writer,
case OutputJSON: case OutputJSON:
return fullOutputJSON(out, obj...) return fullOutputJSON(out, obj...)
default: default:
return fmt.Errorf("Unknown output format: %q", options.output) return fmt.Errorf("Unknown output format: %q", options.Output)
} }
} }

View File

@ -116,13 +116,13 @@ func RunGetInstanceGroups(ctx context.Context, options *GetInstanceGroupsOptions
} }
var obj []runtime.Object var obj []runtime.Object
if options.output != OutputTable { if options.Output != OutputTable {
for _, c := range instancegroups { for _, c := range instancegroups {
obj = append(obj, c) obj = append(obj, c)
} }
} }
switch options.output { switch options.Output {
case OutputTable: case OutputTable:
return igOutputTable(cluster, instancegroups, out) return igOutputTable(cluster, instancegroups, out)
case OutputYaml: case OutputYaml:
@ -130,7 +130,7 @@ func RunGetInstanceGroups(ctx context.Context, options *GetInstanceGroupsOptions
case OutputJSON: case OutputJSON:
return fullOutputJSON(out, obj...) return fullOutputJSON(out, obj...)
default: default:
return fmt.Errorf("Unknown output format: %q", options.output) return fmt.Errorf("Unknown output format: %q", options.Output)
} }
} }

View File

@ -84,18 +84,18 @@ func RunGetInstances(ctx context.Context, f *util.Factory, out io.Writer, option
} }
clusterName := rootCommand.ClusterName(true) clusterName := rootCommand.ClusterName(true)
options.clusterName = clusterName options.ClusterName = clusterName
if clusterName == "" { if clusterName == "" {
return fmt.Errorf("--name is required") return fmt.Errorf("--name is required")
} }
cluster, err := clientset.GetCluster(ctx, options.clusterName) cluster, err := clientset.GetCluster(ctx, options.ClusterName)
if err != nil { if err != nil {
return err return err
} }
if cluster == nil { if cluster == nil {
return fmt.Errorf("cluster not found %q", options.clusterName) return fmt.Errorf("cluster not found %q", options.ClusterName)
} }
cloud, err := cloudup.BuildCloud(cluster) cloud, err := cloudup.BuildCloud(cluster)
@ -137,11 +137,11 @@ func RunGetInstances(ctx context.Context, f *util.Factory, out io.Writer, option
cg.AdjustNeedUpdate() cg.AdjustNeedUpdate()
} }
switch options.output { switch options.Output {
case OutputTable: case OutputTable:
return instanceOutputTable(cloudInstances, out) return instanceOutputTable(cloudInstances, out)
default: default:
return fmt.Errorf("unsupported output format: %q", options.output) return fmt.Errorf("unsupported output format: %q", options.Output)
} }
} }

View File

@ -144,7 +144,7 @@ func RunGetKeypairs(ctx context.Context, out io.Writer, options *GetKeypairsOpti
if len(items) == 0 { if len(items) == 0 {
return fmt.Errorf("no keypairs found") return fmt.Errorf("no keypairs found")
} }
switch options.output { switch options.Output {
case OutputTable: case OutputTable:
t := &tables.Table{} t := &tables.Table{}
@ -191,7 +191,7 @@ func RunGetKeypairs(ctx context.Context, out io.Writer, options *GetKeypairsOpti
return fmt.Errorf("json output format is not (currently) supported for keypairs") return fmt.Errorf("json output format is not (currently) supported for keypairs")
default: default:
return fmt.Errorf("Unknown output format: %q", options.output) return fmt.Errorf("Unknown output format: %q", options.Output)
} }
} }

View File

@ -193,7 +193,7 @@ func RunGetSecrets(ctx context.Context, options *GetSecretsOptions, args []strin
if len(items) == 0 { if len(items) == 0 {
return fmt.Errorf("No secrets found") return fmt.Errorf("No secrets found")
} }
switch options.output { switch options.Output {
case OutputTable: case OutputTable:
@ -239,6 +239,6 @@ func RunGetSecrets(ctx context.Context, options *GetSecretsOptions, args []strin
return nil return nil
default: default:
return fmt.Errorf("Unknown output format: %q", options.output) return fmt.Errorf("Unknown output format: %q", options.Output)
} }
} }

13
docs/cli/kops_get.md generated
View File

@ -20,10 +20,7 @@ kops get [flags]
### Examples ### Examples
``` ```
# Get all clusters in a state store # Get a cluster and its instance groups
kops get clusters
# Get a cluster and its instancegroups
kops get k8s-cluster.example.com kops get k8s-cluster.example.com
# Get a cluster and its instancegroups' YAML desired configuration # Get a cluster and its instancegroups' YAML desired configuration
@ -31,19 +28,13 @@ kops get [flags]
# Save a cluster and its instancegroups' desired configuration to YAML file # Save a cluster and its instancegroups' desired configuration to YAML file
kops get k8s-cluster.example.com -o yaml > cluster-desired-config.yaml kops get k8s-cluster.example.com -o yaml > cluster-desired-config.yaml
# Get a secret
kops get secrets kube -oplaintext
# Get the admin password for a cluster
kops get secrets admin -oplaintext
``` ```
### Options ### Options
``` ```
-h, --help help for get -h, --help help for get
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
``` ```
### Options inherited from parent commands ### Options inherited from parent commands

View File

@ -40,7 +40,7 @@ kops get assets [flags]
--logtostderr log to standard error instead of files (default true) --logtostderr log to standard error instead of files (default true)
--name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable --name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable
--one_output If true, only write logs to their native severity level (vs also writing to each lower severity level) --one_output If true, only write logs to their native severity level (vs also writing to each lower severity level)
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
--skip_headers If true, avoid header prefixes in the log messages --skip_headers If true, avoid header prefixes in the log messages
--skip_log_headers If true, avoid headers when opening log files --skip_log_headers If true, avoid headers when opening log files
--state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable --state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable

View File

@ -49,7 +49,7 @@ kops get clusters [flags]
--logtostderr log to standard error instead of files (default true) --logtostderr log to standard error instead of files (default true)
--name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable --name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable
--one_output If true, only write logs to their native severity level (vs also writing to each lower severity level) --one_output If true, only write logs to their native severity level (vs also writing to each lower severity level)
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
--skip_headers If true, avoid header prefixes in the log messages --skip_headers If true, avoid header prefixes in the log messages
--skip_log_headers If true, avoid headers when opening log files --skip_log_headers If true, avoid headers when opening log files
--state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable --state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable

View File

@ -45,7 +45,7 @@ kops get instancegroups [flags]
--logtostderr log to standard error instead of files (default true) --logtostderr log to standard error instead of files (default true)
--name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable --name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable
--one_output If true, only write logs to their native severity level (vs also writing to each lower severity level) --one_output If true, only write logs to their native severity level (vs also writing to each lower severity level)
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
--skip_headers If true, avoid header prefixes in the log messages --skip_headers If true, avoid header prefixes in the log messages
--skip_log_headers If true, avoid headers when opening log files --skip_log_headers If true, avoid headers when opening log files
--state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable --state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable

View File

@ -39,7 +39,7 @@ kops get instances [flags]
--logtostderr log to standard error instead of files (default true) --logtostderr log to standard error instead of files (default true)
--name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable --name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable
--one_output If true, only write logs to their native severity level (vs also writing to each lower severity level) --one_output If true, only write logs to their native severity level (vs also writing to each lower severity level)
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
--skip_headers If true, avoid header prefixes in the log messages --skip_headers If true, avoid header prefixes in the log messages
--skip_log_headers If true, avoid headers when opening log files --skip_log_headers If true, avoid headers when opening log files
--state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable --state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable

View File

@ -39,7 +39,7 @@ kops get keypairs [KEYSET]... [flags]
--logtostderr log to standard error instead of files (default true) --logtostderr log to standard error instead of files (default true)
--name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable --name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable
--one_output If true, only write logs to their native severity level (vs also writing to each lower severity level) --one_output If true, only write logs to their native severity level (vs also writing to each lower severity level)
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
--skip_headers If true, avoid header prefixes in the log messages --skip_headers If true, avoid header prefixes in the log messages
--skip_log_headers If true, avoid headers when opening log files --skip_log_headers If true, avoid headers when opening log files
--state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable --state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable

View File

@ -43,7 +43,7 @@ kops get secrets [flags]
--logtostderr log to standard error instead of files (default true) --logtostderr log to standard error instead of files (default true)
--name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable --name string Name of cluster. Overrides KOPS_CLUSTER_NAME environment variable
--one_output If true, only write logs to their native severity level (vs also writing to each lower severity level) --one_output If true, only write logs to their native severity level (vs also writing to each lower severity level)
-o, --output string output format. One of: table, yaml, json (default "table") -o, --output string output format. One of: table, yaml, json (default "table")
--skip_headers If true, avoid header prefixes in the log messages --skip_headers If true, avoid header prefixes in the log messages
--skip_log_headers If true, avoid headers when opening log files --skip_log_headers If true, avoid headers when opening log files
--state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable --state string Location of state storage (kops 'config' file). Overrides KOPS_STATE_STORE environment variable