511 lines
17 KiB
Go
511 lines
17 KiB
Go
package main
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"testing"
|
|
|
|
"cook/utils"
|
|
|
|
"github.com/stretchr/testify/assert"
|
|
)
|
|
|
|
func TestTOMLLoadBasic(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-basic-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Create a simple TOML test file
|
|
tomlContent := `[[commands]]
|
|
name = "SimpleTest"
|
|
regex = "test = !num"
|
|
lua = "v1 * 2"
|
|
files = ["test.txt"]
|
|
|
|
[[commands]]
|
|
name = "AnotherTest"
|
|
regex = "value = (!num)"
|
|
lua = "v1 + 10"
|
|
files = ["*.txt"]
|
|
`
|
|
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
err = os.WriteFile(tomlFile, []byte(tomlContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write TOML test file: %v", err)
|
|
}
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test loading TOML commands
|
|
commands, err := utils.LoadCommandsFromTomlFiles("test.toml")
|
|
assert.NoError(t, err, "Should load TOML commands without error")
|
|
assert.Len(t, commands, 2, "Should load 2 commands from TOML")
|
|
|
|
// Verify first command
|
|
assert.Equal(t, "SimpleTest", commands[0].Name, "First command name should match")
|
|
assert.Equal(t, "test = !num", commands[0].Regex, "First command regex should match")
|
|
assert.Equal(t, "v1 * 2", commands[0].Lua, "First command Lua should match")
|
|
assert.Equal(t, []string{"test.txt"}, commands[0].Files, "First command files should match")
|
|
|
|
// Verify second command
|
|
assert.Equal(t, "AnotherTest", commands[1].Name, "Second command name should match")
|
|
assert.Equal(t, "value = (!num)", commands[1].Regex, "Second command regex should match")
|
|
assert.Equal(t, "v1 + 10", commands[1].Lua, "Second command Lua should match")
|
|
assert.Equal(t, []string{"*.txt"}, commands[1].Files, "Second command files should match")
|
|
}
|
|
|
|
func TestTOMLGlobalModifiers(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-global-modifiers-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Create TOML content with global modifiers
|
|
tomlContent := `[[commands]]
|
|
modifiers = { multiplier = 3, prefix = "TEST_", enabled = true }
|
|
|
|
[[commands]]
|
|
name = "UseGlobalModifiers"
|
|
regex = "value = !num"
|
|
lua = "v1 * multiplier; s1 = prefix .. s1"
|
|
files = ["test.txt"]
|
|
`
|
|
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
err = os.WriteFile(tomlFile, []byte(tomlContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write TOML test file: %v", err)
|
|
}
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test loading TOML commands
|
|
commands, err := utils.LoadCommandsFromTomlFiles("test.toml")
|
|
assert.NoError(t, err, "Should load TOML commands without error")
|
|
assert.Len(t, commands, 2, "Should load 2 commands from TOML")
|
|
|
|
// Verify global modifiers command (first command should have only modifiers)
|
|
assert.Empty(t, commands[0].Name, "Global modifiers command should have no name")
|
|
assert.Empty(t, commands[0].Regex, "Global modifiers command should have no regex")
|
|
assert.Empty(t, commands[0].Lua, "Global modifiers command should have no lua")
|
|
assert.Empty(t, commands[0].Files, "Global modifiers command should have no files")
|
|
assert.Len(t, commands[0].Modifiers, 3, "Global modifiers command should have 3 modifiers")
|
|
assert.Equal(t, int64(3), commands[0].Modifiers["multiplier"], "Multiplier should be 3")
|
|
assert.Equal(t, "TEST_", commands[0].Modifiers["prefix"], "Prefix should be TEST_")
|
|
assert.Equal(t, true, commands[0].Modifiers["enabled"], "Enabled should be true")
|
|
|
|
// Verify regular command
|
|
assert.Equal(t, "UseGlobalModifiers", commands[1].Name, "Regular command name should match")
|
|
assert.Equal(t, "value = !num", commands[1].Regex, "Regular command regex should match")
|
|
}
|
|
|
|
func TestTOMLMultilineRegex(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-multiline-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Create TOML content with multiline regex using literal strings
|
|
tomlContent := `[[commands]]
|
|
modifiers = { factor = 2.5 }
|
|
|
|
[[commands]]
|
|
name = "MultilineTest"
|
|
regex = '''
|
|
\[config\.settings\]
|
|
|
|
depth = !num
|
|
|
|
width = !num
|
|
|
|
height = !num'''
|
|
lua = "v1 * factor"
|
|
files = ["test.conf"]
|
|
isolate = true
|
|
`
|
|
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
err = os.WriteFile(tomlFile, []byte(tomlContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write TOML test file: %v", err)
|
|
}
|
|
|
|
// Create test file that matches the multiline pattern
|
|
testContent := `[config.settings]
|
|
|
|
depth = 10
|
|
|
|
width = 20
|
|
|
|
height = 30
|
|
`
|
|
|
|
testFile := filepath.Join(tmpDir, "test.conf")
|
|
err = os.WriteFile(testFile, []byte(testContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write test file: %v", err)
|
|
}
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test loading TOML commands
|
|
commands, err := utils.LoadCommandsFromTomlFiles("test.toml")
|
|
assert.NoError(t, err, "Should load TOML commands without error")
|
|
assert.Len(t, commands, 2, "Should load 2 commands from TOML")
|
|
|
|
// Verify the multiline regex command
|
|
multilineCmd := commands[1]
|
|
assert.Equal(t, "MultilineTest", multilineCmd.Name, "Command name should match")
|
|
assert.Contains(t, multilineCmd.Regex, "\\[config\\.settings\\]", "Regex should contain escaped brackets")
|
|
assert.Contains(t, multilineCmd.Regex, "depth = !num", "Regex should contain depth pattern")
|
|
assert.Contains(t, multilineCmd.Regex, "width = !num", "Regex should contain width pattern")
|
|
assert.Contains(t, multilineCmd.Regex, "height = !num", "Regex should contain height pattern")
|
|
assert.Contains(t, multilineCmd.Regex, "\n", "Regex should contain newlines")
|
|
assert.True(t, multilineCmd.Isolate, "Isolate should be true")
|
|
|
|
// Verify the regex preserves proper structure
|
|
expectedLines := []string{
|
|
"\\[config\\.settings\\]",
|
|
"depth = !num",
|
|
"width = !num",
|
|
"height = !num",
|
|
}
|
|
|
|
for _, line := range expectedLines {
|
|
assert.Contains(t, multilineCmd.Regex, line, "Regex should contain: "+line)
|
|
}
|
|
}
|
|
|
|
func TestTOMLComplexRegexPatterns(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-complex-regex-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Create TOML content with complex regex patterns
|
|
tomlContent := `[[commands]]
|
|
name = "ComplexPatterns"
|
|
regexes = [
|
|
"\\[section\\.([^\\]]+)\\]",
|
|
"(?P<key>\\w+)\\s*=\\s*(?P<value>\\d+\\.\\d+)",
|
|
"network\\.(\\w+)\\.(enable|disable)"
|
|
]
|
|
lua = "if is_number(value) then value = num(value) * 1.1 end; return true"
|
|
files = ["*.conf", "*.ini"]
|
|
`
|
|
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
err = os.WriteFile(tomlFile, []byte(tomlContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write TOML test file: %v", err)
|
|
}
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test loading TOML commands
|
|
commands, err := utils.LoadCommandsFromTomlFiles("test.toml")
|
|
assert.NoError(t, err, "Should load TOML commands without error")
|
|
assert.Len(t, commands, 1, "Should load 1 command from TOML")
|
|
|
|
// Verify the complex regex command
|
|
cmd := commands[0]
|
|
assert.Equal(t, "ComplexPatterns", cmd.Name, "Command name should match")
|
|
assert.Len(t, cmd.Regexes, 3, "Should have 3 regex patterns")
|
|
|
|
// Verify each regex pattern
|
|
assert.Equal(t, `\[section\.([^\]]+)\]`, cmd.Regexes[0], "First regex should match section pattern")
|
|
assert.Equal(t, `(?P<key>\w+)\s*=\s*(?P<value>\d+\.\d+)`, cmd.Regexes[1], "Second regex should match key-value pattern")
|
|
assert.Equal(t, `network\.(\w+)\.(enable|disable)`, cmd.Regexes[2], "Third regex should match network pattern")
|
|
|
|
assert.Equal(t, []string{"*.conf", "*.ini"}, cmd.Files, "Files should match")
|
|
}
|
|
|
|
func TestTOMLJSONMode(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-json-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Create TOML content with JSON mode commands
|
|
tomlContent := `[[commands]]
|
|
name = "JSONMultiply"
|
|
json = true
|
|
lua = "for i, item in ipairs(data.items) do data.items[i].value = item.value * 2 end; return true"
|
|
files = ["data.json"]
|
|
|
|
[[commands]]
|
|
name = "JSONObjectUpdate"
|
|
json = true
|
|
lua = "data.version = '2.0.0'; data.enabled = true; return true"
|
|
files = ["config.json"]
|
|
`
|
|
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
err = os.WriteFile(tomlFile, []byte(tomlContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write TOML test file: %v", err)
|
|
}
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test loading TOML commands
|
|
commands, err := utils.LoadCommandsFromTomlFiles("test.toml")
|
|
assert.NoError(t, err, "Should load TOML commands without error")
|
|
assert.Len(t, commands, 2, "Should load 2 commands from TOML")
|
|
|
|
// Verify first JSON command
|
|
cmd1 := commands[0]
|
|
assert.Equal(t, "JSONMultiply", cmd1.Name, "First command name should match")
|
|
assert.True(t, cmd1.JSON, "First command should have JSON mode enabled")
|
|
assert.Equal(t, "for i, item in ipairs(data.items) do data.items[i].value = item.value * 2 end; return true", cmd1.Lua, "First command Lua should match")
|
|
assert.Equal(t, []string{"data.json"}, cmd1.Files, "First command files should match")
|
|
|
|
// Verify second JSON command
|
|
cmd2 := commands[1]
|
|
assert.Equal(t, "JSONObjectUpdate", cmd2.Name, "Second command name should match")
|
|
assert.True(t, cmd2.JSON, "Second command should have JSON mode enabled")
|
|
assert.Equal(t, "data.version = '2.0.0'; data.enabled = true; return true", cmd2.Lua, "Second command Lua should match")
|
|
assert.Equal(t, []string{"config.json"}, cmd2.Files, "Second command files should match")
|
|
}
|
|
|
|
func TestTOMLEndToEndIntegration(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-integration-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Create comprehensive TOML content
|
|
tomlContent := `[[commands]]
|
|
modifiers = { multiplier = 4, base_value = 100 }
|
|
|
|
[[commands]]
|
|
name = "IntegrationTest"
|
|
regex = '''
|
|
\[kinetics\.stressValues\.v2\.capacity\]
|
|
|
|
steam_engine = !num
|
|
|
|
water_wheel = !num
|
|
|
|
copper_valve_handle = !num'''
|
|
lua = "v1 * multiplier"
|
|
files = ["test.txt"]
|
|
isolate = true
|
|
|
|
[[commands]]
|
|
name = "SimplePattern"
|
|
regex = "enabled = (true|false)"
|
|
lua = "= false"
|
|
files = ["test.txt"]
|
|
`
|
|
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
err = os.WriteFile(tomlFile, []byte(tomlContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write TOML test file: %v", err)
|
|
}
|
|
|
|
// Create test file that matches the patterns
|
|
testContent := `[kinetics.stressValues.v2.capacity]
|
|
|
|
steam_engine = 256
|
|
|
|
water_wheel = 64
|
|
|
|
copper_valve_handle = 16
|
|
|
|
some_other_setting = enabled = true
|
|
`
|
|
|
|
testFile := filepath.Join(tmpDir, "test.txt")
|
|
err = os.WriteFile(testFile, []byte(testContent), 0644)
|
|
if err != nil {
|
|
t.Fatalf("Failed to write test file: %v", err)
|
|
}
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test the complete workflow using the main function
|
|
commands, err := utils.LoadCommands([]string{"test.toml"})
|
|
assert.NoError(t, err, "Should load TOML commands without error")
|
|
assert.Len(t, commands, 3, "Should load 3 commands total (including global modifiers)")
|
|
|
|
// Associate files with commands
|
|
files := []string{"test.txt"}
|
|
associations, err := utils.AssociateFilesWithCommands(files, commands)
|
|
assert.NoError(t, err, "Should associate files with commands")
|
|
|
|
// Verify associations
|
|
association := associations["test.txt"]
|
|
assert.Len(t, association.IsolateCommands, 1, "Should have 1 isolate command")
|
|
assert.Len(t, association.Commands, 1, "Should have 1 regular command")
|
|
assert.Equal(t, "IntegrationTest", association.IsolateCommands[0].Name, "Isolate command should match")
|
|
assert.Equal(t, "SimplePattern", association.Commands[0].Name, "Regular command should match")
|
|
|
|
t.Logf("TOML integration test completed successfully")
|
|
t.Logf("Loaded %d commands from TOML", len(commands))
|
|
t.Logf("Associated commands: %d isolate, %d regular",
|
|
len(association.IsolateCommands), len(association.Commands))
|
|
}
|
|
|
|
func TestTOMLErrorHandling(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "toml-error-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Test 1: Invalid TOML syntax
|
|
invalidTOML := `[[commands]]
|
|
name = "Invalid"
|
|
regex = "test = !num"
|
|
lua = "v1 * 2"
|
|
files = ["test.txt"
|
|
# Missing closing bracket
|
|
`
|
|
|
|
invalidFile := filepath.Join(tmpDir, "invalid.toml")
|
|
err = os.WriteFile(invalidFile, []byte(invalidTOML), 0644)
|
|
|
|
commands, err := utils.LoadCommandsFromTomlFiles("invalid.toml")
|
|
assert.Error(t, err, "Should return error for invalid TOML syntax")
|
|
assert.Nil(t, commands, "Should return nil commands for invalid TOML")
|
|
assert.Contains(t, err.Error(), "failed to unmarshal TOML file", "Error should mention TOML unmarshaling")
|
|
|
|
// Test 2: Non-existent file
|
|
commands, err = utils.LoadCommandsFromTomlFiles("nonexistent.toml")
|
|
assert.NoError(t, err, "Should handle non-existent file without error")
|
|
assert.Empty(t, commands, "Should return empty commands for non-existent file")
|
|
|
|
// Test 3: Empty TOML file creates an error (this is expected behavior)
|
|
emptyFile := filepath.Join(tmpDir, "empty.toml")
|
|
err = os.WriteFile(emptyFile, []byte(""), 0644)
|
|
|
|
commands, err = utils.LoadCommandsFromTomlFiles("empty.toml")
|
|
assert.Error(t, err, "Should return error for empty TOML file")
|
|
assert.Nil(t, commands, "Should return nil commands for empty TOML")
|
|
}
|
|
|
|
func TestYAMLToTOMLConversion(t *testing.T) {
|
|
// Create a temporary directory for testing
|
|
tmpDir, err := os.MkdirTemp("", "yaml-to-toml-conversion-test")
|
|
if err != nil {
|
|
t.Fatalf("Failed to create temp dir: %v", err)
|
|
}
|
|
defer os.RemoveAll(tmpDir)
|
|
|
|
// Change to temp directory
|
|
origDir, _ := os.Getwd()
|
|
defer os.Chdir(origDir)
|
|
os.Chdir(tmpDir)
|
|
|
|
// Create a test YAML file
|
|
yamlContent := `- name: "ConversionTest"
|
|
regex: "value = !num"
|
|
lua: "v1 * 3"
|
|
files: ["test.txt"]
|
|
loglevel: DEBUG
|
|
|
|
- name: "AnotherTest"
|
|
regex: "enabled = (true|false)"
|
|
lua: "= false"
|
|
files: ["*.conf"]
|
|
|
|
- name: "GlobalModifiers"
|
|
modifiers:
|
|
multiplier: 2.5
|
|
prefix: "CONV_"
|
|
`
|
|
|
|
yamlFile := filepath.Join(tmpDir, "test.yml")
|
|
err = os.WriteFile(yamlFile, []byte(yamlContent), 0644)
|
|
assert.NoError(t, err, "Should write YAML test file")
|
|
|
|
// Test conversion
|
|
err = utils.ConvertYAMLToTOML("test.yml")
|
|
assert.NoError(t, err, "Should convert YAML to TOML without error")
|
|
|
|
// Check that TOML file was created
|
|
tomlFile := filepath.Join(tmpDir, "test.toml")
|
|
_, err = os.Stat(tomlFile)
|
|
assert.NoError(t, err, "TOML file should exist after conversion")
|
|
|
|
// Read and verify TOML content
|
|
tomlData, err := os.ReadFile(tomlFile)
|
|
assert.NoError(t, err, "Should read TOML file")
|
|
|
|
tomlContent := string(tomlData)
|
|
assert.Contains(t, tomlContent, `name = "ConversionTest"`, "TOML should contain first command name")
|
|
assert.Contains(t, tomlContent, `name = "AnotherTest"`, "TOML should contain second command name")
|
|
assert.Contains(t, tomlContent, `name = "GlobalModifiers"`, "TOML should contain global modifiers command")
|
|
assert.Contains(t, tomlContent, `multiplier = 2.5`, "TOML should contain multiplier")
|
|
assert.Contains(t, tomlContent, `prefix = "CONV_"`, "TOML should contain prefix")
|
|
|
|
// Test that converted TOML loads correctly
|
|
commands, err := utils.LoadCommandsFromTomlFiles("test.toml")
|
|
assert.NoError(t, err, "Should load converted TOML without error")
|
|
assert.Len(t, commands, 3, "Should load 3 commands from converted TOML")
|
|
|
|
// Find global modifiers command (it might not be first)
|
|
var globalCmd utils.ModifyCommand
|
|
foundGlobal := false
|
|
for _, cmd := range commands {
|
|
if cmd.Name == "GlobalModifiers" {
|
|
globalCmd = cmd
|
|
foundGlobal = true
|
|
break
|
|
}
|
|
}
|
|
assert.True(t, foundGlobal, "Should find global modifiers command")
|
|
assert.Equal(t, 2.5, globalCmd.Modifiers["multiplier"], "Should preserve multiplier value")
|
|
assert.Equal(t, "CONV_", globalCmd.Modifiers["prefix"], "Should preserve prefix value")
|
|
|
|
// Test skip functionality - run conversion again
|
|
err = utils.ConvertYAMLToTOML("test.yml")
|
|
assert.NoError(t, err, "Should handle existing TOML file without error")
|
|
|
|
// Verify original TOML file wasn't modified
|
|
originalTomlData, err := os.ReadFile(tomlFile)
|
|
assert.NoError(t, err, "Should read TOML file again")
|
|
assert.Equal(t, tomlData, originalTomlData, "TOML file content should be unchanged")
|
|
|
|
t.Logf("YAML to TOML conversion test completed successfully")
|
|
} |