VNX-1107: Insufficient Isolation of Symbolic Constant Definitions
The same symbolic constant, with the same name and the same literal value, is defined separately in two or more Java source files (static final fields, or interface fields) instead of once in a shared constants class that the others reference. Each copy is changed on its own, so a timeout, retry limit, URL or key length that is meant to be one value drifts between classes. Reported: every duplicate definition, on the line that names the constant. Not reported: constants defined once and imported elsewhere, same names with different values (TAG, per-class limits), loggers and other non-literal initialisers, serialVersionUID, trivial values (true/false, 0, 1, -1, empty string, null), definitions repeated inside one file, generated sources (Android BuildConfig, protoc output and other files with a generator header before the first type declaration, or @Generated; an IDE's 'Auto-generated method stub' comment does not count), and test files. Only literal values are compared; constants computed from expressions are not.
| Field | Value |
|---|---|
| Rule ID | VNX-1107 |
| Severity | Low |
| SARIF level | note |
| Kind | sast |
| Languages | Java |
| CWE | CWE-1107 |
| CAPEC | CAPEC-66 |
| ATT&CK | T1190 |
| CWSS vector | CWSS:1.0/TI:L/AP:RU/AL:S/IC:N/FC:LT/RP:RU/RL:S/AV:L/AS:N/IN:A/SC:A/BI:L/DI:H/EX:L/EC:N/P:L |
| Tags | maintainability constants java cwe-1107 |
| Source | internal/sast/rules/vnx-1107.rego |
Overview
VNX-1107 maps to CWE-1107: Insufficient Isolation of Symbolic Constant Definitions. The same symbolic constant, with the same name and the same literal value, is defined separately in two or more Java source files (static final fields, or interface fields) instead of once in a shared constants class that the others reference. Each copy is changed on its own, so a timeout, retry limit, URL or key length that is meant to be one value drifts between classes. Reported: every duplicate definition, on the line that names the constant. Not reported: constants defined once and imported elsewhere, same names with different values (TAG, per-class limits), loggers and other non-literal initialisers, serialVersionUID, trivial values (true/false, 0, 1, -1, empty string, null), definitions repeated inside one file, generated sources (Android BuildConfig, protoc output and other files with a generator header before the first type declaration, or @Generated; an IDE’s ‘Auto-generated method stub’ comment does not count), and test files. Only literal values are compared; constants computed from expressions are not.
Why This Matters
Two classes that each declare MAX_RETRIES = 5 hold two constants that only happen to agree today. A change to one leaves the other behind, and the code that was meant to share one value no longer does.
What Gets Flagged
// OrderService.java
private static final int MAX_RETRIES = 5; // FLAGGED
// InvoiceService.java
static final int MAX_RETRIES = 5; // FLAGGED
Not flagged: a constant defined once in a shared class and imported, the same name with different values (TAG = "OrderService"), loggers, serialVersionUID, trivial values (0, 1, "", false) and test files.
Remediation
Move the constant to one shared constants class (or configuration) and reference it from every class that needs it.
References
Suppressing this rule
Put a nosec comment on the line, or on line 1 to cover the whole file. Use the comment marker of the file’s language (#, //, -- or ;):
# nosec vnx-1107
// nosec vnx-1107
Or record an ignore rule: vulnetix ignore add --rule vnx-1107 --reason "...". See Suppressing findings.