View Javadoc

    1   package net.sourceforge.pmd;
    2
    3   import java.util.HashMap;
    4   import java.util.List;
    5   import java.util.Map;
    6
    7   import net.sourceforge.pmd.ast.CompilationUnit;
    8   import net.sourceforge.pmd.ast.JavaRuleChainVisitor;
    9   import net.sourceforge.pmd.jsp.ast.JspRuleChainVisitor;
    10
    11  /**
    12   * The RuleChain is a means by which Rules can participate in a uniform
    13   * visitation of the AST, and not need perform their own independent visitation.
    14   * The RuleChain exists as a means to improve the speed of PMD when there are
    15   * many Rules.
    16   */
    17  public class RuleChain {
    18      // Mapping from Language to RuleChainVisitor
    19      private final Map<Language, RuleChainVisitor> languageToRuleChainVisitor = new HashMap<Language, RuleChainVisitor>();
    20
    21      /**
    22       * Add all Rules from the given RuleSet which want to participate in the
    23       * RuleChain.
    24       *
    25       * @param ruleSet
    26       *            The RuleSet to add Rules from.
    27       */
    28      public void add(RuleSet ruleSet) {
    29          Language language = ruleSet.getLanguage();
    30          for (Rule r: ruleSet.getRules()) {
    31              add(ruleSet, r, language);
    32          }
    33      }
    34
    35      /**
    36       * Add the given Rule if it wants to participate in the RuleChain.
    37       *
    38       * @param ruleSet
    39       *            The RuleSet to which the rule belongs.
    40       * @param rule
    41       *            The Rule to add.
    42       * @param language
    43       *            The Language used by the Rule.
    44       */
    45      private void add(RuleSet ruleSet, Rule rule, Language language) {
    46          RuleChainVisitor visitor = getRuleChainVisitor(language);
    47          if (visitor != null) {
    48              visitor.add(ruleSet, rule);
    49          }
    50      }
    51
    52      /**
    53       * Apply the RuleChain to the given ASTCompilationUnits using the given
    54       * RuleContext, for those rules using the given Language.
    55       *
    56       * @param astCompilationUnits
    57       *            The ASTCompilationUnits.
    58       * @param ctx
    59       *            The RuleContext.
    60       * @param language
    61       *            The Language.
    62       */
    63      public void apply(List<CompilationUnit> astCompilationUnits, RuleContext ctx,
    64              Language language) {
    65          RuleChainVisitor visitor = getRuleChainVisitor(language);
    66          if (visitor != null) {
    67              visitor.visitAll(astCompilationUnits, ctx);
    68          }
    69      }
    70
    71      // Get the RuleChainVisitor for the appropriate Language.
    72      private RuleChainVisitor getRuleChainVisitor(Language language) {
    73          if (language == null) {
    74              language = Language.JAVA;
    75          }
    76          RuleChainVisitor visitor = languageToRuleChainVisitor.get(language);
    77          if (visitor == null) {
    78              if (Language.JAVA.equals(language)) {
    79                  visitor = new JavaRuleChainVisitor();
    80              } else if (Language.JSP.equals(language)) {
    81                  visitor = new JspRuleChainVisitor();
    82              } else {
    83                  throw new IllegalArgumentException("Unknown language: "
    84                          + language);
    85              }
    86              languageToRuleChainVisitor.put(language, visitor);
    87          }
    88          return visitor;
    89      }
    90  }