Problem
Every call to engine.evaluate() calls loadExpressionsWithFilters(key), which:
- Iterates through
key.allNames (a rule key can have multiple alias names)
- For each name, calls
configReader.getAll(k)
- Then calls
configReader.foreach({ cfgKey -> cfgKey.startsWith(indexedKeyPrefix) }, ...) which scans ALL config entries to find indexed rules
This is O(n) per rule evaluation where n = total config entries. For the built-in config, there are ~50+ rules. With user configs, this can be 100+.
The same key (e.g., api.name) is looked up repeatedly for different elements but the expression list is identical β the result never changes between config reloads.
Impact
With 2,500+ rule evaluations per scan, this means 2,500+ full config scans.
Estimated speedup: 2-3x for large configs
Fix
Cache the result of loadExpressionsWithFilters(key) with invalidation on config reload:
private val expressionCache = ConcurrentHashMap<String, List<Pair<String, String?>>>()
private fun loadExpressionsWithFilters(key: RuleKey<*>): List<Pair<String, String?>> {
return expressionCache.getOrPut(key.name) {
val result = ArrayList<Pair<String, String?>>()
for (k in key.allNames) {
val rules = configReader.getAll(k)
rules.forEach { exp -> result.add(exp to null) }
val indexedKeyPrefix = "$k["
configReader.foreach(
{ cfgKey -> cfgKey.startsWith(indexedKeyPrefix) },
{ indexedKey, value ->
val filterExp = indexedKey.removePrefix(k).removeSurrounding("[", "]")
result.add(value to filterExp)
}
)
}
result
}
}
Invalidate on config reload (e.g., via a listener or by checking a config version).
Location
src/main/kotlin/com/itangcent/easyapi/rule/engine/RuleEngine.kt:237-252
Problem
Every call to
engine.evaluate()callsloadExpressionsWithFilters(key), which:key.allNames(a rule key can have multiple alias names)configReader.getAll(k)configReader.foreach({ cfgKey -> cfgKey.startsWith(indexedKeyPrefix) }, ...)which scans ALL config entries to find indexed rulesThis is O(n) per rule evaluation where n = total config entries. For the built-in config, there are ~50+ rules. With user configs, this can be 100+.
The same key (e.g.,
api.name) is looked up repeatedly for different elements but the expression list is identical β the result never changes between config reloads.Impact
With 2,500+ rule evaluations per scan, this means 2,500+ full config scans.
Estimated speedup: 2-3x for large configs
Fix
Cache the result of
loadExpressionsWithFilters(key)with invalidation on config reload:Invalidate on config reload (e.g., via a listener or by checking a config version).
Location
src/main/kotlin/com/itangcent/easyapi/rule/engine/RuleEngine.kt:237-252