SonarSource/sonarqube · warning

Unable to parse version numbers for major/minor comparison…

Error message

Unable to parse version numbers for major/minor comparison: old='{}', new='{}'

What it means

The helper isMajorOrMinorVersionChange extracts major/minor components of two versions to decide if a flag reset is needed. If accessing version components fails unexpectedly, it logs this warning with both versions and conservatively returns false (no reset), so a version change would be missed this run.

Solutions

  1. Check both logged version strings; correct the stored SONARQUBE_CURRENT_VERSION property to a valid x.y.z version if it is malformed.
  2. If a reset was expected but skipped, manually set the stored version to a matching major/minor and restart so the comparison succeeds.
  3. Restart after fixing to let the task re-evaluate the version change.
  4. Report as a bug if versions are clearly valid yet parsing still fails.

Example fix

-- before: malformed stored version prevents comparison
internal_properties: SONARQUBE_CURRENT_VERSION = 'abc'
-- after: valid version string
internal_properties: SONARQUBE_CURRENT_VERSION = '10.4.0'
Defensive patterns

Strategy: fallback

Validate before calling

function majorMinor(v) {
  const m = /^(\d+)\.(\d+)/.exec(String(v));
  return m ? { major: +m[1], minor: +m[2] } : null;
}

Type guard

function hasMajorMinor(v) {
  return v != null && Number.isInteger(v.major) && Number.isInteger(v.minor);
}

Try / catch

try {
  return compareMajorMinor(oldV, newV);
} catch (e) {
  logger.warn('Unable to parse version numbers for comparison', e);
  return false; // conservative: skip reset
}

Prevention

When it happens

Trigger: isMajorOrMinorVersionChange (invoked from start) throwing while reading major()/minor() of old/new Version objects — defensive catch for any parsing/extraction failure in the comparison path.

Common situations: Malformed stored version strings slipping past earlier parsing; unusual version formats from snapshots or dev builds; corrupted internal property values.

Understand the failure class

Background: "Invalid ... format", "must be in format X", "does not look like a ..." — invalid argument format errors across CLI tools and libraries — this error's family across 17 libraries.

Related errors


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

Appendix: source

Thrown at server/sonar-webserver-core/src/main/java/org/sonar/server/startup/IssueFlagResetSetupTask.java:102

        resetFromSonarQubeUpdateFlag();
      }
    } catch (Exception e) {
      LOGGER.warn("Unable to parse stored version '{}', updating to current version '{}'", 
        currentVersion.get(), runtimeVersionString, e);
      updateCurrentVersion(runtimeVersionString);
    }
  }

  private static boolean isMajorOrMinorVersionChange(Version newVersion, Version oldVersion) {
    try {
      int newMajor = newVersion.major();
      int newMinor = newVersion.minor();
      int oldMajor = oldVersion.major();
      int oldMinor = oldVersion.minor();
      
      return newMajor != oldMajor || newMinor != oldMinor;
    } catch (Exception e) {
      LOGGER.warn("Unable to parse version numbers for major/minor comparison: old='{}', new='{}'", oldVersion, newVersion, e);
      return false;
    }
  }

  private void updateCurrentVersion(String currentVersion) {
    internalProperties.write(SONARQUBE_CURRENT_VERSION, currentVersion);
  }

  private void resetFromSonarQubeUpdateFlag() {
    try (DbSession dbSession = dbClient.openSession(false)) {
      int updatedRows = dbClient.issueDao().resetFlagFromSonarQubeUpdate(dbSession);
      dbSession.commit();
      LOGGER.info("Reset FROM_SONARQUBE_UPDATE flag to false for {} issues", updatedRows);
    }
  }


  @Override

View on GitHub (pinned to 184c821202)