{"record":{"id":"32eb9d9e7bddfe90","repo":"SonarSource/sonarqube","slug":"cannot-write-elasticsearch-jvm-options-file","errorCode":null,"errorMessage":"Cannot write Elasticsearch jvm options file","messagePattern":"Cannot write Elasticsearch jvm options file","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"server/sonar-main/src/main/java/org/sonar/application/command/EsJvmOptions.java","lineNumber":134,"sourceCode":"    // log4j 2\n    res.put(\"-Dlog4j.shutdownHookEnabled=\", \"false\");\n    res.put(\"-Dlog4j2.disable.jmx=\", \"true\");\n    res.put(\"-Dlog4j2.formatMsgNoLookups=\", \"true\");\n    /*\n     * Due to internationalization enhancements in JDK 9 org.sonarqube.ws.tester.Elasticsearch need to set the provider to COMPAT otherwise\n     * time/date\n     * parsing will break in an incompatible way for some date patterns and locales.\n     */\n    res.put(\"-Djava.locale.providers=\", \"COMPAT\");\n  }\n\n  public void writeToJvmOptionFile(File file) {\n    String jvmOptions = getAll().stream().collect(Collectors.joining(\"\\n\"));\n    String jvmOptionsContent = ELASTICSEARCH_JVM_OPTIONS_HEADER + jvmOptions;\n    try {\n      Files.write(file.toPath(), jvmOptionsContent.getBytes(StandardCharsets.UTF_8));\n    } catch (IOException e) {\n      throw new IllegalStateException(\"Cannot write Elasticsearch jvm options file\", e);\n    }\n  }\n}\n","sourceCodeStart":116,"sourceCodeEnd":138,"githubUrl":"https://github.com/SonarSource/sonarqube/blob/184c821202192afc1c599fc912d0889b69fffa53/server/sonar-main/src/main/java/org/sonar/application/command/EsJvmOptions.java#L116-L138","documentation":"EsJvmOptions.writeToJvmOptionFile renders all Elasticsearch JVM options plus a warning header and writes them to the target file with Files.write in UTF-8. Any IOException is wrapped in an IllegalStateException because the generated jvm.options file is required for the Elasticsearch child process to start.","triggerScenarios":"Calling writeToJvmOptionFile when the destination directory does not exist, the path is not writable by the process user, or the disk is full while writing the Elasticsearch jvm.options file.","commonSituations":"Elasticsearch data/temp directories on read-only mounts, permission-restricted install directories after package upgrades, exhausted disk space on the ES node, or the target file locked by another process on Windows.","solutions":["Ensure the target directory for the jvm.options file exists and is writable by the SonarQube process user","Free disk space on the partition holding the Elasticsearch files","Fix filesystem permissions/ownership of the sonarqube install and temp directories (chown to the service user)","Check the wrapped IOException cause in the stack trace to identify the exact filesystem problem"],"exampleFix":"// before\n$SONAR_HOME/elasticsearch owned by root, service runs as sonarqube\n// after\nchown -R sonarqube:sonarqube $SONAR_HOME/elasticsearch\nchmod -R u+w $SONAR_HOME/elasticsearch","handlingStrategy":"try-catch","validationCode":"File dir = file.getParentFile();\nif (!dir.isDirectory() || !dir.canWrite() || dir.getUsableSpace() < 5 * 1024 * 1024) {\n  throw new IllegalStateException(\"ES jvm.options target dir not writable/full: \" + dir);\n}","typeGuard":"boolean canWriteFile(File f) {\n  File p = f.getParentFile();\n  return f.canWrite() || (!f.exists() && p != null && p.isDirectory() && p.canWrite());\n}","tryCatchPattern":"try {\n  esJvmOptions.writeToJvmOptionFile(file);\n} catch (IllegalStateException e) {\n  if (e.getMessage().equals(\"Cannot write Elasticsearch jvm options file\")) {\n    log.error(\"Check ES dir permissions and disk space\", e.getCause());\n  }\n  throw e;\n}","preventionTips":["Ensure the service user owns $SONAR_HOME/elasticsearch","Monitor disk usage on the sonarqube host","Re-check permissions after package upgrades or reinstalls"],"tags":["java","filesystem","elasticsearch"],"backgroundTag":"file-write-failed","analyzedSha":"184c821202192afc1c599fc912d0889b69fffa53","analyzedAt":"2026-09-09T12:23:51.573Z","contentChangedAt":"2026-09-09T12:23:51.573Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}