bugfix: Initialize metrics with empty tags (#2847)

* Initialize metrics with empty tags

* Better name for Project tags

* No need for dedicated set scope tags on metrics
This commit is contained in:
Fabiano Soares Honorato
2022-12-21 15:36:44 -03:00
committed by GitHub
parent f680e4b4a4
commit 9a38e35493
4 changed files with 55 additions and 13 deletions

View File

@@ -98,20 +98,23 @@ type ProjectContext struct {
ExecutionOrderGroup int
}
// SetScopeTags adds ProjectContext tags to a new returned scope.
func (p ProjectContext) SetScopeTags(scope tally.Scope) tally.Scope {
// SetProjectScopeTags adds ProjectContext tags to a new returned scope.
func (p ProjectContext) SetProjectScopeTags(scope tally.Scope) tally.Scope {
v := ""
if p.TerraformVersion != nil {
v = p.TerraformVersion.String()
}
return scope.Tagged(map[string]string{
"base_repo": p.BaseRepo.FullName,
"pr_number": strconv.Itoa(p.Pull.Num),
"project": p.ProjectName,
"project_path": p.RepoRelDir,
"terraform_version": v,
"workspace": p.Workspace,
})
tags := ProjectScopeTags{
BaseRepo: p.BaseRepo.FullName,
PrNumber: strconv.Itoa(p.Pull.Num),
Project: p.ProjectName,
ProjectPath: p.RepoRelDir,
TerraformVersion: v,
Workspace: p.Workspace,
}
return scope.Tagged(tags.Loadtags())
}
// GetShowResultFileName returns the filename (not the path) to store the tf show result

View File

@@ -0,0 +1,38 @@
package command
import (
"reflect"
"regexp"
"strings"
)
type ProjectScopeTags struct {
BaseRepo string
PrNumber string
Project string
ProjectPath string
TerraformVersion string
Workspace string
}
func (s ProjectScopeTags) Loadtags() map[string]string {
tags := make(map[string]string)
v := reflect.ValueOf(s)
t := v.Type()
for i := 0; i < v.NumField(); i++ {
tags[toSnakeCase(t.Field(i).Name)] = v.Field(i).String()
}
return tags
}
func toSnakeCase(str string) string {
var matchFirstCap = regexp.MustCompile("(.)([A-Z][a-z]+)")
var matchAllCap = regexp.MustCompile("([a-z0-9])([A-Z])")
snake := matchFirstCap.ReplaceAllString(str, "${1}_${2}")
snake = matchAllCap.ReplaceAllString(snake, "${1}_${2}")
return strings.ToLower(snake)
}

View File

@@ -19,7 +19,8 @@ type InstrumentedProjectCommandRunner struct {
}
func NewInstrumentedProjectCommandRunner(scope tally.Scope, projectCommandRunner ProjectCommandRunner) *InstrumentedProjectCommandRunner {
scope = scope.SubScope("project")
projectTags := command.ProjectScopeTags{}
scope = scope.Tagged(projectTags.Loadtags())
for _, m := range []string{metrics.ExecutionSuccessMetric, metrics.ExecutionErrorMetric, metrics.ExecutionFailureMetric} {
metrics.InitCounter(scope, m)
@@ -49,7 +50,7 @@ func (p *InstrumentedProjectCommandRunner) ApprovePolicies(ctx command.ProjectCo
func RunAndEmitStats(commandName string, ctx command.ProjectContext, execute func(ctx command.ProjectContext) command.ProjectResult, scope tally.Scope) command.ProjectResult {
// ensures we are differentiating between project level command and overall command
scope = ctx.SetScopeTags(scope)
scope = ctx.SetProjectScopeTags(scope)
logger := ctx.Log
executionTime := scope.Timer(metrics.ExecutionTimeMetric).Start()

View File

@@ -78,7 +78,7 @@ func (cb *CommandScopedStatsProjectCommandContextBuilder) BuildProjectContext(
// specifically use the command name in the context instead of the arg
// since we can return multiple commands worth of contexts for a given command name arg
// to effectively pipeline them.
cmd.Scope = cmd.SetScopeTags(cmd.Scope)
cmd.Scope = cmd.SetProjectScopeTags(cmd.Scope)
projectCmds = append(projectCmds, cmd)
}