1// Copyright (C) MongoDB, Inc. 2014-present.
2//
3// Licensed under the Apache License, Version 2.0 (the "License"); you may
4// not use this file except in compliance with the License. You may obtain
5// a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
6
7package line
8
9import (
10	"github.com/mongodb/mongo-tools/mongostat/status"
11)
12
13// Flags to determine cases when to activate/deactivate columns for output.
14const (
15	FlagAlways   = 1 << iota // always activate the column
16	FlagHosts                // only active if we may have multiple hosts
17	FlagDiscover             // only active when mongostat is in discover mode
18	FlagRepl                 // only active if one of the nodes being monitored is in a replset
19	FlagLocks                // only active if node is capable of calculating lock info
20	FlagAll                  // only active if mongostat was run with --all option
21	FlagMMAP                 // only active if node has mmap-specific fields
22	FlagWT                   // only active if node has wiredtiger-specific fields
23)
24
25// StatHeader describes a single column for mongostat's terminal output,
26// its formatting, and in which modes it should be displayed.
27type StatHeader struct {
28	// ReadField produces a particular field according to the StatHeader instance.
29	// Some fields are based on a diff, so both latest ServerStatuses are taken.
30	ReadField func(c *status.ReaderConfig, newStat, oldStat *status.ServerStatus) string
31}
32
33// StatHeaders are the complete set of data metrics supported by mongostat.
34var (
35	keyNames = map[string][]string{ // short, long, deprecated
36		"host":           {"host", "Host", "host"},
37		"storage_engine": {"storage_engine", "Storage engine", "engine"},
38		"insert":         {"insert", "Insert opcounter (diff)", "insert"},
39		"query":          {"query", "Query opcounter (diff)", "query"},
40		"update":         {"update", "Update opcounter (diff)", "update"},
41		"delete":         {"delete", "Delete opcounter (diff)", "delete"},
42		"getmore":        {"getmore", "GetMore opcounter (diff)", "getmore"},
43		"command":        {"command", "Command opcounter (diff)", "command"},
44		"dirty":          {"dirty", "Cache dirty (percentage)", "% dirty"},
45		"used":           {"used", "Cache used (percentage)", "% used"},
46		"flushes":        {"flushes", "Number of flushes (diff)", "flushes"},
47		"mapped":         {"mapped", "Mapped (size)", "mapped"},
48		"vsize":          {"vsize", "Virtual (size)", "vsize"},
49		"res":            {"res", "Resident (size)", "res"},
50		"nonmapped":      {"nonmapped", "Non-mapped (size)", "non-mapped"},
51		"faults":         {"faults", "Page faults (diff)", "faults"},
52		"lrw":            {"lrw", "Lock acquire count, read|write (diff percentage)", "lr|lw %"},
53		"lrwt":           {"lrwt", "Lock acquire time, read|write (diff percentage)", "lrt|lwt"},
54		"locked_db":      {"locked_db", "Locked db info, '(db):(percentage)'", "locked"},
55		"qrw":            {"qrw", "Queued accesses, read|write", "qr|qw"},
56		"arw":            {"arw", "Active accesses, read|write", "ar|aw"},
57		"net_in":         {"net_in", "Network input (size)", "netIn"},
58		"net_out":        {"net_out", "Network output (size)", "netOut"},
59		"conn":           {"conn", "Current connection count", "conn"},
60		"set":            {"set", "FlagReplica set name", "set"},
61		"repl":           {"repl", "FlagReplica set type", "repl"},
62		"time":           {"time", "Time of sample", "time"},
63	}
64	StatHeaders = map[string]StatHeader{
65		"host":           {status.ReadHost},
66		"storage_engine": {status.ReadStorageEngine},
67		"insert":         {status.ReadInsert},
68		"query":          {status.ReadQuery},
69		"update":         {status.ReadUpdate},
70		"delete":         {status.ReadDelete},
71		"getmore":        {status.ReadGetMore},
72		"command":        {status.ReadCommand},
73		"dirty":          {status.ReadDirty},
74		"used":           {status.ReadUsed},
75		"flushes":        {status.ReadFlushes},
76		"mapped":         {status.ReadMapped},
77		"vsize":          {status.ReadVSize},
78		"res":            {status.ReadRes},
79		"nonmapped":      {status.ReadNonMapped},
80		"faults":         {status.ReadFaults},
81		"lrw":            {status.ReadLRW},
82		"lrwt":           {status.ReadLRWT},
83		"locked_db":      {status.ReadLockedDB},
84		"qrw":            {status.ReadQRW},
85		"arw":            {status.ReadARW},
86		"net_in":         {status.ReadNetIn},
87		"net_out":        {status.ReadNetOut},
88		"conn":           {status.ReadConn},
89		"set":            {status.ReadSet},
90		"repl":           {status.ReadRepl},
91		"time":           {status.ReadTime},
92	}
93	CondHeaders = []struct {
94		Key  string
95		Flag int
96	}{
97		{"host", FlagHosts},
98		{"insert", FlagAlways},
99		{"query", FlagAlways},
100		{"update", FlagAlways},
101		{"delete", FlagAlways},
102		{"getmore", FlagAlways},
103		{"command", FlagAlways},
104		{"dirty", FlagWT},
105		{"used", FlagWT},
106		{"flushes", FlagAlways},
107		{"mapped", FlagMMAP},
108		{"vsize", FlagAlways},
109		{"res", FlagAlways},
110		{"nonmapped", FlagMMAP | FlagAll},
111		{"faults", FlagMMAP},
112		{"lrw", FlagMMAP | FlagAll},
113		{"lrwt", FlagMMAP | FlagAll},
114		{"locked_db", FlagLocks},
115		{"qrw", FlagAlways},
116		{"arw", FlagAlways},
117		{"net_in", FlagAlways},
118		{"net_out", FlagAlways},
119		{"conn", FlagAlways},
120		{"set", FlagRepl},
121		{"repl", FlagRepl},
122		{"time", FlagAlways},
123	}
124)
125
126func defaultKeyMap(index int) map[string]string {
127	names := make(map[string]string)
128	for k, v := range keyNames {
129		names[k] = v[index]
130	}
131	return names
132}
133
134func DefaultKeyMap() map[string]string {
135	return defaultKeyMap(0)
136}
137
138func LongKeyMap() map[string]string {
139	return defaultKeyMap(1)
140}
141
142func DeprecatedKeyMap() map[string]string {
143	return defaultKeyMap(2)
144}
145