Merge pull request #51971 from juanvallejo/jvallejo/add-list-option-to-kubectl-label

Automatic merge from submit-queue (batch tested with PRs 52485, 52443, 52597, 52450, 51971). If you want to cherry-pick this change to another branch, please follow the instructions <a href="https://github.com/kubernetes/community/blob/master/contributors/devel/cherry-picks.md">here</a>..

add --list option to label cmd

**Release note**:
```release-note
added --list option to the `kubectl label` command
```

Adds a `--list` option to `kubectl label ...` with similar behavior to `kubectl env ... --list`

**Before**
```
$ kubectl label pod/mypod --list
Error: unknown flag: --list

Usage:
...
```

**After**
```
$ kubectl label pod/mypod --list
labelkey1=existinglabel1
labelkey2=existinglabel2

$ kubectl label pod/mypod --list label1=newlabel1
labelkey1=existinglabel1
labelkey2=existinglabel2
label1=newlabel1
```

Related downstream bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=1268877

cc @fabianofranz @kubernetes/sig-cli-misc
This commit is contained in:
Kubernetes Submit Queue 2017-09-23 18:49:00 -07:00 committed by GitHub
commit d7fc98f5d0

View File

@ -49,6 +49,7 @@ type LabelOptions struct {
// Common user flags // Common user flags
overwrite bool overwrite bool
list bool
local bool local bool
dryrun bool dryrun bool
all bool all bool
@ -127,6 +128,7 @@ func NewCmdLabel(f cmdutil.Factory, out io.Writer) *cobra.Command {
} }
cmdutil.AddPrinterFlags(cmd) cmdutil.AddPrinterFlags(cmd)
cmd.Flags().Bool("overwrite", false, "If true, allow labels to be overwritten, otherwise reject label updates that overwrite existing labels.") cmd.Flags().Bool("overwrite", false, "If true, allow labels to be overwritten, otherwise reject label updates that overwrite existing labels.")
cmd.Flags().BoolVar(&options.list, "list", options.list, "If true, display the labels for a given resource.")
cmd.Flags().Bool("local", false, "If true, label will NOT contact api-server but run locally.") cmd.Flags().Bool("local", false, "If true, label will NOT contact api-server but run locally.")
cmd.Flags().StringP("selector", "l", "", "Selector (label query) to filter on, not including uninitialized ones, supports '=', '==', and '!='.(e.g. -l key1=value1,key2=value2).") cmd.Flags().StringP("selector", "l", "", "Selector (label query) to filter on, not including uninitialized ones, supports '=', '==', and '!='.(e.g. -l key1=value1,key2=value2).")
cmd.Flags().Bool("all", false, "Select all resources, including uninitialized ones, in the namespace of the specified resource types") cmd.Flags().Bool("all", false, "Select all resources, including uninitialized ones, in the namespace of the specified resource types")
@ -144,6 +146,7 @@ func NewCmdLabel(f cmdutil.Factory, out io.Writer) *cobra.Command {
// Complete adapts from the command line args and factory to the data required. // Complete adapts from the command line args and factory to the data required.
func (o *LabelOptions) Complete(out io.Writer, cmd *cobra.Command, args []string) (err error) { func (o *LabelOptions) Complete(out io.Writer, cmd *cobra.Command, args []string) (err error) {
o.out = out o.out = out
o.list = cmdutil.GetFlagBool(cmd, "list")
o.local = cmdutil.GetFlagBool(cmd, "local") o.local = cmdutil.GetFlagBool(cmd, "local")
o.overwrite = cmdutil.GetFlagBool(cmd, "overwrite") o.overwrite = cmdutil.GetFlagBool(cmd, "overwrite")
o.all = cmdutil.GetFlagBool(cmd, "all") o.all = cmdutil.GetFlagBool(cmd, "all")
@ -158,6 +161,11 @@ func (o *LabelOptions) Complete(out io.Writer, cmd *cobra.Command, args []string
} }
o.resources = resources o.resources = resources
o.newLabels, o.removeLabels, err = parseLabels(labelArgs) o.newLabels, o.removeLabels, err = parseLabels(labelArgs)
if o.list && len(o.outputFormat) > 0 {
return cmdutil.UsageErrorf(cmd, "--list and --output may not be specified together")
}
return err return err
} }
@ -166,7 +174,7 @@ func (o *LabelOptions) Validate() error {
if len(o.resources) < 1 && cmdutil.IsFilenameSliceEmpty(o.FilenameOptions.Filenames) { if len(o.resources) < 1 && cmdutil.IsFilenameSliceEmpty(o.FilenameOptions.Filenames) {
return fmt.Errorf("one or more resources must be specified as <resource> <name> or <resource>/<name>") return fmt.Errorf("one or more resources must be specified as <resource> <name> or <resource>/<name>")
} }
if len(o.newLabels) < 1 && len(o.removeLabels) < 1 { if len(o.newLabels) < 1 && len(o.removeLabels) < 1 && !o.list {
return fmt.Errorf("at least one label update is required") return fmt.Errorf("at least one label update is required")
} }
return nil return nil
@ -225,7 +233,7 @@ func (o *LabelOptions) RunLabel(f cmdutil.Factory, cmd *cobra.Command) error {
var outputObj runtime.Object var outputObj runtime.Object
dataChangeMsg := "not labeled" dataChangeMsg := "not labeled"
if o.dryrun || o.local { if o.dryrun || o.local || o.list {
err = labelFunc(info.Object, o.overwrite, o.resourceVersion, o.newLabels, o.removeLabels) err = labelFunc(info.Object, o.overwrite, o.resourceVersion, o.newLabels, o.removeLabels)
if err != nil { if err != nil {
return err return err
@ -287,6 +295,19 @@ func (o *LabelOptions) RunLabel(f cmdutil.Factory, cmd *cobra.Command) error {
} }
} }
if o.list {
accessor, err := meta.Accessor(outputObj)
if err != nil {
return err
}
for k, v := range accessor.GetLabels() {
fmt.Fprintf(o.out, "%s=%s\n", k, v)
}
return nil
}
var mapper meta.RESTMapper var mapper meta.RESTMapper
if o.local { if o.local {
mapper, _ = f.Object() mapper, _ = f.Object()