elastic/elasticsearch · error · PolicyValidationException
files entitlement must contain 'mode' for every listed file
Error message
files entitlement must contain 'mode' for every listed file
What it means
Thrown when a files-entitlement entry has no `mode` field. Mode is mandatory on every listed file because the parser cannot infer whether read-write access is intended, and defaulting to read could silently break plugins that need to write.
Source
Thrown at libs/entitlement/src/main/java/org/elasticsearch/entitlement/runtime/policy/entitlements/FilesEntitlement.java:259
String pathSetting = checkString.apply(file, "path_setting");
String settingBaseDirAsString = checkString.apply(file, "basedir_if_relative");
String modeAsString = checkString.apply(file, "mode");
String platformAsString = checkString.apply(file, "platform");
Boolean exclusiveBoolean = checkBoolean.apply(file, "exclusive");
boolean exclusive = exclusiveBoolean != null && exclusiveBoolean;
if (file.isEmpty() == false) {
throw new PolicyValidationException("unknown key(s) [" + file + "] in a listed file for files entitlement");
}
int foundKeys = (pathAsString != null ? 1 : 0) + (relativePathAsString != null ? 1 : 0) + (pathSetting != null ? 1 : 0);
if (foundKeys != 1) {
throw new PolicyValidationException(
"a files entitlement entry must contain one of " + "[path, relative_path, path_setting]"
);
}
if (modeAsString == null) {
throw new PolicyValidationException("files entitlement must contain 'mode' for every listed file");
}
Mode mode = parseMode(modeAsString);
Platform platform = null;
if (platformAsString != null) {
platform = parsePlatform(platformAsString);
}
if (relativeTo != null && relativePathAsString == null) {
throw new PolicyValidationException("'relative_to' may only be used with 'relative_path'");
}
if (settingBaseDirAsString != null && pathSetting == null) {
throw new PolicyValidationException("'basedir_if_relative' may only be used with 'path_setting'");
}
final FileData fileData;
if (relativePathAsString != null) {
if (relativeTo == null) {View on GitHub (pinned to db6a809a66)
Solutions
- Add `"mode": "read"` or `"mode": "read_write"` to every entry in the `paths` array.
- Audit all entries, since the check fires per-entry — fixing one will simply surface the next.
Example fix
// before
{ "path": "/var/log/es" }
// after
{ "path": "/var/log/es", "mode": "read_write" } Defensive patterns
Strategy: validation
Validate before calling
public static void validateModePresent(Map<String,Object> entry) {
if (!entry.containsKey("mode")) {
throw new IllegalArgumentException("files entry is missing required 'mode'");
}
} Type guard
public static boolean hasMode(Map<String,Object> entry) {
return entry.containsKey("mode");
} Prevention
- Add `required: ["mode"]` to your policy JSON Schema.
- Never assume a default mode — set it explicitly on every entry.
- When iterating entries in code, fail the whole policy on the first missing mode.
When it happens
Trigger: A files-entitlement entry omits the `mode` key, e.g. `{ "path": "/var/log/es" }` with no mode specified.
Common situations: Author assumes read is the default; entry was created by copying a template that left mode out; partial edit removed the mode line; YAML merge that dropped the key.
Related errors
- invalid mode: {}, valid values: [read, read_write]
- invalid platform: {}, valid values: [linux, macos, windows]
- invalid relative directory: {}, valid values: [config, data,
- must specify at least one path
- expected [{}] to be type [String] but found type [{}]
AI-assisted analysis of elastic/elasticsearch@db6a809a66 (2026-08-12).
Data as JSON: /api/errors/99f5c1f47c3dbc8b.
Report an issue: GitHub.