Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding a new static analyzer (PVS-Studio) #1

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -34,3 +34,7 @@ out/
logs/

.java-version


### PVS-Studio ###
.PVS-Studio
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,16 @@ Gradle configuration for spotbugs is located in [gradle/spotbugs.gradle](gradle/
Command:
`gradle spotBugsMain`

### PVS-Studio
[PVS-Studio](https://www.viva64.com/en/pvs-studio/) is a promising static code analyzer. It can detect such problems as potential null object dereference, conditional expressions that are always true or false, unreachable code, infinite recursion, comparison of objects with incompatible types, and much more. In addition, the analyzer's strength is the search for copy-paste errors that are difficult to find during code review, for example, equivalent implementation of branches in an if-then-else statement or two completely different methods, comparing a variable with itself, etc.

Gradle configuration for PVS-Studio is located in [gradle/pvsstudio.gradle](gradle/pvsstudio.gradle).

Command:
`gradle pvsAnalyze`

Output:
![PVS-Studio Report](results/pvsstudioReport.png)

## Practices

Expand Down
2 changes: 1 addition & 1 deletion build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@ repositories {
dependencies {
testImplementation 'org.junit.jupiter:junit-jupiter:5.6.0'
testImplementation 'org.hamcrest:hamcrest-core:2.2'

}

sourceSets {
Expand Down Expand Up @@ -54,6 +53,7 @@ apply from: 'gradle/checkstyle.gradle'
apply from: 'gradle/jacoco.gradle'
apply from: 'gradle/pmd.gradle'
apply from: 'gradle/spotbugs.gradle'
apply from: 'gradle/pvsstudio.gradle'

integrationTest.dependsOn test
jacocoTestCoverageVerification.dependsOn jacocoTestReport
Expand Down
26 changes: 26 additions & 0 deletions gradle/pvsstudio.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
buildscript {
repositories {
mavenCentral()
maven {
url uri('http://files.viva64.com/java/pvsstudio-maven-repository/')
}
}
dependencies {
classpath group: 'com.pvsstudio',
name: 'pvsstudio-gradle-plugin',
version: '7.07.38241'
}
}

apply plugin: com.pvsstudio.PvsStudioGradlePlugin
pvsstudio {
projectPath = "$projectDir"

outputType = 'html'
outputFile = "${project.reportsDir}/pvsstudio/report.html"

analyzeOnly = ["./src/main/java/com/qualitychecks/entity/RandomShapeFactory.java"]

username = "PVS-Studio Free"
serialNumber ="FREE-FREE-FREE-FREE"
}
Binary file added results/pvsstudioReport.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
73 changes: 73 additions & 0 deletions src/main/java/com/qualitychecks/entity/RandomShapeFactory.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
// This is an open source non-commercial project. Dear PVS-Studio, please check it.
// PVS-Studio Static Code Analyzer for C, C++, C#, and Java: http://www.viva64.com

package com.qualitychecks.entity;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.math.BigDecimal;
import java.util.*;
import java.util.function.Function;
import java.util.logging.Level;
import java.util.logging.LogManager;
import java.util.logging.Logger;

public final class RandomShapeFactory {
public enum ShapeType {
Circle, Rectangle
}

private static RandomShapeFactory factory = new RandomShapeFactory();
private static Logger logger = LogManager.getLogManager().getLogger(RandomShapeFactory.class.getName());

private static final Map<String, Integer> COLORS = new HashMap<>();

static {
COLORS.put("black", 0);
COLORS.put("red", 16711680);
COLORS.put("green", 65280);
COLORS.put("blue", 255);
COLORS.put("magenta", 16711935);
COLORS.put("blue", 16776960);
COLORS.put("cyan", 65535);
}

private List<String> values;

private RandomShapeFactory() {
Function<String, Boolean> isNumeric = str -> str != null && str.matches("[-+]?\\d*\\.?\\d+");
try {
BufferedReader reader = new BufferedReader(new InputStreamReader(getClass().getResourceAsStream("shapeFactoryValues")));
for (String value : reader.readLine().split(" ")) {
if (isNumeric.apply(value)) {
values.add(value);
} else {
logger.warning(String.format("'%s' - invalid value", value));
}
}
reader.close();
} catch (IOException ex) {
// default values
values = Arrays.asList("1", "2", "3");
logger.log(Level.SEVERE, ex.getMessage(), ex);
}
}

public static RandomShapeFactory getInstance() {
return factory;
}

public Shape getShapeRandomSize(final ShapeType type) {
switch (type) {
case Circle:
return new Circle(new BigDecimal(values.get(new Random().nextInt(values.size()))));
case Rectangle:
return new Rectangle(new BigDecimal(new Random().nextInt(values.size())),
new BigDecimal(new Random().nextInt(values.size())));
/* other shapes*/
default:
throw new IllegalArgumentException("Wrong shape type:" + type);
}
}
}
1 change: 1 addition & 0 deletions src/main/resources/shapeFactoryValues
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
1 3.2 5.7 9.6 4.5 9