diff --git a/docs/pt-mongodb-query-digest.rst b/docs/pt-mongodb-query-digest.rst index 36edcf7c..22cf6521 100644 --- a/docs/pt-mongodb-query-digest.rst +++ b/docs/pt-mongodb-query-digest.rst @@ -45,6 +45,10 @@ Options ``-d``, ``--database`` Specifies which database to profile +``-f``, ``--output-format`` + Specifies the report output format. Valid options are: ``text``, ``json``. + The default value is ``text``. + ``-l``, ``--log-level`` Specifies the log level: ``panic``, ``fatal``, ``error``, ``warn``, ``info``, ``debug error`` diff --git a/docs/pt-mongodb-summary.rst b/docs/pt-mongodb-summary.rst index e5b0b074..5bb3c4a7 100644 --- a/docs/pt-mongodb-summary.rst +++ b/docs/pt-mongodb-summary.rst @@ -35,6 +35,10 @@ Options with a MongoDB server. By default, the ``admin`` database is used. +``-f``, ``--output-format`` + Specifies the report output format. Valid options are: ``text``, ``json``. + The default value is ``text``. + ``-p``, ``--password`` Specifies the password to use when connecting to a server with authentication enabled. diff --git a/src/go/pt-mongodb-query-digest/README.md b/src/go/pt-mongodb-query-digest/README.md index dca9948e..f7db1109 100644 --- a/src/go/pt-mongodb-query-digest/README.md +++ b/src/go/pt-mongodb-query-digest/README.md @@ -38,6 +38,7 @@ The last step is sorting the results. The default sort order is by ascending que |-a|--authenticationDatabase|database used to establish credentials and privileges with a MongoDB server admin| |-c|--no-version-check|Don't check for updates| |-d|--database|database to profile| +|-f|--output-format|report output format. Valid values are text, json. Default: text| |-l|--log-level|Log level:, panic, fatal, error, warn, info, debug error| |-n|--limit|show the first n queries| |-o|--order-by|comma separated list of order by fields (max values): `count`, `ratio`, `query-time`, `docs-scanned`, `docs-returned`.
A `-` in front of the field name denotes reverse order.
Example:`--order-by="count,-ratio"`).| diff --git a/src/go/pt-mongodb-query-digest/main.go b/src/go/pt-mongodb-query-digest/main.go index eb50bb33..a5681913 100644 --- a/src/go/pt-mongodb-query-digest/main.go +++ b/src/go/pt-mongodb-query-digest/main.go @@ -1,6 +1,8 @@ package main import ( + "bytes" + "encoding/json" "fmt" "os" "sort" @@ -59,6 +61,12 @@ type options struct { Version bool } +type report struct { + Headers []string + QueryStats []stats.QueryStats + QueryTotals stats.QueryStats +} + func main() { opts, err := getOptions() @@ -148,65 +156,56 @@ func main() { queriesStats := queries.CalcQueriesStats(uptime) sortedQueryStats := sortQueries(queriesStats, opts.OrderBy) - - queryTotals := queries.CalcTotalQueriesStats(uptime) - tt, _ := template.New("query").Funcs(template.FuncMap{ - "Format": format, - }).Parse(getTotalsTemplate()) - tt.Execute(os.Stdout, queryTotals) - - t, _ := template.New("query").Funcs(template.FuncMap{ - "Format": format, - }).Parse(getQueryTemplate()) - if opts.Limit > 0 && len(sortedQueryStats) > opts.Limit { sortedQueryStats = sortedQueryStats[:opts.Limit] } - for _, qs := range sortedQueryStats { - t.Execute(os.Stdout, qs) + + rep := report{ + Headers: getHeaders(opts), + QueryTotals: queries.CalcTotalQueriesStats(uptime), + QueryStats: sortedQueryStats, } + out, err := formatResults(rep, opts.OutputFormat) + if err != nil { + log.Errorf("Cannot parse the report: %s", err.Error()) + os.Exit(5) + } + + fmt.Println(string(out)) + } -func formatResults(stats []stats.QueryStats, opts options, format string) ([]byte, error) { +func formatResults(rep report, outputFormat string) ([]byte, error) { var buf *bytes.Buffer - switch format { + switch outputFormat { case "json": - b, err := json.MarshalIndent(stats, "", " ") + b, err := json.MarshalIndent(rep, "", " ") if err != nil { return nil, fmt.Errorf("[Error] Cannot convert results to json: %s", err.Error()) } buf = bytes.NewBuffer(b) default: - printHeader(opts) buf = new(bytes.Buffer) - t := template.Must(template.New("replicas").Parse(templates.Replicas)) - t.Execute(buf, ci.ReplicaMembers) + tt, _ := template.New("query").Funcs(template.FuncMap{ + "Format": format, + }).Parse(getTotalsTemplate()) + tt.Execute(buf, rep.QueryTotals) - t = template.Must(template.New("hosttemplateData").Parse(templates.HostInfo)) - t.Execute(buf, ci.HostInfo) + t, _ := template.New("query").Funcs(template.FuncMap{ + "Format": format, + }).Parse(getQueryTemplate()) - t = template.Must(template.New("runningOps").Parse(templates.RunningOps)) - t.Execute(buf, ci.RunningOps) - - t = template.Must(template.New("ssl").Parse(templates.Security)) - t.Execute(buf, ci.SecuritySettings) - - if ci.OplogInfo != nil && len(ci.OplogInfo) > 0 { - t = template.Must(template.New("oplogInfo").Parse(templates.Oplog)) - t.Execute(buf, ci.OplogInfo[0]) + for _, qs := range rep.QueryStats { + t.Execute(buf, qs) } - - t = template.Must(template.New("clusterwide").Parse(templates.Clusterwide)) - t.Execute(buf, ci.ClusterWideInfo) - - t = template.Must(template.New("balancer").Parse(templates.BalancerStats)) - t.Execute(buf, ci.BalancerStats) } return buf.Bytes(), nil +} + // format scales a number and returns a string made of the scaled value and unit (K=Kilo, M=Mega, T=Tera) // using I.F where i is the number of digits for the integer part and F is the number of digits for the // decimal part @@ -303,6 +302,7 @@ func getOptions() (*options, error) { } if opts.OutputFormat != "json" && opts.OutputFormat != "text" { + opts.OutputFormat = "text" log.Infof("Invalid output format '%s'. Using text format", opts.OutputFormat) } @@ -348,11 +348,13 @@ func getDialInfo(opts *options) *pmgo.DialInfo { return pmgoDialInfo } -func printHeader(opts *options) { - fmt.Printf("%s - %s\n", TOOLNAME, time.Now().Format(time.RFC1123Z)) - fmt.Printf("Host: %s\n", opts.Host) - fmt.Printf("Skipping profiled queries on these collections: %v\n", opts.SkipCollections) - fmt.Println("") +func getHeaders(opts *options) []string { + h := []string{ + fmt.Sprintf("%s - %s\n", TOOLNAME, time.Now().Format(time.RFC1123Z)), + fmt.Sprintf("Host: %s\n", opts.Host), + fmt.Sprintf("Skipping profiled queries on these collections: %v\n", opts.SkipCollections), + } + return h } func getQueryTemplate() string { diff --git a/src/go/pt-mongodb-query-digest/main_test.go b/src/go/pt-mongodb-query-digest/main_test.go index 8260b180..db7847d5 100644 --- a/src/go/pt-mongodb-query-digest/main_test.go +++ b/src/go/pt-mongodb-query-digest/main_test.go @@ -67,6 +67,7 @@ func TestParseArgs(t *testing.T) { OrderBy: strings.Split(DEFAULT_ORDERBY, ","), SkipCollections: strings.Split(DEFAULT_SKIPCOLLECTIONS, ","), AuthDB: DEFAULT_AUTHDB, + OutputFormat: "text", }, }, { @@ -82,6 +83,7 @@ func TestParseArgs(t *testing.T) { SkipCollections: strings.Split(DEFAULT_SKIPCOLLECTIONS, ","), AuthDB: DEFAULT_AUTHDB, Help: false, + OutputFormat: "text", }, }, } diff --git a/src/go/pt-mongodb-summary/README.rst b/src/go/pt-mongodb-summary/README.rst index 551f59ac..bc429358 100644 --- a/src/go/pt-mongodb-summary/README.rst +++ b/src/go/pt-mongodb-summary/README.rst @@ -15,16 +15,14 @@ Please check the `releases `_ ta Paramters ^^^^^^^^^ -===== ============== ======= ================================================================================ -Short Long Default Description -===== ============== ======= ================================================================================ -u user empty user name to use when connecting if DB auth is enabled -p password empty password to use when connecting if DB auth is enabled -a auth-db admin database used to establish credentials and privileges with a MongoDB server -f output-format text output format: text, json. Default: text -===== ============== ======= ================================================================================ +|Short|Long|Default|Description| +|-----|----|-------|-----------| +|-a|--auth-db|admin|database used to establish credentials and privileges with a MongoDB server| +|-f|--output-format|report output format|Valid values are text, json. Default: text| +|-f|--output-format|text|output format: text, json. Default: text| +|-p|--password|empty|password to use when connecting if DB auth is enabled| +|-u|--user|empty|user name to use when connecting if DB auth is enabled| -| ``-p`` is an optional parameter. If it is used it shouldn't have a blank between the parameter and its value: `-p` It can be also used as `-p` without specifying a password; in that case, the program will ask the password to avoid using a password in the command line.