RuleSets xref
1 /**
2 * BSD-style license; for more info see http://pmd.sourceforge.net/license.html
3 */
4 package net.sourceforge.pmd;
5
6 import java.io.File;
7 import java.util.ArrayList;
8 import java.util.Collection;
9 import java.util.HashSet;
10 import java.util.Iterator;
11 import java.util.List;
12 import java.util.Set;
13
14 import net.sourceforge.pmd.lang.Language;
15 import net.sourceforge.pmd.lang.ast.Node;
16
17 /**
18 * Grouping of Rules per Language in a RuleSet.
19 *
20 * @author pieter_van_raemdonck - Application Engineers NV/SA - www.ae.be
21 */
22 public class RuleSets {
23 /**
24 * Map of RuleLanguage on RuleSet.
25 */
26 private Collection<RuleSet> ruleSets = new ArrayList<RuleSet>();
27
28 /**
29 * RuleChain for efficient AST visitation.
30 */
31 private RuleChain ruleChain = new RuleChain();
32
33 /**
34 * Public constructor.
35 */
36 public RuleSets() {
37 }
38
39 /**
40 * Public constructor. Add the given rule set.
41 *
42 * @param ruleSet the RuleSet
43 */
44 public RuleSets(RuleSet ruleSet) {
45 this();
46 addRuleSet(ruleSet);
47 }
48
49 /**
50 * Add a ruleset for a language. Only one ruleset can be added for a specific
51 * language. If ruleSet.getLanguage() is null, it is assumed to be a RuleSet of java
52 * rules.
53 *
54 * @param ruleSet the RuleSet
55 */
56 public void addRuleSet(RuleSet ruleSet) {
57 ruleSets.add(ruleSet);
58 ruleChain.add(ruleSet);
59 }
60
61 /**
62 * Get all the RuleSets.
63 *
64 * @return RuleSet[]
65 */
66 public RuleSet[] getAllRuleSets() {
67 return ruleSets.toArray(new RuleSet[ruleSets.size()]);
68 }
69
70 public Iterator<RuleSet> getRuleSetsIterator() {
71 return ruleSets.iterator();
72 }
73
74 /**
75 * Return all rules from all rulesets.
76 *
77 * @return Set
78 */
79 public Set<Rule> getAllRules() {
80 Set<Rule> result = new HashSet<Rule>();
81 for (RuleSet r : ruleSets) {
82 result.addAll(r.getRules());
83 }
84 return result;
85 }
86
87 /**
88 * Check if a given source file should be checked by rules in this RuleSets.
89 *
90 * @param file the source file to check
91 * @return <code>true</code> if the file should be checked, <code>false</code> otherwise
92 */
93 public boolean applies(File file) {
94 for (RuleSet ruleSet : ruleSets) {
95 if (ruleSet.applies(file)) {
96 return true;
97 }
98 }
99 return false;
100 }
101
102 /**
103 * Notify all rules of the start of processing.
104 */
105 public void start(RuleContext ctx) {
106 for (RuleSet ruleSet : ruleSets) {
107 ruleSet.start(ctx);
108 }
109 }
110
111 /**
112 * Apply all applicable rules to the compilation units.
113 * Applicable means the language of the rules must match the language
114 * of the source (@see applies).
115 *
116 * @param acuList the List of compilation units; the type these must have,
117 * depends on the source language
118 * @param ctx the RuleContext
119 * @param language the Language of the source
120 */
121 public void apply(List<Node> acuList, RuleContext ctx, Language language) {
122 ruleChain.apply(acuList, ctx, language);
123 for (RuleSet ruleSet : ruleSets) {
124 if (ruleSet.applies(ctx.getSourceCodeFile())) {
125 ruleSet.apply(acuList, ctx);
126 }
127 }
128 }
129
130 /**
131 * Notify all rules of the end of processing.
132 */
133 public void end(RuleContext ctx) {
134 for (RuleSet ruleSet : ruleSets) {
135 ruleSet.end(ctx);
136 }
137 }
138
139 /**
140 * Check if the rules that apply to a source of the given language
141 * use DFA.
142 *
143 * @param language the language of a source
144 * @return true if any rule in the RuleSet needs the DFA layer
145 */
146 public boolean usesDFA(Language language) {
147 for (RuleSet ruleSet : ruleSets) {
148 if (ruleSet.usesDFA(language)) {
149 return true;
150 }
151 }
152 return false;
153 }
154
155 /**
156 * Returns the first Rule found with the given name.
157 *
158 * Note: Since we support multiple languages, rule names
159 * are not expected to be unique within any specific
160 * ruleset.
161 *
162 * @param ruleName the exact name of the rule to find
163 * @return the rule or null if not found
164 */
165 public Rule getRuleByName(String ruleName) {
166 Rule rule = null;
167 for (Iterator<RuleSet> i = ruleSets.iterator(); i.hasNext() && rule == null;) {
168 RuleSet ruleSet = i.next();
169 rule = ruleSet.getRuleByName(ruleName);
170 }
171 return rule;
172 }
173
174 public boolean usesTypeResolution(Language language) {
175 for (RuleSet ruleSet : ruleSets) {
176 if (ruleSet.usesTypeResolution(language)) {
177 return true;
178 }
179 }
180 return false;
181 }
182
183 /**
184 * Remove and collect any rules that report problems.
185 *
186 * @param collector
187 */
188 public void removeDysfunctionalRules(Collection<Rule> collector) {
189
190 for (RuleSet ruleSet : ruleSets) {
191 ruleSet.removeDysfunctionalRules(collector);
192 }
193 }
194 }