Skip to content

Commit

Permalink
SONARJAVA-4546 Support @org.jspecify.annotations.NullMarked in existi…
Browse files Browse the repository at this point in the history
…ng nullability checks up to Package Level (#4896)
  • Loading branch information
pauloreilly-sonarsource authored Oct 7, 2024
1 parent 09ec082 commit 6ec169b
Show file tree
Hide file tree
Showing 39 changed files with 1,473 additions and 34 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -218,7 +218,7 @@
{
"ruleKey": "S1128",
"hasTruePositives": true,
"falseNegatives": 32,
"falseNegatives": 34,
"falsePositives": 0
},
{
Expand Down Expand Up @@ -320,7 +320,7 @@
{
"ruleKey": "S1168",
"hasTruePositives": true,
"falseNegatives": 6,
"falseNegatives": 24,
"falsePositives": 0
},
{
Expand All @@ -338,7 +338,7 @@
{
"ruleKey": "S1172",
"hasTruePositives": true,
"falseNegatives": 13,
"falseNegatives": 21,
"falsePositives": 0
},
{
Expand Down Expand Up @@ -1286,7 +1286,7 @@
{
"ruleKey": "S2447",
"hasTruePositives": true,
"falseNegatives": 0,
"falseNegatives": 4,
"falsePositives": 0
},
{
Expand All @@ -1298,13 +1298,13 @@
{
"ruleKey": "S2583",
"hasTruePositives": true,
"falseNegatives": 21,
"falseNegatives": 20,
"falsePositives": 0
},
{
"ruleKey": "S2589",
"hasTruePositives": true,
"falseNegatives": 5,
"falseNegatives": 6,
"falsePositives": 0
},
{
Expand All @@ -1322,13 +1322,13 @@
{
"ruleKey": "S2637",
"hasTruePositives": true,
"falseNegatives": 21,
"falseNegatives": 87,
"falsePositives": 0
},
{
"ruleKey": "S2638",
"hasTruePositives": true,
"falseNegatives": 7,
"falseNegatives": 9,
"falsePositives": 0
},
{
Expand Down Expand Up @@ -1442,7 +1442,7 @@
{
"ruleKey": "S2789",
"hasTruePositives": true,
"falseNegatives": 11,
"falseNegatives": 37,
"falsePositives": 0
},
{
Expand Down Expand Up @@ -1664,7 +1664,7 @@
{
"ruleKey": "S3516",
"hasTruePositives": true,
"falseNegatives": 11,
"falseNegatives": 8,
"falsePositives": 0
},
{
Expand Down Expand Up @@ -1766,7 +1766,7 @@
{
"ruleKey": "S3958",
"hasTruePositives": true,
"falseNegatives": 2,
"falseNegatives": 4,
"falsePositives": 0
},
{
Expand Down Expand Up @@ -2018,7 +2018,7 @@
{
"ruleKey": "S4682",
"hasTruePositives": true,
"falseNegatives": 0,
"falseNegatives": 8,
"falsePositives": 0
},
{
Expand All @@ -2036,7 +2036,7 @@
{
"ruleKey": "S4738",
"hasTruePositives": false,
"falseNegatives": 55,
"falseNegatives": 68,
"falsePositives": 0
},
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S1128",
"hasTruePositives": true,
"falseNegatives": 33,
"falseNegatives": 34,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S1168",
"hasTruePositives": true,
"falseNegatives": 6,
"falseNegatives": 24,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S1172",
"hasTruePositives": true,
"falseNegatives": 17,
"falseNegatives": 21,
"falsePositives": 0
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S2447",
"hasTruePositives": true,
"falseNegatives": 0,
"falseNegatives": 4,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S2583",
"hasTruePositives": true,
"falseNegatives": 12,
"falseNegatives": 20,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S2589",
"hasTruePositives": true,
"falseNegatives": 4,
"falseNegatives": 6,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S2637",
"hasTruePositives": true,
"falseNegatives": 21,
"falseNegatives": 87,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S2638",
"hasTruePositives": true,
"falseNegatives": 12,
"falseNegatives": 14,
"falsePositives": 0
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S2789",
"hasTruePositives": true,
"falseNegatives": 17,
"falseNegatives": 43,
"falsePositives": 0
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S3516",
"hasTruePositives": true,
"falseNegatives": 6,
"falseNegatives": 8,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S3958",
"hasTruePositives": true,
"falseNegatives": 2,
"falseNegatives": 4,
"falsePositives": 0
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S4682",
"hasTruePositives": true,
"falseNegatives": 2,
"falseNegatives": 10,
"falsePositives": 0
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"ruleKey": "S4738",
"hasTruePositives": false,
"falseNegatives": 46,
"falseNegatives": 70,
"falsePositives": 0
}
6 changes: 6 additions & 0 deletions java-checks-test-sources/default/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,12 @@
3) Several plugins are disabled bellow to not generate jars
-->
<dependencies>
<!-- https://mvnrepository.com/artifact/org.jspecify/jspecify -->
<dependency>
<groupId>org.jspecify</groupId>
<artifactId>jspecify</artifactId>
<version>1.0.0</version>
</dependency>
<dependency>
<groupId>org.checkerframework</groupId>
<artifactId>checker-compat-qual</artifactId>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
package checks.jspecify;

import java.util.stream.Stream;
import javax.annotation.CheckForNull;
import javax.annotation.Nullable;
import org.jspecify.annotations.NullMarked;
import org.jspecify.annotations.NullUnmarked;

@NullMarked
class BooleanMethodReturnCheckJSpecifySampleA {
public Boolean myMethod() {
return null; // Noncompliant {{Null is returned but a "Boolean" is expected.}}
}

public Boolean myOtherMethod() {
return Boolean.TRUE; // Compliant
}

BooleanMethodReturnCheckJSpecifySampleA() {
// constructor (with null return type) are not covered by the rule
return;
}

@Nullable
public Boolean foo() {
return null; // Compliant
}

@NullUnmarked
public Boolean bar() {
return null; // Compliant
}
}

@NullMarked
class BooleanMethodReturnCheckJSpecifySampleB {
private class Boolean {
}

public Boolean myMethodFailing() {
return null; // Compliant
}

public java.lang.Boolean myOtherMethod() {
class BooleanMethodReturnCheckSampleC {
private java.lang.Boolean myInnerMethod() {
return null; // Noncompliant {{Null is returned but a "Boolean" is expected.}}
}
private BooleanMethodReturnCheckSampleC foo() {
return null; // Compliant
}
}
return null; // Noncompliant {{Null is returned but a "Boolean" is expected.}}
// ^^^^
}

@CheckForNull
public java.lang.Boolean myMethod2() {
return null; // compliant method is annotated with @CheckForNull
}
}

@NullMarked
class BooleanMethodReturnCheckJSpecifySampleD {
public Boolean foo() {
class BooleanMethodReturnCheckSampleE {
void bar() {
return;
}
}
Stream.of("A").forEach(a -> {
return; // Compliant
});
return true;
}
}

class BooleanMethodReturnCheckJSpecifySampleE {
@NullMarked
public Boolean myMethod() {
return null; // Noncompliant {{Null is returned but a "Boolean" is expected.}}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package checks.jspecify;

import org.jspecify.annotations.NullMarked;
import org.jspecify.annotations.NullUnmarked;

@NullMarked
class ChangeMethodContractCheck {

@interface MyAnnotation {}

@NullUnmarked
String annotatedUnmarked(Object a) { return null; }
}

class ChangeMethodContractCheck_B extends ChangeMethodContractCheck {

@NullMarked
@Override
String annotatedUnmarked(Object a) { return null; } // Noncompliant {{Fix the incompatibility of the annotation @NullMarked to honor @NullUnmarked of the overridden method.}}

}

Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package checks.jspecify;

import org.jspecify.annotations.NullMarked;
import org.jspecify.annotations.NullUnmarked;

@NullMarked
class EqualsParametersMarkedNonNullCheckSampleA {

// @NullUnmarked not applicable to parameter
public boolean equals(Object obj) { // Compliant
return true;
}
}

@NullMarked
class EqualsParametersMarkedNonNullCheckSampleB {

@NullUnmarked
// @NullUnmarked not applicable to parameter
public boolean equals(Object obj) { // Compliant
return true;
}
}
Loading

0 comments on commit 6ec169b

Please sign in to comment.