##### Overview

- Download PMD 5.0.4
- What's new in PMD 5.0.4
- PMD in the news
- PMD-related products and books
- Best practices
- Future directions
- Similar projects
- Credits
- License
- What does 'PMD' mean?

##### Usage

- Installation
- Command line usage
- Ant task usage
- Maven plugin usage
- Mvn plugin usage
- IDE plugin usage
- Suppressing warnings
- Finding duplicated code
- JSP support

##### Customizing PMD

- Compiling PMD
- How to write a rule
- Writing XPath rules
- How to make a rule set
- How it works
- Rule guidelines
- PMD developers information
- PMD Release Process

##### For example

- Run PMD on a Sourceforge project

##### Misc.

- XPath tutorial (Gregorian)

##### Rule Sets

- ecmascript
  - Basic Ecmascript
  - Braces
  - Unnecessary
- java
  - Android
  - Basic
  - Braces
  - Clone Implementation
  - Code Size
  - Comments
  - Controversial
  - Coupling
  - Design
  - Empty Code
  - Finalizer
  - Import Statements
  - J2EE
  - JavaBeans
  - JUnit
  - Jakarta Commons Logging
  - Java Logging
  - Migration
  - Naming
  - Optimization
  - Strict Exceptions
  - String and StringBuffer
  - Security Code Guidelines
  - Type Resolution
  - Unnecessary
  - Unused Code
- jsp
  - Basic JSF
  - Basic JSP
- xml
  - Basic XML
- xsl
  - XPath in XSL

##### Project Documentation

- Project Information
- Project Reports

## Naming

The Naming Ruleset contains rules regarding preferred usage of names and identifiers.

### ShortVariable

Since: PMD 0.3

Fields, local variables, or parameter names that are very short are not helpful to the reader.

    //VariableDeclaratorId[string-length(@Image) < 3]
     [not(ancestor::ForInit)]
     [not((ancestor::FormalParameter) and (ancestor::TryStatement))]

Example(s):

    public class Something {
    	private int q = 15; 						// field - too short
    	public static void main( String as[] ) {  	// formal arg - too short
    		int r = 20 + q; 						// local var - too short
    		for (int i = 0; i < 10; i++) { 			// not a violation (inside 'for' loop)
    			r += q;
    		}
    	}
    }

### LongVariable

Since: PMD 0.3

Fields, formal arguments, or local variable names that are too long can make the code difficult to follow.

    //VariableDeclaratorId[string-length(@Image) > $minimum]

