apache/skywalking · error · UnexpectedException

Some configuration files of enabled rules are not found, ena

Error message

Some configuration files of enabled rules are not found, enabled rules: {}

What it means

UnexpectedException thrown by the Rules loader when one or more rule names listed in the 'forceEnabledRules'/'enabledRules' configuration have no corresponding file on disk (their entry in formedEnabledRules stayed false after the directory walk). The OAP refuses to start with a partially loaded ruleset and reports exactly which enabled rules are missing.

Source

Thrown at oap-server/analyzer/meter-analyzer/src/main/java/org/apache/skywalking/oap/meter/analyzer/v2/prometheus/rule/Rules.java:134

            }).forEach(p -> {
                final String rel = root.relativize(p).toString();
                final String ruleName = rel.substring(0, rel.lastIndexOf('.'));
                // Keep the actual extension: both .yaml and .yml load, and synthesising .yaml for
                // a .yml rule points the provenance at a file that does not exist.
                diskPaths.put(ruleName, rel);
                try {
                    diskBytes.put(ruleName, Files.readAllBytes(p));
                } catch (IOException e) {
                    throw new UnexpectedException("Load rule file " + p.getFileName() + " failed", e);
                }
            });
        }

        if (formedEnabledRules.containsValue(false)) {
            List<String> rulesNotFound = formedEnabledRules.keySet().stream()
                    .filter(rule -> !formedEnabledRules.get(rule))
                    .collect(Collectors.toList());
            throw new UnexpectedException("Some configuration files of enabled rules are not found, enabled rules: " + rulesNotFound);
        }

        // Merge with classpath-discovered resolvers (runtime-rule DB, plus any future
        // priority-ranked source). ACTIVE substitutes existing disk entries; INACTIVE
        // drops them. Resolver-only rules (no disk twin) are NOT merged here — they're
        // applied by RuleSync.runOnce post-seal via the dynamic layer channel.
        final Map<String, byte[]> merged = useInstalledManager
            ? RuleSetMerger.merge(path, diskBytes)
            : RuleSetMerger.merge(path, diskBytes, manager);

        return merged.entrySet().stream()
            .map(e -> parseRule(path, e.getKey(), diskPaths.get(e.getKey()), e.getValue()))
            .filter(Objects::nonNull)
            .collect(Collectors.toList());
    }

    private static Rule parseRule(final String rulesetDir, final String ruleName,
                                  final String relPath, final byte[] bytes) {

View on GitHub (pinned to 102af09b4a)

Solutions

  1. Check the exception message — it lists the exact missing rule names; verify each has a matching .yaml/.yml in the rules directory
  2. Fix typos/casing in the enabled-rules entries in application.yml (rule name = file name without extension)
  3. If the rule was removed in the newer OAP version, delete the stale entry from enabledRules or migrate to the replacement rule
  4. Verify the meter-analyzer rulesPath setting resolves to the directory that actually contains the rule files (in the running container, not just in the repo)

Example fix

# before (application.yml)
mal-rule:
  enabledRules:
    - spring-serv
# after
mal-rule:
  enabledRules:
    - spring-service
Defensive patterns

Strategy: validation

Validate before calling

// Before start: every enabled rule must have a file
Set<String> onDisk = Files.list(rulesPath).map(p -> p.getFileName().toString().replaceAll("\\.(ya?ml)$", "")).collect(Collectors.toSet());
for (String r : configuredEnabledRules) {
    if (!onDisk.contains(r)) throw new IllegalStateException("Missing rule file for: " + r);
}

Prevention

When it happens

Trigger: Config lists a rule name (e.g. 'vm' or 'k8s-cp') in enabledRules/forceEnabledRules but no <rule>.yaml/.yml exists in the resolved rules directory; also when the file name casing or extension doesn't match, or the rulesPath points at the wrong directory.

Common situations: Upgrading OAP where a rule was renamed or removed but application.yml still enables it; typos in rule names in application.yml; wrong meter-analyzer rulesPath (empty default path vs custom path); running a stripped-down distribution that ships fewer built-in rule files.

Related errors


AI-assisted analysis of apache/skywalking@102af09b4a (2026-08-14). Data as JSON: /api/errors/fa60161fde376652. Report an issue: GitHub.