github.com/jcarley/cli@v0.0.0-20180201210820-966d90434c30/commands/metrics/contract.go (about)

     1  package metrics
     2  
     3  import (
     4  	"github.com/Sirupsen/logrus"
     5  	"github.com/daticahealth/cli/commands/services"
     6  	"github.com/daticahealth/cli/config"
     7  	"github.com/daticahealth/cli/lib/auth"
     8  	"github.com/daticahealth/cli/lib/prompts"
     9  	"github.com/daticahealth/cli/models"
    10  	"github.com/jault3/mow.cli"
    11  )
    12  
    13  type MetricType uint8
    14  
    15  const (
    16  	CPU MetricType = iota
    17  	Memory
    18  	NetworkIn
    19  	NetworkOut
    20  )
    21  
    22  // Cmd is the contract between the user and the CLI. This specifies the command
    23  // name, arguments, and required/optional arguments and flags for the command.
    24  var Cmd = models.Command{
    25  	Name:      "metrics",
    26  	ShortHelp: "Print service and environment metrics in your local time zone",
    27  	LongHelp: "The <code>metrics</code> command gives access to environment metrics or individual service metrics through a variety of formats. " +
    28  		"This is useful for checking on the status and performance of your application or environment as a whole. " +
    29  		"The metrics command cannot be run directly but has subcommands.",
    30  	CmdFunc: func(settings *models.Settings) func(cmd *cli.Cmd) {
    31  		return func(cmd *cli.Cmd) {
    32  			cmd.CommandLong(CPUSubCmd.Name, CPUSubCmd.ShortHelp, CPUSubCmd.LongHelp, CPUSubCmd.CmdFunc(settings))
    33  			cmd.CommandLong(MemorySubCmd.Name, MemorySubCmd.ShortHelp, MemorySubCmd.LongHelp, MemorySubCmd.CmdFunc(settings))
    34  			cmd.CommandLong(NetworkInSubCmd.Name, NetworkInSubCmd.ShortHelp, NetworkInSubCmd.LongHelp, NetworkInSubCmd.CmdFunc(settings))
    35  			cmd.CommandLong(NetworkOutSubCmd.Name, NetworkOutSubCmd.ShortHelp, NetworkOutSubCmd.LongHelp, NetworkOutSubCmd.CmdFunc(settings))
    36  		}
    37  	},
    38  }
    39  
    40  var CPUSubCmd = models.Command{
    41  	Name:      "cpu",
    42  	ShortHelp: "Print service and environment CPU metrics in your local time zone",
    43  	LongHelp: "<code>metrics cpu</code> prints out CPU metrics for your environment or individual services. " +
    44  		"You can print out metrics in csv, json, plain text, or spark lines format. " +
    45  		"If you want plain text format, omit the <code>--json</code> and <code>--csv</code> flags. " +
    46  		"You can only stream metrics using plain text or spark lines formats. " +
    47  		"To print out metrics for every service in your environment, omit the <code>SERVICE_NAME</code> argument. " +
    48  		"Otherwise you may choose a service, such as an app service, to retrieve metrics for. " +
    49  		"Here are some sample commands\n\n" +
    50  		"<pre>\ndatica -E \"<your_env_name>\" metrics cpu\n" +
    51  		"datica -E \"<your_env_name>\" metrics cpu app01 --stream\n" +
    52  		"datica -E \"<your_env_name>\" metrics cpu --json\n" +
    53  		"datica -E \"<your_env_name>\" metrics cpu db01 --csv -m 60\n</pre>",
    54  	CmdFunc: func(settings *models.Settings) func(cmd *cli.Cmd) {
    55  		return func(subCmd *cli.Cmd) {
    56  			serviceName := subCmd.StringArg("SERVICE_NAME", "", "The name of the service to print metrics for")
    57  			json := subCmd.BoolOpt("json", false, "Output the data as json")
    58  			csv := subCmd.BoolOpt("csv", false, "Output the data as csv")
    59  			text := subCmd.BoolOpt("text", true, "Output the data in plain text")
    60  			stream := subCmd.BoolOpt("stream", false, "Repeat calls once per minute until this process is interrupted.")
    61  			mins := subCmd.IntOpt("m mins", 1, "How many minutes worth of metrics to retrieve.")
    62  			subCmd.Action = func() {
    63  				if _, err := auth.New(settings, prompts.New()).Signin(); err != nil {
    64  					logrus.Fatal(err.Error())
    65  				}
    66  				if err := config.CheckRequiredAssociation(settings); err != nil {
    67  					logrus.Fatal(err.Error())
    68  				}
    69  				err := CmdMetrics(*serviceName, CPU, *json, *csv, *text, *stream, *mins, New(settings), services.New(settings))
    70  				if err != nil {
    71  					logrus.Fatal(err.Error())
    72  				}
    73  			}
    74  			subCmd.Spec = "[SERVICE_NAME] [(--json | --csv | --text)] [--stream] [-m]"
    75  		}
    76  	},
    77  }
    78  
    79  var MemorySubCmd = models.Command{
    80  	Name:      "memory",
    81  	ShortHelp: "Print service and environment memory metrics in your local time zone",
    82  	LongHelp: "<code>metrics memory</code> prints out memory metrics for your environment or individual services. " +
    83  		"You can print out metrics in csv, json, plain text, or spark lines format. " +
    84  		"If you want plain text format, omit the <code>--json</code> and <code>--csv</code> flags. " +
    85  		"You can only stream metrics using plain text or spark lines formats. " +
    86  		"To print out metrics for every service in your environment, omit the <code>SERVICE_NAME</code> argument. " +
    87  		"Otherwise you may choose a service, such as an app service, to retrieve metrics for. " +
    88  		"Here are some sample commands\n\n" +
    89  		"<pre>\ndatica -E \"<your_env_name>\" metrics memory\n" +
    90  		"datica -E \"<your_env_name>\" metrics memory app01 --stream\n" +
    91  		"datica -E \"<your_env_name>\" metrics memory --json\n" +
    92  		"datica -E \"<your_env_name>\" metrics memory db01 --csv -m 60\n</pre>",
    93  	CmdFunc: func(settings *models.Settings) func(cmd *cli.Cmd) {
    94  		return func(subCmd *cli.Cmd) {
    95  			serviceName := subCmd.StringArg("SERVICE_NAME", "", "The name of the service to print metrics for")
    96  			json := subCmd.BoolOpt("json", false, "Output the data as json")
    97  			csv := subCmd.BoolOpt("csv", false, "Output the data as csv")
    98  			text := subCmd.BoolOpt("text", true, "Output the data in plain text")
    99  			stream := subCmd.BoolOpt("stream", false, "Repeat calls once per minute until this process is interrupted.")
   100  			mins := subCmd.IntOpt("m mins", 1, "How many minutes worth of metrics to retrieve.")
   101  			subCmd.Action = func() {
   102  				if _, err := auth.New(settings, prompts.New()).Signin(); err != nil {
   103  					logrus.Fatal(err.Error())
   104  				}
   105  				if err := config.CheckRequiredAssociation(settings); err != nil {
   106  					logrus.Fatal(err.Error())
   107  				}
   108  				err := CmdMetrics(*serviceName, Memory, *json, *csv, *text, *stream, *mins, New(settings), services.New(settings))
   109  				if err != nil {
   110  					logrus.Fatal(err.Error())
   111  				}
   112  			}
   113  			subCmd.Spec = "[SERVICE_NAME] [(--json | --csv | --text)] [--stream] [-m]"
   114  		}
   115  	},
   116  }
   117  
   118  var NetworkInSubCmd = models.Command{
   119  	Name:      "network-in",
   120  	ShortHelp: "Print service and environment received network data metrics in your local time zone",
   121  	LongHelp: "<code>metrics network-in</code> prints out received network metrics for your environment or individual services. " +
   122  		"You can print out metrics in csv, json, plain text, or spark lines format. " +
   123  		"If you want plain text format, omit the <code>--json</code> and <code>--csv</code> flags. " +
   124  		"You can only stream metrics using plain text or spark lines formats. " +
   125  		"To print out metrics for every service in your environment, omit the <code>SERVICE_NAME</code> argument. " +
   126  		"Otherwise you may choose a service, such as an app service, to retrieve metrics for. Here are some sample commands\n\n" +
   127  		"<pre>\ndatica -E \"<your_env_name>\" metrics network-in\n" +
   128  		"datica -E \"<your_env_name>\" metrics network-in app01 --stream\n" +
   129  		"datica -E \"<your_env_name>\" metrics network-in --json\n" +
   130  		"datica -E \"<your_env_name>\" metrics network-in db01 --csv -m 60\n</pre>",
   131  	CmdFunc: func(settings *models.Settings) func(cmd *cli.Cmd) {
   132  		return func(subCmd *cli.Cmd) {
   133  			serviceName := subCmd.StringArg("SERVICE_NAME", "", "The name of the service to print metrics for")
   134  			json := subCmd.BoolOpt("json", false, "Output the data as json")
   135  			csv := subCmd.BoolOpt("csv", false, "Output the data as csv")
   136  			text := subCmd.BoolOpt("text", true, "Output the data in plain text")
   137  			stream := subCmd.BoolOpt("stream", false, "Repeat calls once per minute until this process is interrupted.")
   138  			mins := subCmd.IntOpt("m mins", 1, "How many minutes worth of metrics to retrieve.")
   139  			subCmd.Action = func() {
   140  				if _, err := auth.New(settings, prompts.New()).Signin(); err != nil {
   141  					logrus.Fatal(err.Error())
   142  				}
   143  				if err := config.CheckRequiredAssociation(settings); err != nil {
   144  					logrus.Fatal(err.Error())
   145  				}
   146  				err := CmdMetrics(*serviceName, NetworkIn, *json, *csv, *text, *stream, *mins, New(settings), services.New(settings))
   147  				if err != nil {
   148  					logrus.Fatal(err.Error())
   149  				}
   150  			}
   151  			subCmd.Spec = "[SERVICE_NAME] [(--json | --csv | --text)] [--stream] [-m]"
   152  		}
   153  	},
   154  }
   155  
   156  var NetworkOutSubCmd = models.Command{
   157  	Name:      "network-out",
   158  	ShortHelp: "Print service and environment transmitted network data metrics in your local time zone",
   159  	LongHelp: "<code>metrics network-out</code> prints out transmitted network metrics for your environment or individual services. " +
   160  		"You can print out metrics in csv, json, plain text, or spark lines format. " +
   161  		"If you want plain text format, simply omit the <code>--json</code> and <code>--csv</code> flags. " +
   162  		"You can only stream metrics using plain text or spark lines formats. " +
   163  		"To print out metrics for every service in your environment, omit the <code>SERVICE_NAME</code> argument. " +
   164  		"Otherwise you may choose a service, such as an app service, to retrieve metrics for. " +
   165  		"Here are some sample commands\n\n" +
   166  		"<pre>\ndatica -E \"<your_env_name>\" metrics network-out\n" +
   167  		"datica -E \"<your_env_name>\" metrics network-out app01 --stream\n" +
   168  		"datica -E \"<your_env_name>\" metrics network-out --json\n" +
   169  		"datica -E \"<your_env_name>\" metrics network-out db01 --csv -m 60\n</pre>",
   170  	CmdFunc: func(settings *models.Settings) func(cmd *cli.Cmd) {
   171  		return func(subCmd *cli.Cmd) {
   172  			serviceName := subCmd.StringArg("SERVICE_NAME", "", "The name of the service to print metrics for")
   173  			json := subCmd.BoolOpt("json", false, "Output the data as json")
   174  			csv := subCmd.BoolOpt("csv", false, "Output the data as csv")
   175  			text := subCmd.BoolOpt("text", true, "Output the data in plain text")
   176  			stream := subCmd.BoolOpt("stream", false, "Repeat calls once per minute until this process is interrupted.")
   177  			mins := subCmd.IntOpt("m mins", 1, "How many minutes worth of metrics to retrieve.")
   178  			subCmd.Action = func() {
   179  				if _, err := auth.New(settings, prompts.New()).Signin(); err != nil {
   180  					logrus.Fatal(err.Error())
   181  				}
   182  				if err := config.CheckRequiredAssociation(settings); err != nil {
   183  					logrus.Fatal(err.Error())
   184  				}
   185  				err := CmdMetrics(*serviceName, NetworkOut, *json, *csv, *text, *stream, *mins, New(settings), services.New(settings))
   186  				if err != nil {
   187  					logrus.Fatal(err.Error())
   188  				}
   189  			}
   190  			subCmd.Spec = "[SERVICE_NAME] [(--json | --csv | --text)] [--stream] [-m]"
   191  		}
   192  	},
   193  }
   194  
   195  // IMetrics
   196  type IMetrics interface {
   197  	RetrieveEnvironmentMetrics(mins int) (*[]models.Metrics, error)
   198  	RetrieveServiceMetrics(mins int, svcID string) (*models.Metrics, error)
   199  }
   200  
   201  // SMetrics is a concrete implementation of IMetrics
   202  type SMetrics struct {
   203  	Settings *models.Settings
   204  }
   205  
   206  // New returns an instance of IMetrics
   207  func New(settings *models.Settings) IMetrics {
   208  	return &SMetrics{
   209  		Settings: settings,
   210  	}
   211  }