Example(s):

    public class Something {
    	int reallyLongIntName = -3;  			// VIOLATION - Field
    	public static void main( String argumentsList[] ) { // VIOLATION - Formal
    		int otherReallyLongName = -5; 		// VIOLATION - Local
    		for (int interestingIntIndex = 0;	// VIOLATION - For
                 interestingIntIndex < 10;
                 interestingIntIndex ++ ) {
        }
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
minimum | 17 | The variable length reporting threshold

### ShortMethodName

Since: PMD 0.3

Method names that are very short are not helpful to the reader.

    //MethodDeclarator[string-length(@Image) < 3]

Example(s):

    public class ShortMethod {
    	public void a( int i ) { // Violation
    	}
    }

### VariableNamingConventions

Since: PMD 1.2

A variable naming conventions rule - customize this to your liking. Currently, it checks for final variables that should be fully capitalized and non-final variables that should not include underscores.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.VariableNamingConventionsRule

Example(s):

    public class Foo {
       public static final int MY_NUM = 0;
       public String myTest = "";
       DataModule dmTest = new DataModule();
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.
parameterSuffix | [] | Method parameter variable suffixes
parameterPrefix | [] | Method parameter variable prefixes
localSuffix | [] | Local variable suffixes
localPrefix | [] | Local variable prefixes
memberSuffix | [] | Member variable suffixes
memberPrefix | [] | Member variable prefixes
staticSuffix | [] | Static variable suffixes
staticPrefix | [] | Static variable prefixes
checkParameters | true | Check constructor and method parameter variables
checkLocals | true | Check local variables
checkMembers | true | Check member variables

### MethodNamingConventions

Since: PMD 1.2

Method names should always begin with a lower case character, and should not contain underscores.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.MethodNamingConventionsRule

Example(s):

    public class Foo {
    	public void fooStuff() {
    	}
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### ClassNamingConventions

Since: PMD 1.2

Class names should always begin with an upper case character.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.ClassNamingConventionsRule

Example(s):

    public class Foo {}

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### AbstractNaming

Since: PMD 1.4

Abstract classes should be named 'AbstractXXX'.

    //ClassOrInterfaceDeclaration
     [@Abstract='true' and @Interface='false']
     [not (starts-with(@Image,'Abstract'))]

Example(s):

    public abstract class Foo { // should be AbstractFoo
    }

### AvoidDollarSigns

Since: PMD 1.5

Avoid using dollar signs in variable/method/class/interface names.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.AvoidDollarSignsRule

Example(s):

    public class Fo$o {  // not a recommended name
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### MethodWithSameNameAsEnclosingClass

Since: PMD 1.5

Non-constructor methods should not have the same name as the enclosing class.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.MethodWithSameNameAsEnclosingClassRule

Example(s):

    public class MyClass {

    	public MyClass() {}			// this is OK because it is a constructor

    	public void MyClass() {}	// this is bad because it is a method
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### SuspiciousHashcodeMethodName

Since: PMD 1.5

The method name and return type are suspiciously close to hashCode(), which may denote an intention to override the hashCode() method.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.SuspiciousHashcodeMethodNameRule

Example(s):

    public class Foo {
    	public int hashcode() {	// oops, this probably was supposed to be 'hashCode'

    	}
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### SuspiciousConstantFieldName

Since: PMD 2.0

Field names using all uppercase characters - Sun's Java naming conventions indicating constants - should be declared as final.

    //ClassOrInterfaceDeclaration[@Interface='false']
     /ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/FieldDeclaration
      [@Final='false']
      [VariableDeclarator/VariableDeclaratorId[upper-case(@Image)=@Image]]

Example(s):

    public class Foo {
     // this is bad, since someone could accidentally
     // do PI = 2.71828; which is actually e
     // final double PI = 3.16; is ok
      double PI = 3.16;
    }

### SuspiciousEqualsMethodName

Since: PMD 2.0

The method name and parameter number are suspiciously close to equals(Object), which can denote an intention to override the equals(Object) method.

    //MethodDeclarator[@Image = 'equals']
    [
        (count(FormalParameters/*) = 1
        and not (FormalParameters/FormalParameter/Type/ReferenceType/ClassOrInterfaceType
            [@Image = 'Object' or @Image = 'java.lang.Object'])
        or not (../ResultType/Type/PrimitiveType[@Image = 'boolean'])
        )  or  (
        count(FormalParameters/*) = 2
        and ../ResultType/Type/PrimitiveType[@Image = 'boolean']
        and FormalParameters//ClassOrInterfaceType[@Image = 'Object' or @Image = 'java.lang.Object']
        )
    ]
    | //MethodDeclarator[@Image = 'equal']
    [
        count(FormalParameters/*) = 1
        and FormalParameters/FormalParameter/Type/ReferenceType/ClassOrInterfaceType
            [@Image = 'Object' or @Image = 'java.lang.Object']
    ]

Example(s):

    public class Foo {
       public int equals(Object o) {
         // oops, this probably was supposed to be boolean equals
       }
       public boolean equals(String s) {
         // oops, this probably was supposed to be equals(Object)
       }
       public boolean equals(Object o1, Object o2) {
         // oops, this probably was supposed to be equals(Object)
       }
    }

### AvoidFieldNameMatchingTypeName

Since: PMD 3.0

It is somewhat confusing to have a field name matching the declaring class name. This probably means that type and/or field names should be chosen more carefully.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.AvoidFieldNameMatchingTypeNameRule

Example(s):

    public class Foo extends Bar {
    	int foo;	// There is probably a better name that can be used
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### AvoidFieldNameMatchingMethodName

Since: PMD 3.0

It can be confusing to have a field name with the same name as a method. While this is permitted, having information (field) and actions (method) is not clear naming. Developers versed in Smalltalk often prefer this approach as the methods denote accessor methods.

This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.naming.AvoidFieldNameMatchingMethodNameRule

Example(s):

    public class Foo {
    	Object bar;
    	// bar is data or an action or both?
    	void bar() {
    	}
    }

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
violationSuppressRegex |  | Suppress violations with messages matching a regular expression
violationSuppressXPath |  | Suppress violations on nodes which match a given relative XPath expression.

### NoPackage

Since: PMD 3.3

Detects when a class or interface does not have a package definition.

    //ClassOrInterfaceDeclaration[count(preceding::PackageDeclaration) = 0]

Example(s):

    // no package declaration
    public class ClassInDefaultPackage {
    }

### PackageCase

Since: PMD 3.3

Detects when a package definition contains uppercase characters.

    //PackageDeclaration/Name[lower-case(@Image)!=@Image]

Example(s):

    package com.MyCompany;  // should be lowercase name

    public class SomeClass {
    }

### MisleadingVariableName

Since: PMD 3.4

Detects when a non-field has a name starting with 'm_'. This usually denotes a field and could be confusing.

    //VariableDeclaratorId
    [starts-with(@Image, 'm_')]
    [not (../../../FieldDeclaration)]

Example(s):

    public class Foo {
        private int m_foo; // OK
        public void bar(String m_baz) {  // Bad
          int m_boz = 42; // Bad
        }
    }

### BooleanGetMethodName

Since: PMD 4.0

Methods that return boolean results should be named as predicate statements to denote this. I.e, 'isReady()', 'hasValues()', 'canCommit()', 'willFail()', etc. Avoid the use of the 'get' prefix for these methods.

    //MethodDeclaration[
    MethodDeclarator[count(FormalParameters/FormalParameter) = 0 or $checkParameterizedMethods = 'true']
                    [starts-with(@Image, 'get')]
    and
    ResultType/Type/PrimitiveType[@Image = 'boolean']
    ]

Example(s):

    public boolean getFoo(); 	// bad
    public boolean isFoo(); 	// ok
    public boolean getFoo(boolean bar); // ok, unless checkParameterizedMethods=true

This rule has the following properties:

Name | Default Value | Description
--- | --- | ---
checkParameterizedMethods | false | Check parameterized methods

### ShortClassName

Since: PMD 5.0

Classnames with fewer than five characters are not recommended.

    //ClassOrInterfaceDeclaration[string-length(@Image) < 5]

Example(s):

    public class Foo {
    }

### GenericsNaming

Since: PMD 4.2.6

Names for references to generic values should be limited to a single uppercase letter.

    //TypeDeclaration/ClassOrInterfaceDeclaration/TypeParameters/TypeParameter[
      string-length(@Image) > 1
      or
      string:upper-case(@Image) != @Image
    ]

Example(s):

    public interface GenericDao<E extends BaseModel, K extends Serializable> extends BaseDao {
       // This is ok...
    }

    public interface GenericDao<E extends BaseModel, K extends Serializable> {
       // Also this
    }

    public interface GenericDao<e extends BaseModel, K extends Serializable> {
       // 'e' should be an 'E'
    }

    public interface GenericDao<EF extends BaseModel, K extends Serializable> {
       // 'EF' is not ok.
    }