Uploaded image for project: 'Maven PMD Plugin'
  1. Maven PMD Plugin
  2. MPMD-178

ExcludeRoots doesn't handle subdirectories (PMD isn't working nicely with Android projects)

    XMLWordPrintableJSON

Details

    • Bug
    • Status: Closed
    • Major
    • Resolution: Fixed
    • 3.0.1
    • 3.7
    • PMD
    • None
    • all

    Description

      We are using PMD to check an Android project. The pom file that "drives" the Android project uses android-maven-plugin (3.8.2).

      Our android project depends on a number of 3rd party libraries. Some of these libraries are apklibs. The android-maven-plugin handles apklibs by expanding them into a given directory before compiling.

      This results in a very long value being passed to maven-pmd in the compileSourceRoots variable. I understand you can't override compileSourceRoots so I turned to excludeRoots to exclude these 3rd parties libraries from analysis

      The target directories that contain source in an maven Android project would look something like:

      /target/generated-sources/extracted-dependencies/src/main/java
      /target/generated-sources/r
      /target/generated-sources/aidl
      /target/unpacked-libs/com.actionbarsherlock_actionbarsherlock_apklib_4.3.0/src
      /target/unpacked-libs/com.github.chrisbanes.pulltorefresh_library_apklib_2.1.2-SNAPSHOT/src
      /target/unpacked-libs/com.slidingmenu_slidingmenu_apklib_1.3-SNAPSHOT/src
      

      So you would hope that the maven-pmd plugin could be configured as

      <excludeRoots>
        <excludeRoot>target/generated-sources</excludeRoot>
        <excludeRoot>target/unpacked-libs</excludeRoot>
      </excludeRoots>
      

      However this doesn't work. The excludeRoots get compared directly for equality in the contains clause of

       if ( sourceDirectory.isDirectory() && !excludeRootFiles.contains( sourceDirectory ) ) 
      

      in AbstractPmdReport.java. This obviously doesn't work as unpacked-libs is the container for a whole host of source directories.

      I suggest that the comparison should look at the base path as

          private boolean isDirectoryExcluded(Collection<File> excludeRootFiles, File sourceDirectoryToCheck)
          {
          	boolean returnVal = false;
          	for (File excludeDir : excludeRootFiles)
          	{
          		if (sourceDirectoryToCheck.getAbsolutePath().startsWith(excludeDir.getAbsolutePath()))
          		{
                      getLog().debug( "Directory " +sourceDirectoryToCheck.getAbsolutePath() + " has been excluded as it matches excludeRoot " + excludeDir.getAbsolutePath());    			
          			returnVal = true;
          			break;
          		}
          	}
          	return returnVal;
          }
      

      With the comparison line becoming

        if (sourceDirectory.isDirectory() && !isDirectoryExcluded(excludeRootFiles, sourceDirectory) )
      

      This is working in my test project and doesn't fail any of the maven-pmd unit tests.

      I tried uploading an attachment with the changes described above but to no avail - not sure what is happening there.

      Attachments

        Activity

          People

            adangel Andreas Dangel
            michaelayates Michael Yates
            Votes:
            0 Vote for this issue
            Watchers:
            3 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved: