KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > puppycrawl > tools > checkstyle > checks > modifier > ModifierOrderCheck


1 ////////////////////////////////////////////////////////////////////////////////
2
// checkstyle: Checks Java source code for adherence to a set of rules.
3
// Copyright (C) 2001-2005 Oliver Burn
4
//
5
// This library is free software; you can redistribute it and/or
6
// modify it under the terms of the GNU Lesser General Public
7
// License as published by the Free Software Foundation; either
8
// version 2.1 of the License, or (at your option) any later version.
9
//
10
// This library is distributed in the hope that it will be useful,
11
// but WITHOUT ANY WARRANTY; without even the implied warranty of
12
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
// Lesser General Public License for more details.
14
//
15
// You should have received a copy of the GNU Lesser General Public
16
// License along with this library; if not, write to the Free Software
17
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18
////////////////////////////////////////////////////////////////////////////////
19
package com.puppycrawl.tools.checkstyle.checks.modifier;
20
21 import antlr.collections.AST;
22
23 import java.util.List JavaDoc;
24 import java.util.ArrayList JavaDoc;
25 import java.util.Iterator JavaDoc;
26
27 import com.puppycrawl.tools.checkstyle.api.Check;
28 import com.puppycrawl.tools.checkstyle.api.TokenTypes;
29 import com.puppycrawl.tools.checkstyle.api.DetailAST;
30
31 /**
32  * <p>
33  * Checks that the order of modifiers conforms to the suggestions in the
34  * <a
35  * HREF="http://java.sun.com/docs/books/jls/second_edition/html/classes.doc.html">
36  * Java Language specification, sections 8.1.1, 8.3.1 and 8.4.3</a>.
37  * The correct order is:</p>
38
39 <ol>
40   <li><span class="code">public</span></li>
41   <li><span class="code">protected</span></li>
42
43   <li><span class="code">private</span></li>
44   <li><span class="code">abstract</span></li>
45   <li><span class="code">static</span></li>
46   <li><span class="code">final</span></li>
47   <li><span class="code">transient</span></li>
48   <li><span class="code">volatile</span></li>
49
50   <li><span class="code">synchronized</span></li>
51   <li><span class="code">native</span></li>
52   <li><span class="code">strictfp</span></li>
53 </ol>
54  * In additional, modifiers are checked to ensure all annotations
55  * are declared before all other modifiers.
56  * <p>
57  * Rationale: Code is easier to read if everybody follows
58  * a standard.
59  * </p>
60  * <p>
61  * An example of how to configure the check is:
62  * </p>
63  * <pre>
64  * &lt;module name="ModifierOrder"/&gt;
65  * </pre>
66  * @author Lars Kühne
67  */

68 public class ModifierOrderCheck
69     extends Check
70 {
71     /**
72      * The order of modifiers as suggested in sections 8.1.1,
73      * 8.3.1 and 8.4.3 of the JLS.
74      */

75     private static final String JavaDoc[] JLS_ORDER =
76     {
77         "public", "protected", "private", "abstract", "static", "final",
78         "transient", "volatile", "synchronized", "native", "strictfp",
79     };
80
81     /** {@inheritDoc} */
82     public int[] getDefaultTokens()
83     {
84         return new int[] {TokenTypes.MODIFIERS};
85     }
86
87     /** {@inheritDoc} */
88     public void visitToken(DetailAST aAST)
89     {
90         final List JavaDoc mods = new ArrayList JavaDoc();
91         AST modifier = aAST.getFirstChild();
92         while (modifier != null) {
93             mods.add(modifier);
94             modifier = modifier.getNextSibling();
95         }
96
97         if (!mods.isEmpty()) {
98             final DetailAST error = checkOrderSuggestedByJLS(mods);
99             if (error != null) {
100                 if (error.getType() == TokenTypes.ANNOTATION) {
101                     log(error.getLineNo(), error.getColumnNo(),
102                             "annotation.order",
103                              error.getFirstChild().getText()
104                              + error.getFirstChild().getNextSibling()
105                                 .getText());
106                 }
107                 else {
108                     log(error.getLineNo(), error.getColumnNo(),
109                             "mod.order", error.getText());
110                 }
111             }
112         }
113     }
114
115
116     /**
117      * Checks if the modifiers were added in the order suggested
118      * in the Java language specification.
119      *
120      * @param aModifiers list of modifier AST tokens
121      * @return null if the order is correct, otherwise returns the offending
122      * * modifier AST.
123      */

124     DetailAST checkOrderSuggestedByJLS(List JavaDoc aModifiers)
125     {
126         int i = 0;
127         DetailAST modifier;
128         final Iterator JavaDoc it = aModifiers.iterator();
129         //No modifiers, no problems
130
if (!it.hasNext()) {
131             return null;
132         }
133
134         //Speed past all initial annotations
135
do {
136             modifier = (DetailAST) it.next();
137         }
138         while (it.hasNext() && (modifier.getType() == TokenTypes.ANNOTATION));
139
140         //All modifiers are annotations, no problem
141
if (modifier.getType() == TokenTypes.ANNOTATION) {
142             return null;
143         }
144
145         while (i < JLS_ORDER.length) {
146             if (modifier.getType() == TokenTypes.ANNOTATION) {
147                 //Annotation not at start of modifiers, bad
148
return modifier;
149             }
150
151             while ((i < JLS_ORDER.length)
152                    && !JLS_ORDER[i].equals(modifier.getText()))
153             {
154                 i++;
155             }
156
157             if (i == JLS_ORDER.length) {
158                 //Current modifier is out of JLS order
159
return modifier;
160             }
161             else if (!it.hasNext()) {
162                 //Reached end of modifiers without problem
163
return null;
164             }
165             else {
166                 modifier = (DetailAST) it.next();
167             }
168         }
169
170         return modifier;
171     }
172 }
173
Popular Tags