{"record":{"id":"b751e2cbc8de19cb","repo":"prestodb/presto","slug":"unable-to-load-redisproviderplugin","errorCode":null,"errorMessage":"Unable to Load RedisProviderPlugin","messagePattern":"Unable to Load RedisProviderPlugin","errorType":"exception","errorClass":"RedisProviderInitializationException","httpStatus":null,"severity":"critical","filePath":"redis-hbo-provider/src/main/java/com/facebook/presto/statistic/PropertiesUtil.java","lineNumber":37,"sourceCode":"import java.nio.file.Files;\nimport java.util.HashMap;\nimport java.util.Map;\nimport java.util.Properties;\n\nimport static com.google.common.collect.Maps.fromProperties;\n\npublic final class PropertiesUtil\n{\n    private PropertiesUtil() {}\n\n    public static Map<String, String> loadProperties(File file)\n    {\n        Properties properties = new Properties();\n        try (InputStream in = Files.newInputStream(file.toPath())) {\n            properties.load(in);\n        }\n        catch (IOException e) {\n            throw new RedisProviderInitializationException(\"Unable to Load RedisProviderPlugin\", e);\n        }\n        return fromProperties(properties);\n    }\n\n    public static Map<String, String> initializeConfigs(String path)\n    {\n        Map<String, String> properties = new HashMap<>(loadProperties(new File(path)));\n        // load secrets\n        if (properties.containsKey(RedisProviderConfig.REDIS_CREDENTIALS_PATH)) {\n            File credentialFile = new File(properties.get(RedisProviderConfig.REDIS_CREDENTIALS_PATH));\n            properties.putAll(loadProperties(credentialFile));\n        }\n        return properties;\n    }\n}\n","sourceCodeStart":19,"sourceCodeEnd":53,"githubUrl":"https://github.com/prestodb/presto/blob/55bb57d202de3b926896fa966c2c4a44c779634e/redis-hbo-provider/src/main/java/com/facebook/presto/statistic/PropertiesUtil.java#L19-L53","documentation":"PropertiesUtil.loadProperties reads a properties file from disk and wraps any IOException thrown while opening or reading it into a RedisProviderInitializationException with this message. It indicates the Redis provider plugin could not load its configuration file, so plugin initialization aborts. The misleading wording comes from the generic message; the actual problem is file I/O on the properties file (or the credentials file referenced by initializeConfigs).","triggerScenarios":"Calling PropertiesUtil.loadProperties(File) or initializeConfigs(path) when the properties file path does not exist, the path is a directory, the process lacks read permissions, a symlink is broken, or the credentials file configured via redis.credentials-path (REDIS_CREDENTIALS_PATH) is unreadable. Also thrown on malformed properties input that triggers an IOException during load.","commonSituations":"Typo or wrong absolute path in redis.properties.file / etc/presto config; the plugin launched under a service user without read access to the config; container image missing the mounted properties file; credentials file deleted or moved after being referenced; relative path resolved against an unexpected working directory.","solutions":["Verify the file path passed to loadProperties/initializeConfigs exists and is a regular readable file (ls -l / Files.exists / file.canRead()).","Fix the permissions so the Presto process user can read the properties file (chmod/chown) and confirm correct ownership in containers.","Check that any credentials file referenced by the redis.credentials-path property exists and is readable, since initializeConfigs loads it through the same code path.","Use an absolute path (or correct relative path for the coordinator/worker working directory) in the plugin configuration.","Read the wrapped IOException cause for the exact reason (NoSuchFileException, AccessDeniedException, etc.) and address it specifically."],"exampleFix":"// before\nMap<String, String> properties = PropertiesUtil.initializeConfigs(\"redis-provider.properties\");\n// after\nFile configFile = new File(\"/etc/presto/redis-provider.properties\");\nif (!configFile.isFile() || !configFile.canRead()) {\n    throw new IllegalStateException(\"Redis provider config missing or unreadable: \" + configFile.getAbsolutePath());\n}\nMap<String, String> properties = PropertiesUtil.initializeConfigs(configFile.getAbsolutePath());","handlingStrategy":"validation","validationCode":"File file = new File(path);\nif (!file.exists()) {\n    throw new IllegalStateException(\"Properties file does not exist: \" + file.getAbsolutePath());\n}\nif (!file.isFile()) {\n    throw new IllegalStateException(\"Path is not a regular file: \" + file.getAbsolutePath());\n}\nif (!file.canRead()) {\n    throw new IllegalStateException(\"No read permission for: \" + file.getAbsolutePath());\n}\n// also verify credentials file referenced by config\nMap<String, String> props = PropertiesUtil.initializeConfigs(file.getAbsolutePath());","typeGuard":"private static boolean isReadableFile(File file)\n{\n    return file != null && file.isFile() && file.canRead();\n}","tryCatchPattern":"try {\n    Map<String, String> configs = PropertiesUtil.loadProperties(configFile);\n}\ncatch (RedisProviderInitializationException e) {\n    Throwable cause = e.getCause(); // IOException: NoSuchFileException, AccessDeniedException, etc.\n    throw new IllegalStateException(\"Cannot load Redis provider config \" + configFile + \": \" + cause, e);\n}","preventionTips":["Use absolute paths for plugin configuration files and verify them at startup","Ensure the Presto service user has read permissions on config and credentials files (check after image/mount changes)","If using redis.credentials-path, assert that file exists before plugin initialization","Mount config files read-only into containers and validate mounts in entrypoint scripts","Fail fast with a clear pre-check (isReadableFile) instead of relying on the generic wrapped message"],"tags":["io","configuration","file-not-found","redis","plugin-initialization"],"backgroundTag":"properties-file-unreadable","analyzedSha":"55bb57d202de3b926896fa966c2c4a44c779634e","analyzedAt":"2026-09-04T12:50:26.162Z","contentChangedAt":"2026-09-04T12:50:26.162Z","schemaVersion":2},"datasetVersion":"2026-09-11T21:17:09.523Z"}