Skip to content

Instantly share code, notes, and snippets.

@aaron-prindle
Last active September 27, 2025 00:29
Show Gist options
  • Save aaron-prindle/7dbe934092717d1b047d0e7aba5dc171 to your computer and use it in GitHub Desktop.
Save aaron-prindle/7dbe934092717d1b047d0e7aba5dc171 to your computer and use it in GitHub Desktop.
declarative validation error matcher path translation feature - benchmark test code
import (
"fmt"
"regexp"
"testing"
)
// generateNormalizationRules is a helper function to create a slice of N pre-compiled normalization rules.
func generateNormalizationRules(n int) []NormalizationRule {
rules := make([]NormalizationRule, n)
for i := 0; i < n; i++ {
// Create a regex pattern and a corresponding replacement string.
// Example: `spec\.devices\.requests\[(\d+)\]\.allocationMode_99` -> "spec.devices.requests[$1].exactly.allocationMode_99"
pattern := fmt.Sprintf(`spec\.devices\.requests\[(\d+)\]\.allocationMode_%d`, i)
replacement := fmt.Sprintf("spec.devices.requests[$1].exactly.allocationMode_%d", i)
rules[i] = NormalizationRule{
Regexp: regexp.MustCompile(pattern),
Replacement: replacement,
}
}
return rules
}
func BenchmarkErrorMatcher_Matches_PathNormalization(b *testing.B) {
baseErr := func() *Error {
return &Error{Type: ErrorTypeInvalid, Detail: "some detail"}
}
benchmarks := []struct {
name string
numNormalizationRules int
setupMatcher func(n int) ErrorMatcher
getWantAndGotErrs func(n int) (*Error, *Error)
}{
{
name: "NoNormalization",
numNormalizationRules: 0,
setupMatcher: func(n int) ErrorMatcher {
// Matcher with ByField but no normalization rules.
return ErrorMatcher{}.ByField()
},
getWantAndGotErrs: func(n int) (*Error, *Error) {
// Simple case where fields do not match, and there's no normalization logic to run.
want := baseErr()
want.Field = "spec.devices.requests[0].allocationMode"
got := baseErr()
got.Field = "spec.devices.requests[0].someOtherField"
return want, got
},
},
{
name: "100Rules_WorstCase",
numNormalizationRules: 100,
setupMatcher: func(n int) ErrorMatcher {
rules := generateNormalizationRules(n)
return ErrorMatcher{}.ByFieldNormalized(rules)
},
getWantAndGotErrs: func(n int) (*Error, *Error) {
// Create errors that will match the LAST normalization rule,
// forcing the matcher to iterate through all N regex patterns.
idx := n - 1
want := baseErr()
want.Field = fmt.Sprintf("spec.devices.requests[0].allocationMode_%d", idx)
got := baseErr()
got.Field = fmt.Sprintf("spec.devices.requests[0].exactly.allocationMode_%d", idx)
return want, got
},
},
{
name: "1000Rules_WorstCase",
numNormalizationRules: 1000,
setupMatcher: func(n int) ErrorMatcher {
rules := generateNormalizationRules(n)
return ErrorMatcher{}.ByFieldNormalized(rules)
},
getWantAndGotErrs: func(n int) (*Error, *Error) {
// Create errors that will match the LAST normalization rule.
idx := n - 1
want := baseErr()
want.Field = fmt.Sprintf("spec.devices.requests[0].allocationMode_%d", idx)
got := baseErr()
got.Field = fmt.Sprintf("spec.devices.requests[0].exactly.allocationMode_%d", idx)
return want, got
},
},
}
for _, bm := range benchmarks {
b.Run(bm.name, func(b *testing.B) {
// Setup is done outside the timer.
matcher := bm.setupMatcher(bm.numNormalizationRules)
want, got := bm.getWantAndGotErrs(bm.numNormalizationRules)
b.ResetTimer()
// The loop will run the Matches function b.N times.
// The initial `want.Field != got.Field` check will fail, triggering the path normalization logic.
for i := 0; i < b.N; i++ {
matcher.Matches(want, got)
}
})
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment