S1128 incorrectly reports unused static imports for same-class constants

Product: SonarQube Community 26.4.0.121862
sonar-java version: sonar-java 8.28.0.43176
sonar-java SE version: sonar-java-symbolic-execution 8.16.3.1589
Java source level: 21 (javac 21, source/target 17)

Rule

java:S1128 — Unnecessary imports should be removed

Description

S1128 incorrectly reports static imports of constants declared in the same class as unused.

Although the constants are referenced in the code, the analyzer attributes their usage to the class members instead of the static imports, leading to a false positive.

Reproducer

// AFTER — three S1128 findings reported on the static imports below
package demo.after;

import java.util.ArrayList;
import java.util.List;
import static demo.after.FileFormatType.DOCX; // reported unused
import static demo.after.FileFormatType.PDF;  // reported unused
import static demo.after.FileFormatType.TXT;  // reported unused

public class FileFormatType {

    public static final String DOCX = "docx";
    public static final String PDF  = "pdf";
    public static final String TXT  = "txt";

    private final String extension;
    private final String description;

    public FileFormatType(String extension, String description) {
        this.extension = extension;
        this.description = description;
    }

    public static List<FileFormatType> defaultFormats() {
        List<FileFormatType> formats = new ArrayList<>();
        formats.add(new FileFormatType(DOCX, "Word Document")); // unqualified use
        formats.add(new FileFormatType(PDF,  "PDF Document"));
        formats.add(new FileFormatType(TXT,  "Plain Text"));
        return formats;
    }

    public boolean isSupported(String ext) {
        return DOCX.equalsIgnoreCase(ext)
            || PDF.equalsIgnoreCase(ext)
            || TXT.equalsIgnoreCase(ext);
    }
}

Hello @Emilyaxe,

Thank you for the detailed report on this rule.

The behaviour you describe is expected and considered to be a true positive: because the constants are declared in the file where they are used, the static imports are unnecessary.
I agree however that the issue’s message could be improved to reflect that they aren’t “unused” but rather “redundant”. We have already opened a ticket to address this.

Best regards,
Aurélien