430 lines
11 KiB
Go
430 lines
11 KiB
Go
package rules
|
|
|
|
import (
|
|
"testing"
|
|
)
|
|
|
|
// Test Rule creation and basic functionality
|
|
func TestRule(t *testing.T) {
|
|
// Test NewRule with default values
|
|
rule := NewRule()
|
|
if rule == nil {
|
|
t.Fatal("NewRule() returned nil")
|
|
}
|
|
|
|
if rule.GetCategory() != 0 {
|
|
t.Errorf("Expected category 0, got %d", rule.GetCategory())
|
|
}
|
|
|
|
if rule.GetType() != 0 {
|
|
t.Errorf("Expected type 0, got %d", rule.GetType())
|
|
}
|
|
|
|
if rule.GetValue() != "" {
|
|
t.Errorf("Expected empty value, got %s", rule.GetValue())
|
|
}
|
|
|
|
if rule.GetCombined() != "NONE" {
|
|
t.Errorf("Expected combined 'NONE', got %s", rule.GetCombined())
|
|
}
|
|
|
|
// Test NewRuleWithValues
|
|
rule2 := NewRuleWithValues(CategoryPlayer, PlayerMaxLevel, "50", "Player:MaxLevel")
|
|
if rule2 == nil {
|
|
t.Fatal("NewRuleWithValues() returned nil")
|
|
}
|
|
|
|
if rule2.GetCategory() != CategoryPlayer {
|
|
t.Errorf("Expected category %d, got %d", CategoryPlayer, rule2.GetCategory())
|
|
}
|
|
|
|
if rule2.GetType() != PlayerMaxLevel {
|
|
t.Errorf("Expected type %d, got %d", PlayerMaxLevel, rule2.GetType())
|
|
}
|
|
|
|
if rule2.GetValue() != "50" {
|
|
t.Errorf("Expected value '50', got %s", rule2.GetValue())
|
|
}
|
|
|
|
if rule2.GetCombined() != "Player:MaxLevel" {
|
|
t.Errorf("Expected combined 'Player:MaxLevel', got %s", rule2.GetCombined())
|
|
}
|
|
|
|
// Test type conversion methods
|
|
if rule2.GetInt32() != 50 {
|
|
t.Errorf("Expected int32 50, got %d", rule2.GetInt32())
|
|
}
|
|
|
|
if rule2.GetBool() != true {
|
|
t.Errorf("Expected bool true, got %t", rule2.GetBool())
|
|
}
|
|
|
|
// Test SetValue
|
|
rule2.SetValue("100")
|
|
if rule2.GetValue() != "100" {
|
|
t.Errorf("Expected value '100' after SetValue, got %s", rule2.GetValue())
|
|
}
|
|
|
|
if rule2.GetInt32() != 100 {
|
|
t.Errorf("Expected int32 100 after SetValue, got %d", rule2.GetInt32())
|
|
}
|
|
}
|
|
|
|
// Test Rule copy constructor
|
|
func TestRuleCopy(t *testing.T) {
|
|
original := NewRuleWithValues(CategoryCombat, CombatMaxRange, "4.0", "Combat:MaxCombatRange")
|
|
copy := NewRuleFromRule(original)
|
|
|
|
if copy == nil {
|
|
t.Fatal("NewRuleFromRule() returned nil")
|
|
}
|
|
|
|
if copy.GetCategory() != original.GetCategory() {
|
|
t.Errorf("Copy category mismatch: expected %d, got %d", original.GetCategory(), copy.GetCategory())
|
|
}
|
|
|
|
if copy.GetType() != original.GetType() {
|
|
t.Errorf("Copy type mismatch: expected %d, got %d", original.GetType(), copy.GetType())
|
|
}
|
|
|
|
if copy.GetValue() != original.GetValue() {
|
|
t.Errorf("Copy value mismatch: expected %s, got %s", original.GetValue(), copy.GetValue())
|
|
}
|
|
|
|
if copy.GetCombined() != original.GetCombined() {
|
|
t.Errorf("Copy combined mismatch: expected %s, got %s", original.GetCombined(), copy.GetCombined())
|
|
}
|
|
|
|
// Test that they are independent copies
|
|
copy.SetValue("8.0")
|
|
if original.GetValue() == copy.GetValue() {
|
|
t.Error("Original and copy are not independent after modification")
|
|
}
|
|
}
|
|
|
|
// Test RuleSet creation and basic operations
|
|
func TestRuleSet(t *testing.T) {
|
|
ruleSet := NewRuleSet()
|
|
if ruleSet == nil {
|
|
t.Fatal("NewRuleSet() returned nil")
|
|
}
|
|
|
|
if ruleSet.GetID() != 0 {
|
|
t.Errorf("Expected ID 0, got %d", ruleSet.GetID())
|
|
}
|
|
|
|
if ruleSet.GetName() != "" {
|
|
t.Errorf("Expected empty name, got %s", ruleSet.GetName())
|
|
}
|
|
|
|
// Test SetID and SetName
|
|
ruleSet.SetID(1)
|
|
ruleSet.SetName("Test Rule Set")
|
|
|
|
if ruleSet.GetID() != 1 {
|
|
t.Errorf("Expected ID 1, got %d", ruleSet.GetID())
|
|
}
|
|
|
|
if ruleSet.GetName() != "Test Rule Set" {
|
|
t.Errorf("Expected name 'Test Rule Set', got %s", ruleSet.GetName())
|
|
}
|
|
|
|
// Test adding rules
|
|
rule1 := NewRuleWithValues(CategoryPlayer, PlayerMaxLevel, "50", "Player:MaxLevel")
|
|
rule2 := NewRuleWithValues(CategoryCombat, CombatMaxRange, "4.0", "Combat:MaxCombatRange")
|
|
|
|
ruleSet.AddRule(rule1)
|
|
ruleSet.AddRule(rule2)
|
|
|
|
// Test rule retrieval
|
|
retrievedRule1 := ruleSet.GetRule(CategoryPlayer, PlayerMaxLevel)
|
|
if retrievedRule1 == nil {
|
|
t.Fatal("GetRule() returned nil for added rule")
|
|
}
|
|
|
|
if retrievedRule1.GetValue() != "50" {
|
|
t.Errorf("Retrieved rule value mismatch: expected '50', got %s", retrievedRule1.GetValue())
|
|
}
|
|
|
|
// Test rule retrieval by name
|
|
retrievedRule2 := ruleSet.GetRuleByName("Combat", "MaxCombatRange")
|
|
if retrievedRule2 == nil {
|
|
t.Fatal("GetRuleByName() returned nil for added rule")
|
|
}
|
|
|
|
if retrievedRule2.GetValue() != "4.0" {
|
|
t.Errorf("Retrieved rule value mismatch: expected '4.0', got %s", retrievedRule2.GetValue())
|
|
}
|
|
|
|
// Test Size
|
|
if ruleSet.Size() != 2 {
|
|
t.Errorf("Expected size 2, got %d", ruleSet.Size())
|
|
}
|
|
|
|
// Test HasRule
|
|
if !ruleSet.HasRule(CategoryPlayer, PlayerMaxLevel) {
|
|
t.Error("HasRule() returned false for existing rule")
|
|
}
|
|
|
|
if ruleSet.HasRule(CategorySpawn, SpawnSpeedMultiplier) {
|
|
t.Error("HasRule() returned true for non-existing rule")
|
|
}
|
|
}
|
|
|
|
// Test RuleSet copy functionality
|
|
func TestRuleSetCopy(t *testing.T) {
|
|
original := NewRuleSet()
|
|
original.SetID(1)
|
|
original.SetName("Original")
|
|
|
|
rule1 := NewRuleWithValues(CategoryPlayer, PlayerMaxLevel, "50", "Player:MaxLevel")
|
|
rule2 := NewRuleWithValues(CategoryCombat, CombatMaxRange, "4.0", "Combat:MaxCombatRange")
|
|
original.AddRule(rule1)
|
|
original.AddRule(rule2)
|
|
|
|
// Test copy constructor
|
|
copy := NewRuleSetFromRuleSet(original)
|
|
if copy == nil {
|
|
t.Fatal("NewRuleSetFromRuleSet() returned nil")
|
|
}
|
|
|
|
if copy.GetID() != original.GetID() {
|
|
t.Errorf("Copy ID mismatch: expected %d, got %d", original.GetID(), copy.GetID())
|
|
}
|
|
|
|
if copy.GetName() != original.GetName() {
|
|
t.Errorf("Copy name mismatch: expected %s, got %s", original.GetName(), copy.GetName())
|
|
}
|
|
|
|
if copy.Size() != original.Size() {
|
|
t.Errorf("Copy size mismatch: expected %d, got %d", original.Size(), copy.Size())
|
|
}
|
|
|
|
// Test that rules were copied correctly
|
|
copyRule := copy.GetRule(CategoryPlayer, PlayerMaxLevel)
|
|
if copyRule == nil {
|
|
t.Fatal("Copied rule set is missing expected rule")
|
|
}
|
|
|
|
if copyRule.GetValue() != "50" {
|
|
t.Errorf("Copied rule value mismatch: expected '50', got %s", copyRule.GetValue())
|
|
}
|
|
}
|
|
|
|
// Test RuleManager initialization
|
|
func TestRuleManager(t *testing.T) {
|
|
ruleManager := NewRuleManager()
|
|
if ruleManager == nil {
|
|
t.Fatal("NewRuleManager() returned nil")
|
|
}
|
|
|
|
if !ruleManager.IsInitialized() {
|
|
t.Error("RuleManager should be initialized after creation")
|
|
}
|
|
|
|
// Test getting a default rule
|
|
rule := ruleManager.GetGlobalRule(CategoryPlayer, PlayerMaxLevel)
|
|
if rule == nil {
|
|
t.Fatal("GetGlobalRule() returned nil for default rule")
|
|
}
|
|
|
|
// Should return the default value from Init()
|
|
if rule.GetValue() != "50" {
|
|
t.Errorf("Expected default value '50', got %s", rule.GetValue())
|
|
}
|
|
|
|
// Test getting rule by name
|
|
rule2 := ruleManager.GetGlobalRuleByName("Player", "MaxLevel")
|
|
if rule2 == nil {
|
|
t.Fatal("GetGlobalRuleByName() returned nil for default rule")
|
|
}
|
|
|
|
if rule2.GetValue() != "50" {
|
|
t.Errorf("Expected default value '50', got %s", rule2.GetValue())
|
|
}
|
|
|
|
// Test blank rule for non-existent rule
|
|
blankRule := ruleManager.GetGlobalRule(9999, 9999)
|
|
if blankRule == nil {
|
|
t.Fatal("GetGlobalRule() should return blank rule for non-existent rule")
|
|
}
|
|
|
|
if blankRule.IsValid() {
|
|
t.Error("Blank rule should not be valid")
|
|
}
|
|
}
|
|
|
|
// Test RuleManager rule set operations
|
|
func TestRuleManagerRuleSets(t *testing.T) {
|
|
ruleManager := NewRuleManager()
|
|
|
|
// Create a test rule set
|
|
ruleSet := NewRuleSet()
|
|
ruleSet.SetID(1)
|
|
ruleSet.SetName("Test Set")
|
|
|
|
// Add some rules to it
|
|
rule1 := NewRuleWithValues(CategoryPlayer, PlayerMaxLevel, "60", "Player:MaxLevel")
|
|
ruleSet.AddRule(rule1)
|
|
|
|
// Add the rule set to the manager
|
|
if !ruleManager.AddRuleSet(ruleSet) {
|
|
t.Fatal("AddRuleSet() returned false")
|
|
}
|
|
|
|
// Test getting the rule set
|
|
retrievedRuleSet := ruleManager.GetRuleSet(1)
|
|
if retrievedRuleSet == nil {
|
|
t.Fatal("GetRuleSet() returned nil")
|
|
}
|
|
|
|
if retrievedRuleSet.GetName() != "Test Set" {
|
|
t.Errorf("Retrieved rule set name mismatch: expected 'Test Set', got %s", retrievedRuleSet.GetName())
|
|
}
|
|
|
|
// Test duplicate rule set
|
|
duplicateRuleSet := NewRuleSet()
|
|
duplicateRuleSet.SetID(1)
|
|
duplicateRuleSet.SetName("Duplicate")
|
|
|
|
if ruleManager.AddRuleSet(duplicateRuleSet) {
|
|
t.Error("AddRuleSet() should return false for duplicate ID")
|
|
}
|
|
|
|
// Test GetNumRuleSets
|
|
if ruleManager.GetNumRuleSets() != 1 {
|
|
t.Errorf("Expected 1 rule set, got %d", ruleManager.GetNumRuleSets())
|
|
}
|
|
|
|
// Test setting global rule set
|
|
if !ruleManager.SetGlobalRuleSet(1) {
|
|
t.Fatal("SetGlobalRuleSet() returned false")
|
|
}
|
|
|
|
// Test that global rule now returns the overridden value
|
|
globalRule := ruleManager.GetGlobalRule(CategoryPlayer, PlayerMaxLevel)
|
|
if globalRule == nil {
|
|
t.Fatal("GetGlobalRule() returned nil after setting global rule set")
|
|
}
|
|
|
|
if globalRule.GetValue() != "60" {
|
|
t.Errorf("Expected overridden value '60', got %s", globalRule.GetValue())
|
|
}
|
|
}
|
|
|
|
// Test category and type name functions
|
|
func TestCategoryNames(t *testing.T) {
|
|
// Test GetCategoryName
|
|
name := GetCategoryName(CategoryPlayer)
|
|
if name != "Player" {
|
|
t.Errorf("Expected category name 'Player', got %s", name)
|
|
}
|
|
|
|
// Test unknown category
|
|
unknownName := GetCategoryName(9999)
|
|
if unknownName != "Unknown" {
|
|
t.Errorf("Expected 'Unknown' for invalid category, got %s", unknownName)
|
|
}
|
|
|
|
// Test GetCategoryByName
|
|
category, exists := GetCategoryByName("Player")
|
|
if !exists {
|
|
t.Error("GetCategoryByName() should find 'Player' category")
|
|
}
|
|
|
|
if category != CategoryPlayer {
|
|
t.Errorf("Expected category %d, got %d", CategoryPlayer, category)
|
|
}
|
|
|
|
// Test unknown category name
|
|
_, exists = GetCategoryByName("NonExistent")
|
|
if exists {
|
|
t.Error("GetCategoryByName() should not find non-existent category")
|
|
}
|
|
}
|
|
|
|
// Test rule validation
|
|
func TestRuleValidation(t *testing.T) {
|
|
ruleManager := NewRuleManager()
|
|
|
|
// Test valid rule
|
|
err := ruleManager.ValidateRule(CategoryPlayer, PlayerMaxLevel, "50")
|
|
if err != nil {
|
|
t.Errorf("ValidateRule() returned error for valid rule: %v", err)
|
|
}
|
|
|
|
// Test rule value too long
|
|
longValue := make([]byte, MaxRuleValueLength+1)
|
|
for i := range longValue {
|
|
longValue[i] = 'a'
|
|
}
|
|
|
|
err = ruleManager.ValidateRule(CategoryPlayer, PlayerMaxLevel, string(longValue))
|
|
if err != ErrRuleValueTooLong {
|
|
t.Errorf("ValidateRule() should return ErrRuleValueTooLong for long value")
|
|
}
|
|
}
|
|
|
|
// Test RuleManagerAdapter
|
|
func TestRuleManagerAdapter(t *testing.T) {
|
|
ruleManager := NewRuleManager()
|
|
adapter := NewRuleManagerAdapter(ruleManager, 0)
|
|
|
|
if adapter == nil {
|
|
t.Fatal("NewRuleManagerAdapter() returned nil")
|
|
}
|
|
|
|
// Test basic rule access
|
|
rule := adapter.GetRule(CategoryPlayer, PlayerMaxLevel)
|
|
if rule == nil {
|
|
t.Fatal("Adapter GetRule() returned nil")
|
|
}
|
|
|
|
if rule.GetValue() != "50" {
|
|
t.Errorf("Expected value '50', got %s", rule.GetValue())
|
|
}
|
|
|
|
// Test convenience methods
|
|
intValue := adapter.GetInt32(CategoryPlayer, PlayerMaxLevel)
|
|
if intValue != 50 {
|
|
t.Errorf("Expected int32 50, got %d", intValue)
|
|
}
|
|
|
|
boolValue := adapter.GetBool(CategoryPlayer, PlayerMaxLevel)
|
|
if !boolValue {
|
|
t.Error("Expected bool true for value '50'")
|
|
}
|
|
|
|
stringValue := adapter.GetString(CategoryPlayer, PlayerMaxLevel)
|
|
if stringValue != "50" {
|
|
t.Errorf("Expected string '50', got %s", stringValue)
|
|
}
|
|
|
|
// Test zone ID
|
|
if adapter.GetZoneID() != 0 {
|
|
t.Errorf("Expected zone ID 0, got %d", adapter.GetZoneID())
|
|
}
|
|
|
|
adapter.SetZoneID(100)
|
|
if adapter.GetZoneID() != 100 {
|
|
t.Errorf("Expected zone ID 100 after SetZoneID, got %d", adapter.GetZoneID())
|
|
}
|
|
}
|
|
|
|
// Benchmark rule access performance
|
|
func BenchmarkRuleAccess(b *testing.B) {
|
|
ruleManager := NewRuleManager()
|
|
|
|
b.ResetTimer()
|
|
for i := 0; i < b.N; i++ {
|
|
_ = ruleManager.GetGlobalRule(CategoryPlayer, PlayerMaxLevel)
|
|
}
|
|
}
|
|
|
|
// Benchmark rule manager creation
|
|
func BenchmarkRuleManagerCreation(b *testing.B) {
|
|
b.ResetTimer()
|
|
for i := 0; i < b.N; i++ {
|
|
_ = NewRuleManager()
|
|
}
|
|
} |