You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
java/non-final-call-in-constructor: a call made inside a lambda in the constructor is not reported #22970
The query reports toString() in the constructor of CtorSeed.Senior: Junior overrides it, the override reads name, and name is only assigned after super() returns, so new Junior() throws. Move the call into a lambda that the constructor runs right away (CtorVariant) and nothing is reported, though the call still happens during construction with the same effect.
Probably unqualifiedCallToNonAbstractMethod, which requires the call's enclosing callable to be the constructor (result.getEnclosingCallable() = c). Inside the lambda the enclosing callable is the lambda's own method.
publicclassCtorSeed {
publicstaticclassSenior {
publicSenior() {
toString(); // overridden in Junior, reads a field not yet set
}
publicStringtoString() {
return"Senior";
}
}
publicstaticclassJuniorextendsSenior {
privateStringname;
publicJunior() {
super();
name = "Junior";
}
publicStringtoString() {
returnname.toUpperCase(); // NullPointerException when called from Senior()
}
}
}
variant/CtorVariant.java:
publicclassCtorVariant {
publicstaticclassSenior {
publicSenior() {
Runnabler = () -> {
toString(); // the same call, inside a lambda run at once; not reported
};
r.run();
}
publicStringtoString() {
return"Senior";
}
}
publicstaticclassJuniorextendsSenior {
privateStringname;
publicJunior() {
super();
name = "Junior";
}
publicStringtoString() {
returnname.toUpperCase();
}
}
}
How to reproduce
codeql database create db --language=java --build-mode=none \
--source-root=<one directory> --overwrite
codeql database analyze db \
codeql/java-queries:codeql-suites/java-security-and-quality.qls \
--format=csv --output=out.csv
# one database per directory
Expected result
"Non-final method invocation in constructor" on the toString() call inside the lambda in CtorVariant.java (line 6), as on CtorSeed.java (line 5).
Output of the commands above:
### CodeQL 2.27.2 query: java/non-final-call-in-constructor
### suite: java-security-and-quality.qls, --build-mode=none, per-file isolated databases
### extraction JDK: openjdk version "21.0.11" 2026-04-21 LTS
--- SEED -- expected: query fires (seed/)
"Non-final method invocation in constructor","If a constructor calls a method that is overridden in a subclass
--- VARIANT -- expected: query fires, actual: not reported (the bug) (variant/)
(query reported nothing)
The java/non-final-call-in-constructor query is a syntactic check for direct calls made inside the constructor body itself, rather than tracking whether lambdas or callbacks created in a constructor are invoked synchronously before construction finishes (since callbacks defined in a constructor are typically invoked later, after initialization).
Activity
sam-robson commentedon Nov 3, 2026
Hi @MarkLee131, thanks for the detailed report. We'll take a look into this and follow up.
sam-robson commentedon Nov 4, 2026
The
java/non-final-call-in-constructorquery is a syntactic check for direct calls made inside the constructor body itself, rather than tracking whether lambdas or callbacks created in a constructor are invoked synchronously before construction finishes (since callbacks defined in a constructor are typically invoked later, after initialization).