Ben Hutchison
Ben Hutchison

Reputation: 5103

Prevent PMD from printing violations twice

I have a Java 7 project being built by Maven 3.2.1. I'm analyzing my source code at build time using PMD (maven-pmd-plugin:3.2, which uses net.sourceforge.pmd:pmd:5.1.2 under the hood).

Given a simple class with one violation, my Maven output has that exact violation printed twice, but I don't want duplicate violations because it's misleading and harder to read.

My Source Code

public class Main {
    public static void main(final String[] args) {
        System.out.println("hello");
    }
}

My pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.stackoverflow</groupId>
    <artifactId>pmd-test</artifactId>
    <version>0.0.1-SNAPSHOT</version>

    <build>
        <plugins>
            <plugin>
                <artifactId>maven-pmd-plugin</artifactId>
                <version>3.2</version>
                <configuration>
                    <linkXref>false</linkXref>
                    <sourceEncoding>utf-8</sourceEncoding>
                    <minimumTokens>100</minimumTokens>
                    <targetJdk>1.7</targetJdk>
                    <minimumPriority>2</minimumPriority>
                    <rulesets>
                        <ruleset>/rulesets/java/logging-java.xml</ruleset>
                    </rulesets>
                    <failurePriority>2</failurePriority>
                    <printFailingErrors>true</printFailingErrors>
                    <verbose>true</verbose>
                </configuration>
                <executions>
                    <execution>
                        <goals>
                            <goal>check</goal>
                        </goals>
                        <phase>prepare-package</phase>
                    </execution>
                </executions>
            </plugin>

            <plugin>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.1</version>
                <configuration>
                    <source>1.7</source>
                    <target>1.7</target>
                </configuration>
            </plugin>

        </plugins>
    </build>
</project>

Maven output

mvn prepare-package

[INFO] Scanning for projects...
[INFO]
[INFO] Using the builder org.apache.maven.lifecycle.internal.builder.singlethreaded.SingleThreadedBuilder with a thread count of 1
[INFO]
[INFO] ------------------------------------------------------------------------
[INFO] Building pmd-test 0.0.1-SNAPSHOT
[INFO] ------------------------------------------------------------------------
[INFO]
[INFO] --- maven-resources-plugin:2.6:resources (default-resources) @ pmd-test ---
[WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent!
[INFO] Copying 0 resource
[INFO]
[INFO] --- maven-compiler-plugin:3.1:compile (default-compile) @ pmd-test ---
[INFO] Changes detected - recompiling the module!
[WARNING] File encoding has not been set, using platform encoding Cp1252, i.e. build is platform dependent!
[INFO] Compiling 1 source file to C:\Projects\pmd-test\target\classes
[INFO]
[INFO] --- maven-resources-plugin:2.6:testResources (default-testResources) @ pmd-test ---
[WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent!
[INFO] Copying 0 resource
[INFO]
[INFO] --- maven-compiler-plugin:3.1:testCompile (default-testCompile) @ pmd-test ---
[INFO] Nothing to compile - all classes are up to date
[INFO]
[INFO] --- maven-surefire-plugin:2.12.4:test (default-test) @ pmd-test ---
[INFO]
[INFO] >>> maven-pmd-plugin:3.2:check (default) @ pmd-test >>>
[INFO]
[INFO] --- maven-pmd-plugin:3.2:pmd (pmd) @ pmd-test ---
[WARNING] Unable to locate Source XRef to link to - DISABLED
[INFO]
[INFO] <<< maven-pmd-plugin:3.2:check (default) @ pmd-test <<<
[INFO]
[INFO] --- maven-pmd-plugin:3.2:check (default) @ pmd-test ---
[INFO] PMD Failure: Main:4 Rule:SystemPrintln Priority:2 System.out.println is used.
[INFO] PMD Failure: Main:4 Rule:SystemPrintln Priority:2 System.out.println is used.
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 2.161 s
[INFO] Finished at: 2016-07-06T20:21:41-08:00
[INFO] Final Memory: 21M/308M
[INFO] ------------------------------------------------------------------------
[ERROR] Failed to execute goal org.apache.maven.plugins:maven-pmd-plugin:3.2:check (default) on project pmd-test: You have 1 PMD violation. For more details see:C:\Projects\pmd-test\target\pmd.xml -> [Help 1]
[ERROR]
[ERROR] To see the full stack trace of the errors, re-run Maven with the -e switch.
[ERROR] Re-run Maven using the -X switch to enable full debug logging.
[ERROR]
[ERROR] For more information about the errors and possible solutions, please read the following articles:
[ERROR] [Help 1] http://cwiki.apache.org/confluence/display/MAVEN/MojoFailureException

Specifically, it prints

[INFO] --- maven-pmd-plugin:3.2:check (default) @ pmd-test ---
[INFO] PMD Failure: Main:4 Rule:SystemPrintln Priority:2 System.out.println is used.
[INFO] PMD Failure: Main:4 Rule:SystemPrintln Priority:2 System.out.println is used.
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE

but I want it to print

[INFO] --- maven-pmd-plugin:3.2:check (default) @ pmd-test ---
[INFO] PMD Failure: Main:4 Rule:SystemPrintln Priority:2 System.out.println is used.
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE

What I've tried

Upvotes: 3

Views: 1336

Answers (1)

Ben Hutchison
Ben Hutchison

Reputation: 5103

This issue was caused by my misconfiguration of the Maven PMD Plugin.

To fix the issue so each violation is only printed once, change the configuration of maven-pmd-plugin to disable either printFailingErrors or verbose. They both default to false, so removing either element will solve the issue.

Example fixed plugin configuration in pom.xml

<plugin>
    <artifactId>maven-pmd-plugin</artifactId>
    <version>3.2</version>
    <configuration>
        <linkXref>false</linkXref>
        <sourceEncoding>utf-8</sourceEncoding>
        <minimumTokens>100</minimumTokens>
        <targetJdk>1.7</targetJdk>
        <minimumPriority>2</minimumPriority>
        <rulesets>
            <ruleset>/rulesets/java/logging-java.xml</ruleset>
        </rulesets>
        <failurePriority>2</failurePriority>
        <verbose>true</verbose>
    </configuration>
    <executions>
        <execution>
            <goals>
                <goal>check</goal>
            </goals>
            <phase>prepare-package</phase>
        </execution>
    </executions>
</plugin>

I think that verbose mode should only print errors or warnings that would not have otherwise been printed, to make it consistent with every other logging system ever made, but here we are.

Upvotes: 3

Related Questions