apache/kafka · error · IllegalArgumentException

Cannot specify a negative version level.

Error message

Cannot specify a negative version level.

What it means

Thrown by the FeatureUpdate constructor when maxVersionLevel is a negative short. Kafka finalized feature version levels are non-negative; a negative value is either a parsing bug or an underflow and is rejected immediately on the client.

Solutions

  1. Pass a non-negative maxVersionLevel (0 for delete, >= 1 for a real level).
  2. Validate the parsed value with a range check (>= 0) before constructing the FeatureUpdate.
  3. Treat -1/'unset' from your own config layer as 'do not send a FeatureUpdate' rather than forwarding it.

Example fix

// before
short level = Short.parseShort userInput; // -1 possible
new FeatureUpdate(level, upgradeType);

// after
if (level < 0) throw new IllegalArgumentException("level must be >= 0: " + level);
new FeatureUpdate(level, upgradeType);
Defensive patterns

Strategy: validation

Validate before calling

if (level < 0) {
    throw new IllegalArgumentException("level must be >= 0: " + level);
}
new FeatureUpdate(level, upgradeType);

Type guard

static boolean isNonNegativeLevel(short level) {
    return level >= 0;
}

Try / catch

try {
    new FeatureUpdate(level, upgradeType);
} catch (IllegalArgumentException e) {
    if (e.getMessage().contains("negative")) {
        // reject input upstream
    }
}

Prevention

When it happens

Trigger: Calling new FeatureUpdate with a negative short, e.g. new FeatureUpdate((short) -1, ...). Building a FeatureUpdate from untrusted/external input that was parsed as a signed value without bounds checking. Arithmetic that wraps a short below zero.

Common situations: Tooling that lets a user type a version level of -1 to mean 'unset'; parsing a protobuf/JSON number into a short without validation; porting code where -1 was previously a sentinel.

Related errors


AI-assisted analysis of apache/kafka@996fb4585a (2026-08-11). Data as JSON: /api/errors/c12e77d178f21f5c. Report an issue: GitHub.

Appendix: source

Thrown at clients/src/main/java/org/apache/kafka/clients/admin/FeatureUpdate.java:78

    /**
     * @param maxVersionLevel   The new maximum version level for the finalized feature.
     *                          a value of zero is special and indicates that the update is intended to
     *                          delete the finalized feature, and should be accompanied by setting
     *                          the upgradeType to safe or unsafe.
     * @param upgradeType     Indicate what kind of upgrade should be performed in this operation.
     *                          - UPGRADE: upgrading the feature level
     *                          - SAFE_DOWNGRADE: only downgrades which do not result in metadata loss are permitted
     *                          - UNSAFE_DOWNGRADE: any downgrade, including those which may result in metadata loss, are permitted
     */
    public FeatureUpdate(final short maxVersionLevel, final UpgradeType upgradeType) {
        if (maxVersionLevel == 0 && upgradeType.equals(UpgradeType.UPGRADE)) {
            throw new IllegalArgumentException(String.format(
                    "The upgradeType flag should be set to SAFE_DOWNGRADE or UNSAFE_DOWNGRADE when the provided maxVersionLevel:%d is < 1.",
                    maxVersionLevel));
        }
        if (maxVersionLevel < 0) {
            throw new IllegalArgumentException("Cannot specify a negative version level.");
        }
        this.maxVersionLevel = maxVersionLevel;
        this.upgradeType = upgradeType;
    }

    public short maxVersionLevel() {
        return maxVersionLevel;
    }

    public UpgradeType upgradeType() {
        return upgradeType;
    }

    @Override
    public boolean equals(Object other) {
        if (this == other) {
            return true;
        }

View on GitHub (pinned to 996fb4585a)