Fix up regex.go

This commit is contained in:
2025-03-27 22:50:15 +01:00
parent e634fe28bd
commit f453079c72

View File

@@ -9,75 +9,9 @@ import (
lua "github.com/yuin/gopher-lua" lua "github.com/yuin/gopher-lua"
"modify/logger" "modify/logger"
"modify/utils"
) )
// RegexProcessor implements the Processor interface using regex patterns
type RegexProcessor struct{}
// ToLua sets capture groups as Lua variables (v1, v2, etc. for numeric values and s1, s2, etc. for strings)
func (p *RegexProcessor) ToLua(L *lua.LState, data interface{}) error {
captureGroups, ok := data.([]*CaptureGroup)
if !ok {
return fmt.Errorf("expected []*CaptureGroup for captures, got %T", data)
}
groupindex := 0
for _, capture := range captureGroups {
if capture.Name == "" {
// We don't want to change the name of the capture group
// Even if it's empty
tempName := fmt.Sprintf("%d", groupindex+1)
groupindex++
L.SetGlobal("s"+tempName, lua.LString(capture.Value))
val, err := strconv.ParseFloat(capture.Value, 64)
if err == nil {
L.SetGlobal("v"+tempName, lua.LNumber(val))
}
} else {
val, err := strconv.ParseFloat(capture.Value, 64)
if err == nil {
L.SetGlobal(capture.Name, lua.LNumber(val))
} else {
L.SetGlobal(capture.Name, lua.LString(capture.Value))
}
}
}
return nil
}
// FromLua implements the Processor interface for RegexProcessor
func (p *RegexProcessor) FromLuaCustom(L *lua.LState, captureGroups []*CaptureGroup) ([]*CaptureGroup, error) {
captureIndex := 0
for _, capture := range captureGroups {
if capture.Name == "" {
capture.Name = fmt.Sprintf("%d", captureIndex+1)
vVarName := fmt.Sprintf("v%s", capture.Name)
sVarName := fmt.Sprintf("s%s", capture.Name)
captureIndex++
vLuaVal := L.GetGlobal(vVarName)
sLuaVal := L.GetGlobal(sVarName)
if sLuaVal.Type() == lua.LTString {
capture.Updated = sLuaVal.String()
}
// Numbers have priority
if vLuaVal.Type() == lua.LTNumber {
capture.Updated = vLuaVal.String()
}
} else {
// Easy shit
capture.Updated = L.GetGlobal(capture.Name).String()
}
}
return captureGroups, nil
}
type CaptureGroup struct { type CaptureGroup struct {
Name string Name string
Value string Value string
@@ -86,8 +20,10 @@ type CaptureGroup struct {
} }
// ProcessContent applies regex replacement with Lua processing // ProcessContent applies regex replacement with Lua processing
func (p *RegexProcessor) ProcessContent(content string, pattern string, luaExpr string) (string, int, int, error) { func ProcessRegex(content string, command utils.ModifyCommand) (string, int, int, error) {
pattern = ResolveRegexPlaceholders(pattern) // We don't HAVE to do this multiple times for a pattern
// But it's quick enough for us to not care
pattern := resolveRegexPlaceholders(command.Pattern)
logger.Debug("Compiling regex pattern: %s", pattern) logger.Debug("Compiling regex pattern: %s", pattern)
compiledPattern, err := regexp.Compile(pattern) compiledPattern, err := regexp.Compile(pattern)
if err != nil { if err != nil {
@@ -96,8 +32,11 @@ func (p *RegexProcessor) ProcessContent(content string, pattern string, luaExpr
} }
logger.Debug("Compiled pattern successfully: %s", pattern) logger.Debug("Compiled pattern successfully: %s", pattern)
previous := luaExpr // Same here, it's just string concatenation, it won't kill us
luaExpr = BuildLuaScript(luaExpr) // More important is that we don't fuck up the command
// But we shouldn't be able to since it's passed by value
previous := command.LuaExpr
luaExpr := BuildLuaScript(command.LuaExpr)
logger.Debug("Transformed Lua expression: %q → %q", previous, luaExpr) logger.Debug("Transformed Lua expression: %q → %q", previous, luaExpr)
// Initialize Lua environment // Initialize Lua environment
@@ -199,7 +138,7 @@ func (p *RegexProcessor) ProcessContent(content string, pattern string, luaExpr
captureGroups = deduplicateGroups(captureGroups) captureGroups = deduplicateGroups(captureGroups)
if err := p.ToLua(L, captureGroups); err != nil { if err := toLua(L, captureGroups); err != nil {
logger.Error("Failed to set Lua variables: %v", err) logger.Error("Failed to set Lua variables: %v", err)
continue continue
} }
@@ -213,7 +152,7 @@ func (p *RegexProcessor) ProcessContent(content string, pattern string, luaExpr
logger.Trace("Lua script executed successfully") logger.Trace("Lua script executed successfully")
// Get modifications from Lua // Get modifications from Lua
captureGroups, err = p.FromLuaCustom(L, captureGroups) captureGroups, err = fromLua(L, captureGroups)
if err != nil { if err != nil {
logger.Error("Failed to retrieve modifications from Lua: %v", err) logger.Error("Failed to retrieve modifications from Lua: %v", err)
continue continue
@@ -314,7 +253,7 @@ func deduplicateGroups(captureGroups []*CaptureGroup) []*CaptureGroup {
// If it were not here our !num in a named capture group would // If it were not here our !num in a named capture group would
// Expand to another capture group in the capture group // Expand to another capture group in the capture group
// We really only want one (our named) capture group // We really only want one (our named) capture group
func ResolveRegexPlaceholders(pattern string) string { func resolveRegexPlaceholders(pattern string) string {
// Handle special pattern modifications // Handle special pattern modifications
if !strings.HasPrefix(pattern, "(?s)") { if !strings.HasPrefix(pattern, "(?s)") {
pattern = "(?s)" + pattern pattern = "(?s)" + pattern
@@ -348,3 +287,67 @@ func ResolveRegexPlaceholders(pattern string) string {
}) })
return pattern return pattern
} }
// ToLua sets capture groups as Lua variables (v1, v2, etc. for numeric values and s1, s2, etc. for strings)
func toLua(L *lua.LState, data interface{}) error {
captureGroups, ok := data.([]*CaptureGroup)
if !ok {
return fmt.Errorf("expected []*CaptureGroup for captures, got %T", data)
}
groupindex := 0
for _, capture := range captureGroups {
if capture.Name == "" {
// We don't want to change the name of the capture group
// Even if it's empty
tempName := fmt.Sprintf("%d", groupindex+1)
groupindex++
L.SetGlobal("s"+tempName, lua.LString(capture.Value))
val, err := strconv.ParseFloat(capture.Value, 64)
if err == nil {
L.SetGlobal("v"+tempName, lua.LNumber(val))
}
} else {
val, err := strconv.ParseFloat(capture.Value, 64)
if err == nil {
L.SetGlobal(capture.Name, lua.LNumber(val))
} else {
L.SetGlobal(capture.Name, lua.LString(capture.Value))
}
}
}
return nil
}
// FromLua implements the Processor interface for RegexProcessor
func fromLua(L *lua.LState, captureGroups []*CaptureGroup) ([]*CaptureGroup, error) {
captureIndex := 0
for _, capture := range captureGroups {
if capture.Name == "" {
capture.Name = fmt.Sprintf("%d", captureIndex+1)
vVarName := fmt.Sprintf("v%s", capture.Name)
sVarName := fmt.Sprintf("s%s", capture.Name)
captureIndex++
vLuaVal := L.GetGlobal(vVarName)
sLuaVal := L.GetGlobal(sVarName)
if sLuaVal.Type() == lua.LTString {
capture.Updated = sLuaVal.String()
}
// Numbers have priority
if vLuaVal.Type() == lua.LTNumber {
capture.Updated = vLuaVal.String()
}
} else {
// Easy shit
capture.Updated = L.GetGlobal(capture.Name).String()
}
}
return captureGroups, nil
}