Null Used With Optional

ID

java.null_optional

Severity

high

Remediation Complexity

trivial

Remediation Risk

low

Remediation Effort

low

Resource

Reliability

Language

Java

Tags

null-safety, reliability

Description

Reports four shapes where null is used together with Optional, reintroducing the NullPointerException that Optional exists to remove: a local variable or field declared Optional initialised to null; a ==/!= null comparison against a name declared Optional; a return null; inside a method declared to return Optional; and a @Nullable annotation on a field, parameter or method whose declared type is Optional.

Rationale

Optional is a container that models the presence or absence of a value without resorting to null. Mixing the two defeats that purpose in two directions:

// Bug: an Optional variable can now be null OR empty -- two ways to mean "absent"
Optional<Config> config = null;
if (config != null) {           // Bug: bypasses Optional's own emptiness check
    apply(config);
}

// Bug: callers that trust the signature and skip a null-check get an NPE anyway
Optional<Config> loadConfig() {
    if (!configFile.exists()) {
        return null;             // should be Optional.empty()
    }
    return Optional.of(read(configFile));
}

// Bug: an Optional return value should never itself be null
@Nullable
Optional<Config> findConfig() {
    return configFile.exists() ? Optional.of(read(configFile)) : Optional.empty();
}

Once any of these shapes ships, every caller must null-check and empty-check the same value, which is exactly the boilerplate Optional was introduced to remove.

Remediation

Use Optional.empty() wherever an absent value would otherwise be null, and call isPresent()/ifPresent() instead of comparing against null:

Optional<Config> config = Optional.empty();
config.ifPresent(NullOptionalExample::apply);

Optional<Config> loadConfig() {
    if (!configFile.exists()) {
        return Optional.empty();
    }
    return Optional.of(read(configFile));
}

© 2026 Xygeni. All rights reserved