SonarSource/sonarqube · error · MessageException

Property [%s] cannot be changed on restart: [%s] => [%s]

Error message

Property [%s] cannot be changed on restart: [%s] => [%s]

What it means

On reload/restart, AppReloaderImpl.ensureUnchangedConfiguration compares old vs newly loaded props for keys that must not change (process/ports/paths). verifyUnchanged throws this MessageException naming the property and its old => new values whenever any such key differs, aborting the restart so the operator restarts the JVM fully instead.

Source

Thrown at server/sonar-main/src/main/java/org/sonar/application/AppReloaderImpl.java:77

    fileSystem.reset();
    logging.configure();
    appState.reset();
  }

  private static void ensureUnchangedConfiguration(Props oldProps, Props newProps) {
    verifyUnchanged(oldProps, newProps, PATH_DATA.getKey());
    verifyUnchanged(oldProps, newProps, PATH_WEB.getKey());
    verifyUnchanged(oldProps, newProps, PATH_LOGS.getKey());
    verifyUnchanged(oldProps, newProps, PATH_TEMP.getKey());
    verifyUnchanged(oldProps, newProps, CLUSTER_ENABLED.getKey());
  }

  private static void verifyUnchanged(Props initialProps, Props newProps, String propKey) {
    String initialValue = initialProps.nonNullValue(propKey);
    String newValue = newProps.nonNullValue(propKey);
    if (!Objects.equals(initialValue, newValue)) {
      throw new MessageException(format("Property [%s] cannot be changed on restart: [%s] => [%s]", propKey, initialValue, newValue));
    }
  }

}

View on GitHub (pinned to 184c821202)

Solutions

  1. Perform a full process restart (systemctl restart sonarqube / restart the JVM) so the new value takes effect.
  2. Revert the protected property to its original value if an in-place restart is required.
  3. Only change unprotected settings if you intend to use the in-app restart.
  4. Coordinate config-management runs with full restarts rather than in-app restarts.

Example fix

// before
$ edit sonar.properties (sonar.web.port=9001)
$ curl -X POST .../api/system/restart  // MessageException
// after
$ sudo systemctl restart sonarqube  // full restart applies the change
Defensive patterns

Strategy: validation

Validate before calling

Set<String> locked = Set.of("sonar.web.port", "sonar.ce.port", "sonar.search.port", "sonar.path.data", "sonar.path.temp");
Props fresh = settingsLoader.load().getProps();
for (String key : locked) {
    if (!Objects.equals(initialProps.nonNullValue(key), fresh.nonNullValue(key))) {
        throw new IllegalStateException(key + " changed; full restart required");
    }
}

Try / catch

try { reloader.reload(settings); } catch (MessageException e) { log.warning(e.getMessage() + " -> perform a full process restart"); }

Prevention

When it happens

Trigger: Editing conf/sonar.properties (or env vars feeding it) to change a protected key — e.g. sonar.web.port, sonar.ce.port, sonar.search.port, sonar.path.* — and then triggering an in-place restart (api/system/restart).

Common situations: Admins changing port or path settings and expecting the in-app Restart button to apply them; configuration management tools rewriting sonar.properties between server start and restart request.

Related errors


AI-assisted analysis of SonarSource/sonarqube@184c821202 (2026-09-09). Data as JSON: /api/errors/7c97972d1ca4d31d. Report an issue: GitHub.