perf: Pre-compile regexes in updates/version package

Move regex compilation from function bodies to package-level variables
to avoid recompilation when parsing version strings.

Affected regexes:
- semverRe: Matches semantic version format (X.Y.Z-prerelease+build)
- rcNumRe: Extracts RC number from prerelease strings

These are called multiple times during version comparison and update checks.
This commit is contained in:
rcourtman 2025-12-02 15:14:15 +00:00
parent fd3c57377c
commit a965285738

View file

@ -12,6 +12,12 @@ import (
"time" "time"
) )
// Pre-compiled regexes for performance (avoid recompilation on each call)
var (
semverRe = regexp.MustCompile(`^(\d+)\.(\d+)\.(\d+)(?:-([^+]+))?(?:\+(.+))?$`)
rcNumRe = regexp.MustCompile(`rc\.?(\d+)`)
)
// Version represents a semantic version // Version represents a semantic version
type Version struct { type Version struct {
Major int Major int
@ -38,9 +44,7 @@ func ParseVersion(versionStr string) (*Version, error) {
// Remove 'v' prefix if present // Remove 'v' prefix if present
versionStr = strings.TrimPrefix(versionStr, "v") versionStr = strings.TrimPrefix(versionStr, "v")
// Regular expression for semantic versioning matches := semverRe.FindStringSubmatch(versionStr)
re := regexp.MustCompile(`^(\d+)\.(\d+)\.(\d+)(?:-([^+]+))?(?:\+(.+))?$`)
matches := re.FindStringSubmatch(versionStr)
if len(matches) == 0 { if len(matches) == 0 {
return nil, fmt.Errorf("invalid version format: %s", versionStr) return nil, fmt.Errorf("invalid version format: %s", versionStr)
@ -405,8 +409,7 @@ func compareInts(a, b int) int {
// extractRCNumber extracts the RC number from a prerelease string like "rc.9" or "rc9" // extractRCNumber extracts the RC number from a prerelease string like "rc.9" or "rc9"
func extractRCNumber(prerelease string) int { func extractRCNumber(prerelease string) int {
re := regexp.MustCompile(`rc\.?(\d+)`) matches := rcNumRe.FindStringSubmatch(strings.ToLower(prerelease))
matches := re.FindStringSubmatch(strings.ToLower(prerelease))
if len(matches) > 1 { if len(matches) > 1 {
num, err := strconv.Atoi(matches[1]) num, err := strconv.Atoi(matches[1])
if err == nil { if err == nil {