// RunGet implements the generic Get command // TODO: convert all direct flag accessors to a struct and pass that instead of cmd func RunGet(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, args []string) error { selector := cmdutil.GetFlagString(cmd, "selector") allNamespaces := cmdutil.GetFlagBool(cmd, "all-namespaces") mapper, typer := f.Object() cmdNamespace, _, err := f.DefaultNamespace() if err != nil { return err } if len(args) == 0 { fmt.Fprint(out, ` You must specify the type of resource to get. Valid resource types include: * pods (aka 'po') * replicationcontrollers (aka 'rc') * services * nodes (aka 'no') * events (aka 'ev') * secrets * limits * persistentVolumes (aka 'pv') * persistentVolumeClaims (aka 'pvc') * quota `) return errors.New("Required resource not specified.") } // handle watch separately since we cannot watch multiple resource types isWatch, isWatchOnly := cmdutil.GetFlagBool(cmd, "watch"), cmdutil.GetFlagBool(cmd, "watch-only") if isWatch || isWatchOnly { r := resource.NewBuilder(mapper, typer, f.ClientMapperForCommand()). NamespaceParam(cmdNamespace).DefaultNamespace().AllNamespaces(allNamespaces). SelectorParam(selector). ResourceTypeOrNameArgs(true, args...). SingleResourceType(). Do() if err != nil { return err } mapping, err := r.ResourceMapping() if err != nil { return err } printer, err := f.PrinterForMapping(cmd, mapping, allNamespaces) if err != nil { return err } obj, err := r.Object() if err != nil { return err } rv, err := mapping.MetadataAccessor.ResourceVersion(obj) if err != nil { return err } // print the current object if !isWatchOnly { if err := printer.PrintObj(obj, out); err != nil { return fmt.Errorf("unable to output the provided object: %v", err) } } // print watched changes w, err := r.Watch(rv) if err != nil { return err } kubectl.WatchLoop(w, func(e watch.Event) error { return printer.PrintObj(e.Object, out) }) return nil } b := resource.NewBuilder(mapper, typer, f.ClientMapperForCommand()). NamespaceParam(cmdNamespace).DefaultNamespace().AllNamespaces(allNamespaces). SelectorParam(selector). ResourceTypeOrNameArgs(true, args...). ContinueOnError(). Latest() printer, generic, err := cmdutil.PrinterForCommand(cmd) if err != nil { return err } if generic { clientConfig, err := f.ClientConfig() if err != nil { return err } defaultVersion := clientConfig.Version singular := false r := b.Flatten().Do() infos, err := r.IntoSingular(&singular).Infos() if err != nil { return err } // the outermost object will be converted to the output-version, but inner // objects can use their mappings version := cmdutil.OutputVersion(cmd, defaultVersion) obj, err := resource.AsVersionedObject(infos, !singular, version) if err != nil { return err } return printer.PrintObj(obj, out) } // use the default printer for each object return b.Do().Visit(func(r *resource.Info) error { printer, err := f.PrinterForMapping(cmd, r.Mapping, allNamespaces) if err != nil { return err } return printer.PrintObj(r.Object, out) }) }
func (f *Factory) NewCmdGet(out io.Writer) *cobra.Command { cmd := &cobra.Command{ Use: "get [(-o|--output=)json|yaml|...] <resource> [<id>]", Short: "Display one or many resources", Long: `Display one or many resources. Possible resources include pods (po), replication controllers (rc), services (se), minions (mi), or events (ev). If you specify a Go template, you can use any fields defined for the API version you are connecting to the server with. Examples: $ kubectl get pods <list all pods in ps output format> $ kubectl get replicationController 1234-56-7890-234234-456456 <list single replication controller in ps output format> $ kubectl get -o json pod 1234-56-7890-234234-456456 <list single pod in json output format>`, Run: func(cmd *cobra.Command, args []string) { mapping, namespace, name := ResourceOrTypeFromArgs(cmd, args, f.Mapper) selector := GetFlagString(cmd, "selector") labelSelector, err := labels.ParseSelector(selector) checkErr(err) client, err := f.RESTClient(cmd, mapping) checkErr(err) outputFormat := GetFlagString(cmd, "output") templateFile := GetFlagString(cmd, "template") defaultPrinter, err := f.Printer(cmd, mapping, GetFlagBool(cmd, "no-headers")) checkErr(err) outputVersion := GetFlagString(cmd, "output-version") if len(outputVersion) == 0 { outputVersion = mapping.APIVersion } printer, err := kubectl.GetPrinter(outputFormat, templateFile, outputVersion, mapping.ObjectConvertor, defaultPrinter) checkErr(err) restHelper := resource.NewHelper(client, mapping) var obj runtime.Object if len(name) == 0 { obj, err = restHelper.List(namespace, labelSelector) } else { obj, err = restHelper.Get(namespace, name) } checkErr(err) isWatch, isWatchOnly := GetFlagBool(cmd, "watch"), GetFlagBool(cmd, "watch-only") // print the current object if !isWatchOnly { if err := printer.PrintObj(obj, out); err != nil { checkErr(fmt.Errorf("unable to output the provided object: %v", err)) } } // print watched changes if isWatch || isWatchOnly { rv, err := mapping.MetadataAccessor.ResourceVersion(obj) checkErr(err) w, err := restHelper.Watch(namespace, rv, labelSelector, labels.Everything()) checkErr(err) kubectl.WatchLoop(w, printer, out) } }, } cmd.Flags().StringP("output", "o", "", "Output format: json|yaml|template|templatefile") cmd.Flags().String("output-version", "", "Output the formatted object with the given version (default api-version)") cmd.Flags().Bool("no-headers", false, "When using the default output, don't print headers") cmd.Flags().StringP("template", "t", "", "Template string or path to template file to use when --output=template or --output=templatefile") cmd.Flags().StringP("selector", "l", "", "Selector (label query) to filter on") cmd.Flags().BoolP("watch", "w", false, "After listing/getting the requested object, watch for changes.") cmd.Flags().Bool("watch-only", false, "Watch for changes to the requseted object(s), without listing/getting first.") return cmd }
// RunGet implements the generic Get command // TODO: convert all direct flag accessors to a struct and pass that instead of cmd // TODO: return an error instead of using glog.Fatal and checkErr func RunGet(f *Factory, out io.Writer, cmd *cobra.Command, args []string) { selector := GetFlagString(cmd, "selector") mapper, typer := f.Object(cmd) cmdNamespace, err := f.DefaultNamespace(cmd) checkErr(err) // handle watch separately since we cannot watch multiple resource types isWatch, isWatchOnly := GetFlagBool(cmd, "watch"), GetFlagBool(cmd, "watch-only") if isWatch || isWatchOnly { r := resource.NewBuilder(mapper, typer, ClientMapperForCommand(cmd, f)). NamespaceParam(cmdNamespace).DefaultNamespace(). SelectorParam(selector). ResourceTypeOrNameArgs(args...). SingleResourceType(). Do() mapping, err := r.ResourceMapping() checkErr(err) printer, err := PrinterForMapping(f, cmd, mapping) checkErr(err) obj, err := r.Object() checkErr(err) rv, err := mapping.MetadataAccessor.ResourceVersion(obj) checkErr(err) // print the current object if !isWatchOnly { if err := printer.PrintObj(obj, out); err != nil { checkErr(fmt.Errorf("unable to output the provided object: %v", err)) } } // print watched changes w, err := r.Watch(rv) checkErr(err) kubectl.WatchLoop(w, func(e watch.Event) error { return printer.PrintObj(e.Object, out) }) return } b := resource.NewBuilder(mapper, typer, ClientMapperForCommand(cmd, f)). NamespaceParam(cmdNamespace).DefaultNamespace(). SelectorParam(selector). ResourceTypeOrNameArgs(args...). Latest() printer, generic, err := PrinterForCommand(cmd) checkErr(err) if generic { clientConfig, err := f.ClientConfig(cmd) checkErr(err) defaultVersion := clientConfig.Version // the outermost object will be converted to the output-version version := outputVersion(cmd, defaultVersion) if len(version) == 0 { // TODO: add a new ResourceBuilder mode for Object() that attempts to ensure the objects // are in the appropriate version if one exists (and if not, use the best effort). // TODO: ensure api-version is set with the default preferred api version by the client // builder on initialization version = latest.Version } printer = kubectl.NewVersionedPrinter(printer, api.Scheme, version) obj, err := b.Flatten().Do().Object() checkErr(err) err = printer.PrintObj(obj, out) checkErr(err) return } // use the default printer for each object err = b.Do().Visit(func(r *resource.Info) error { printer, err := PrinterForMapping(f, cmd, r.Mapping) if err != nil { return err } return printer.PrintObj(r.Object, out) }) checkErr(err) }
// RunGet implements the generic Get command // TODO: convert all direct flag accessors to a struct and pass that instead of cmd func RunGet(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, args []string) error { selector := cmdutil.GetFlagString(cmd, "selector") mapper, typer := f.Object() cmdNamespace, err := f.DefaultNamespace() if err != nil { return err } // handle watch separately since we cannot watch multiple resource types isWatch, isWatchOnly := cmdutil.GetFlagBool(cmd, "watch"), cmdutil.GetFlagBool(cmd, "watch-only") if isWatch || isWatchOnly { r := resource.NewBuilder(mapper, typer, f.ClientMapperForCommand()). NamespaceParam(cmdNamespace).DefaultNamespace(). SelectorParam(selector). ResourceTypeOrNameArgs(true, args...). SingleResourceType(). Do() if err != nil { return err } mapping, err := r.ResourceMapping() if err != nil { return err } printer, err := f.PrinterForMapping(cmd, mapping) if err != nil { return err } obj, err := r.Object() if err != nil { return err } rv, err := mapping.MetadataAccessor.ResourceVersion(obj) if err != nil { return err } // print the current object if !isWatchOnly { if err := printer.PrintObj(obj, out); err != nil { return fmt.Errorf("unable to output the provided object: %v", err) } } // print watched changes w, err := r.Watch(rv) if err != nil { return err } kubectl.WatchLoop(w, func(e watch.Event) error { return printer.PrintObj(e.Object, out) }) return nil } b := resource.NewBuilder(mapper, typer, f.ClientMapperForCommand()). NamespaceParam(cmdNamespace).DefaultNamespace(). SelectorParam(selector). ResourceTypeOrNameArgs(true, args...). ContinueOnError(). Latest() printer, generic, err := cmdutil.PrinterForCommand(cmd) if err != nil { return err } if generic { clientConfig, err := f.ClientConfig() if err != nil { return err } defaultVersion := clientConfig.Version singular := false r := b.Flatten().Do() infos, err := r.IntoSingular(&singular).Infos() if err != nil { return err } // the outermost object will be converted to the output-version, but inner // objects can use their mappings version := cmdutil.OutputVersion(cmd, defaultVersion) obj, err := resource.AsVersionedObject(infos, !singular, version) if err != nil { return err } return printer.PrintObj(obj, out) } // use the default printer for each object return b.Do().Visit(func(r *resource.Info) error { printer, err := f.PrinterForMapping(cmd, r.Mapping) if err != nil { return err } return printer.PrintObj(r.Object, out) }) }