Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

metrics: add db QPS metric #9151

Merged
merged 19 commits into from
Feb 13, 2019
2 changes: 2 additions & 0 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,7 @@ type Status struct {
StatusPort uint `toml:"status-port" json:"status-port"`
MetricsAddr string `toml:"metrics-addr" json:"metrics-addr"`
MetricsInterval uint `toml:"metrics-interval" json:"metrics-interval"`
RecordQPSbyDB bool `toml:"record-db-qps" json:"record-db-qps"`
}

// Performance is the performance section of the config.
Expand Down Expand Up @@ -299,6 +300,7 @@ var defaultConf = Config{
ReportStatus: true,
StatusPort: 10080,
MetricsInterval: 15,
RecordQPSbyDB: false,
},
Performance: Performance{
MaxMemory: 0,
Expand Down
3 changes: 3 additions & 0 deletions config/config.toml.example
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,9 @@ metrics-addr = ""
# Prometheus client push interval in second, set \"0\" to disable prometheus push.
metrics-interval = 15

# Record statements qps by database name if it is enabled.
record-db-qps = false

[performance]
# Max CPUs to use, 0 use number of CPUs in the machine.
max-procs = 0
Expand Down
109 changes: 108 additions & 1 deletion executor/compiler.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,114 @@ func CountStmtNode(stmtNode ast.StmtNode, inRestrictedSQL bool) {
if inRestrictedSQL {
return
}
metrics.StmtNodeCounter.WithLabelValues(GetStmtLabel(stmtNode)).Inc()

typeLabel := GetStmtLabel(stmtNode)
metrics.StmtNodeCounter.WithLabelValues(typeLabel).Inc()

if !config.GetGlobalConfig().Status.RecordQPSbyDB {
return
}

dbLabels := getStmtDbLabel(stmtNode)
for dbLabel := range dbLabels {
metrics.DbStmtNodeCounter.WithLabelValues(dbLabel, typeLabel).Inc()
}
}

func getStmtDbLabel(stmtNode ast.StmtNode) map[string]struct{} {
dbLabelSet := make(map[string]struct{})

switch x := stmtNode.(type) {
case *ast.AlterTableStmt:
dbLabel := x.Table.Schema.O
dbLabelSet[dbLabel] = struct{}{}
case *ast.CreateIndexStmt:
dbLabel := x.Table.Schema.O
dbLabelSet[dbLabel] = struct{}{}
case *ast.CreateTableStmt:
dbLabel := x.Table.Schema.O
dbLabelSet[dbLabel] = struct{}{}
case *ast.InsertStmt:
iamzhoug37 marked this conversation as resolved.
Show resolved Hide resolved
dbLabels := getDbFromResultNode(x.Table.TableRefs)
for _, db := range dbLabels {
dbLabelSet[db] = struct{}{}
}
dbLabels = getDbFromResultNode(x.Select)
for _, db := range dbLabels {
dbLabelSet[db] = struct{}{}
}
case *ast.DropIndexStmt:
dbLabel := x.Table.Schema.O
dbLabelSet[dbLabel] = struct{}{}
case *ast.DropTableStmt:
tables := x.Tables
for _, table := range tables {
dbLabel := table.Schema.O
if _, ok := dbLabelSet[dbLabel]; !ok {
dbLabelSet[dbLabel] = struct{}{}
}
}
case *ast.SelectStmt:
dbLabels := getDbFromResultNode(x)
for _, db := range dbLabels {
dbLabelSet[db] = struct{}{}
}
case *ast.UpdateStmt:
if x.TableRefs != nil {
dbLabels := getDbFromResultNode(x.TableRefs.TableRefs)
for _, db := range dbLabels {
dbLabelSet[db] = struct{}{}
}
}
case *ast.DeleteStmt:
if x.TableRefs != nil {
dbLabels := getDbFromResultNode(x.TableRefs.TableRefs)
for _, db := range dbLabels {
dbLabelSet[db] = struct{}{}
}
}
}

return dbLabelSet
}

func getDbFromResultNode(resultNode ast.ResultSetNode) []string { //may have duplicate db name
var dbLabels []string

if resultNode == nil {
return dbLabels
}

switch x := resultNode.(type) {
case *ast.TableSource:
return getDbFromResultNode(x.Source)
case *ast.SelectStmt:
if x.From != nil {
return getDbFromResultNode(x.From.TableRefs)
}
case *ast.TableName:
dbLabels = append(dbLabels, x.DBInfo.Name.O)
case *ast.Join:
if x.Left != nil {
dbs := getDbFromResultNode(x.Left)
if dbs != nil {
for _, db := range dbs {
dbLabels = append(dbLabels, db)
}
}
}

if x.Right != nil {
dbs := getDbFromResultNode(x.Right)
if dbs != nil {
for _, db := range dbs {
dbLabels = append(dbLabels, db)
}
}
}
}

return dbLabels
}

// GetStmtLabel generates a label for a statement.
Expand Down
9 changes: 9 additions & 0 deletions metrics/executor.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,4 +36,13 @@ var (
Name: "statement_total",
Help: "Counter of StmtNode.",
}, []string{LblType})

// DbStmtNodeCounter records the number of statement with the same type and db.
DbStmtNodeCounter = prometheus.NewCounterVec(
prometheus.CounterOpts{
Namespace: "tidb",
Subsystem: "executor",
Name: "statement_db_total",
Help: "Counter of StmtNode by Database.",
}, []string{LblDb, LblType})
)
1 change: 1 addition & 0 deletions metrics/metrics.go
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,7 @@ func RegisterMetrics() {
prometheus.MustRegister(StatementPerTransaction)
prometheus.MustRegister(StatsInaccuracyRate)
prometheus.MustRegister(StmtNodeCounter)
prometheus.MustRegister(DbStmtNodeCounter)
prometheus.MustRegister(StoreQueryFeedbackCounter)
prometheus.MustRegister(TiKVBackoffCounter)
prometheus.MustRegister(TiKVBackoffHistogram)
Expand Down
1 change: 1 addition & 0 deletions metrics/session.go
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@ const (
LblError = "error"
LblRollback = "rollback"
LblType = "type"
LblDb = "db"
LblResult = "result"
LblSQLType = "sql_type"
LblGeneral = "general"
Expand Down