top_node.go 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147
  1. /*
  2. Copyright 2016 The Kubernetes Authors.
  3. Licensed under the Apache License, Version 2.0 (the "License");
  4. you may not use this file except in compliance with the License.
  5. You may obtain a copy of the License at
  6. http://www.apache.org/licenses/LICENSE-2.0
  7. Unless required by applicable law or agreed to in writing, software
  8. distributed under the License is distributed on an "AS IS" BASIS,
  9. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  10. See the License for the specific language governing permissions and
  11. limitations under the License.
  12. */
  13. package cmd
  14. import (
  15. "errors"
  16. "io"
  17. cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
  18. "k8s.io/kubernetes/pkg/kubectl/metricsutil"
  19. "github.com/renstrom/dedent"
  20. "github.com/spf13/cobra"
  21. "k8s.io/kubernetes/pkg/api"
  22. "k8s.io/kubernetes/pkg/labels"
  23. )
  24. // TopNodeOptions contains all the options for running the top-node cli command.
  25. type TopNodeOptions struct {
  26. ResourceName string
  27. Selector string
  28. Client *metricsutil.HeapsterMetricsClient
  29. Printer *metricsutil.TopCmdPrinter
  30. }
  31. var (
  32. topNodeLong = dedent.Dedent(`
  33. Display Resource (CPU/Memory/Storage) usage of nodes.
  34. The top-node command allows you to see the resource consumption of nodes.`)
  35. topNodeExample = dedent.Dedent(`
  36. # Show metrics for all nodes
  37. kubectl top node
  38. # Show metrics for a given node
  39. kubectl top node NODE_NAME`)
  40. )
  41. func NewCmdTopNode(f *cmdutil.Factory, out io.Writer) *cobra.Command {
  42. options := &TopNodeOptions{}
  43. cmd := &cobra.Command{
  44. Use: "node [NAME | -l label]",
  45. Short: "Display Resource (CPU/Memory/Storage) usage of nodes",
  46. Long: topNodeLong,
  47. Example: topNodeExample,
  48. Run: func(cmd *cobra.Command, args []string) {
  49. if err := options.Complete(f, cmd, args, out); err != nil {
  50. cmdutil.CheckErr(err)
  51. }
  52. if err := options.Validate(); err != nil {
  53. cmdutil.CheckErr(cmdutil.UsageError(cmd, err.Error()))
  54. }
  55. if err := options.RunTopNode(); err != nil {
  56. cmdutil.CheckErr(err)
  57. }
  58. },
  59. Aliases: []string{"nodes"},
  60. }
  61. cmd.Flags().StringVarP(&options.Selector, "selector", "l", "", "Selector (label query) to filter on")
  62. return cmd
  63. }
  64. func (o *TopNodeOptions) Complete(f *cmdutil.Factory, cmd *cobra.Command, args []string, out io.Writer) error {
  65. var err error
  66. if len(args) == 1 {
  67. o.ResourceName = args[0]
  68. } else if len(args) > 1 {
  69. return cmdutil.UsageError(cmd, cmd.Use)
  70. }
  71. cli, err := f.Client()
  72. if err != nil {
  73. return err
  74. }
  75. o.Client = metricsutil.DefaultHeapsterMetricsClient(cli)
  76. o.Printer = metricsutil.NewTopCmdPrinter(out)
  77. return nil
  78. }
  79. func (o *TopNodeOptions) Validate() error {
  80. if len(o.ResourceName) > 0 && len(o.Selector) > 0 {
  81. return errors.New("only one of NAME or --selector can be provided")
  82. }
  83. if len(o.Selector) > 0 {
  84. _, err := labels.Parse(o.Selector)
  85. if err != nil {
  86. return err
  87. }
  88. }
  89. return nil
  90. }
  91. func (o TopNodeOptions) RunTopNode() error {
  92. var err error
  93. selector := labels.Everything()
  94. if len(o.Selector) > 0 {
  95. selector, err = labels.Parse(o.Selector)
  96. if err != nil {
  97. return err
  98. }
  99. }
  100. metrics, err := o.Client.GetNodeMetrics(o.ResourceName, selector)
  101. if err != nil {
  102. return err
  103. }
  104. var nodes []api.Node
  105. if len(o.ResourceName) > 0 {
  106. node, err := o.Client.Nodes().Get(o.ResourceName)
  107. if err != nil {
  108. return err
  109. }
  110. nodes = append(nodes, *node)
  111. } else {
  112. nodeList, err := o.Client.Nodes().List(api.ListOptions{
  113. LabelSelector: selector,
  114. })
  115. if err != nil {
  116. return err
  117. }
  118. nodes = append(nodes, nodeList.Items...)
  119. }
  120. allocatable := make(map[string]api.ResourceList)
  121. for _, n := range nodes {
  122. allocatable[n.Name] = n.Status.Allocatable
  123. }
  124. return o.Printer.PrintNodeMetrics(metrics, allocatable)
  125. }