01: package net.sourceforge.pmd;
02:
03: import java.util.HashMap;
04: import java.util.List;
05: import java.util.Map;
06:
07: import net.sourceforge.pmd.ast.CompilationUnit;
08: import net.sourceforge.pmd.ast.JavaRuleChainVisitor;
09: 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(language, r);
32: }
33: }
34:
35: /**
36: * Add the given Rule if it wants to participate in the RuleChain.
37: *
38: * @param language
39: * The Language used by the Rule.
40: * @param rule
41: * The Rule to add.
42: */
43: public void add(Language language, Rule rule) {
44: RuleChainVisitor visitor = getRuleChainVisitor(language);
45: if (visitor != null) {
46: visitor.add(rule);
47: }
48: }
49:
50: /**
51: * Apply the RuleChain to the given ASTCompilationUnits using the given
52: * RuleContext, for those rules using the given Language.
53: *
54: * @param astCompilationUnits
55: * The ASTCompilationUnits.
56: * @param ctx
57: * The RuleContext.
58: * @param language
59: * The Language.
60: */
61: public void apply(List<CompilationUnit> astCompilationUnits,
62: RuleContext ctx, Language language) {
63: RuleChainVisitor visitor = getRuleChainVisitor(language);
64: if (visitor != null) {
65: visitor.visitAll(astCompilationUnits, ctx);
66: }
67: }
68:
69: // Get the RuleChainVisitor for the appropriate Language.
70: private RuleChainVisitor getRuleChainVisitor(Language language) {
71: if (language == null) {
72: language = Language.JAVA;
73: }
74: RuleChainVisitor visitor = languageToRuleChainVisitor
75: .get(language);
76: if (visitor == null) {
77: if (Language.JAVA.equals(language)) {
78: visitor = new JavaRuleChainVisitor();
79: } else if (Language.JSP.equals(language)) {
80: visitor = new JspRuleChainVisitor();
81: } else {
82: throw new IllegalArgumentException("Unknown language: "
83: + language);
84: }
85: languageToRuleChainVisitor.put(language, visitor);
86: }
87: return visitor;
88: }
89: }
|