View Javadoc
1   ///////////////////////////////////////////////////////////////////////////////////////////////
2   // checkstyle: Checks Java source code and other text files for adherence to a set of rules.
3   // Copyright (C) 2001-2026 the original author or authors.
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  
20  package com.puppycrawl.tools.checkstyle.checks.imports;
21  
22  import static com.google.common.truth.Truth.assertWithMessage;
23  import static com.puppycrawl.tools.checkstyle.checks.imports.CustomImportOrderCheck.MSG_LEX;
24  import static com.puppycrawl.tools.checkstyle.checks.imports.CustomImportOrderCheck.MSG_LINE_SEPARATOR;
25  import static com.puppycrawl.tools.checkstyle.checks.imports.CustomImportOrderCheck.MSG_NONGROUP_EXPECTED;
26  import static com.puppycrawl.tools.checkstyle.checks.imports.CustomImportOrderCheck.MSG_NONGROUP_IMPORT;
27  import static com.puppycrawl.tools.checkstyle.checks.imports.CustomImportOrderCheck.MSG_ORDER;
28  import static com.puppycrawl.tools.checkstyle.checks.imports.CustomImportOrderCheck.MSG_SEPARATED_IN_GROUP;
29  import static com.puppycrawl.tools.checkstyle.internal.utils.TestUtil.getExpectedThrowable;
30  
31  import java.io.File;
32  
33  import org.junit.jupiter.api.Test;
34  
35  import com.puppycrawl.tools.checkstyle.AbstractModuleTestSupport;
36  import com.puppycrawl.tools.checkstyle.Checker;
37  import com.puppycrawl.tools.checkstyle.DefaultConfiguration;
38  import com.puppycrawl.tools.checkstyle.api.CheckstyleException;
39  import com.puppycrawl.tools.checkstyle.api.TokenTypes;
40  import com.puppycrawl.tools.checkstyle.internal.utils.TestUtil;
41  import com.puppycrawl.tools.checkstyle.utils.CommonUtil;
42  
43  public class CustomImportOrderCheckTest extends AbstractModuleTestSupport {
44  
45      /** Shortcuts to make code more compact. */
46      private static final String STATIC = CustomImportOrderCheck.STATIC_RULE_GROUP;
47      private static final String SAME = CustomImportOrderCheck.SAME_PACKAGE_RULE_GROUP;
48      private static final String THIRD = CustomImportOrderCheck.THIRD_PARTY_PACKAGE_RULE_GROUP;
49      private static final String STD = CustomImportOrderCheck.STANDARD_JAVA_PACKAGE_RULE_GROUP;
50      private static final String SPECIAL = CustomImportOrderCheck.SPECIAL_IMPORTS_RULE_GROUP;
51  
52      @Override
53      public String getPackageLocation() {
54          return "com/puppycrawl/tools/checkstyle/checks/imports/customimportorder";
55      }
56  
57      @Test
58      public void testGetRequiredTokens() {
59          final CustomImportOrderCheck checkObj = new CustomImportOrderCheck();
60          final int[] expected = {
61              TokenTypes.IMPORT,
62              TokenTypes.STATIC_IMPORT,
63              TokenTypes.PACKAGE_DEF,
64          };
65          assertWithMessage("Default required tokens are invalid")
66              .that(checkObj.getRequiredTokens())
67              .isEqualTo(expected);
68      }
69  
70      @Test
71      public void testCustom() throws Exception {
72          final String[] expected = {
73              "16:1: " + getCheckMessage(MSG_LEX, "java.awt.Button.ABORT",
74                      "java.io.File.createTempFile"),
75              "17:1: " + getCheckMessage(MSG_LEX, "java.awt.print.Paper.*",
76                      "java.io.File.createTempFile"),
77              "20:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.Button"),
78              "21:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.Frame"),
79              "22:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.Dialog"),
80              "23:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.color.ColorSpace"),
81              "24:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.event.ActionEvent"),
82              "25:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "javax.swing.JComponent"),
83              "26:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "javax.swing.JTable"),
84              "27:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.File"),
85              "28:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.IOException"),
86              "29:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.InputStream"),
87              "30:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.Reader"),
88          };
89  
90          verifyWithInlineConfigParser(
91                  getPath("InputCustomImportOrderDefault.java"), expected);
92      }
93  
94      /**
95       * Checks different group orderings and imports which are out of those
96       * specified in the configuration.
97       */
98      @Test
99      public void testStaticStandardThird() throws Exception {
100         final String[] expected = {
101             "16:1: " + getCheckMessage(MSG_LEX, "java.awt.Button.ABORT",
102                     "java.io.File.createTempFile"),
103             "17:1: " + getCheckMessage(MSG_LEX, "java.awt.print.Paper.*",
104                     "java.io.File.createTempFile"),
105             "22:1: " + getCheckMessage(MSG_LEX, "java.awt.Dialog", "java.awt.Frame"),
106             "27:1: " + getCheckMessage(MSG_LEX, "java.io.File", "javax.swing.JTable"),
107             "28:1: " + getCheckMessage(MSG_LEX, "java.io.IOException", "javax.swing.JTable"),
108             "29:1: " + getCheckMessage(MSG_LEX, "java.io.InputStream", "javax.swing.JTable"),
109             "30:1: " + getCheckMessage(MSG_LEX, "java.io.Reader", "javax.swing.JTable"),
110             "34:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "com.google.common.collect.*"),
111             "34:1: " + getCheckMessage(MSG_LEX, "com.google.common.collect.*",
112                     "com.google.errorprone.annotations.*"),
113         };
114 
115         verifyWithInlineConfigParser(
116                 getPath("InputCustomImportOrderDefault3.java"), expected);
117     }
118 
119     @Test
120     public void testStaticStandardThirdListCustomRules() throws Exception {
121         final String[] expected = {
122             "16:1: " + getCheckMessage(MSG_LEX, "java.awt.Button.ABORT",
123                     "java.io.File.createTempFile"),
124             "17:1: " + getCheckMessage(MSG_LEX, "java.awt.print.Paper.*",
125                     "java.io.File.createTempFile"),
126             "22:1: " + getCheckMessage(MSG_LEX, "java.awt.Dialog", "java.awt.Frame"),
127             "27:1: " + getCheckMessage(MSG_LEX, "java.io.File", "javax.swing.JTable"),
128             "28:1: " + getCheckMessage(MSG_LEX, "java.io.IOException", "javax.swing.JTable"),
129             "29:1: " + getCheckMessage(MSG_LEX, "java.io.InputStream", "javax.swing.JTable"),
130             "30:1: " + getCheckMessage(MSG_LEX, "java.io.Reader", "javax.swing.JTable"),
131             "34:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "com.google.common.collect.*"),
132             "34:1: " + getCheckMessage(MSG_LEX, "com.google.common.collect.*",
133                     "com.google.errorprone.annotations.*"),
134         };
135 
136         verifyWithInlineConfigParser(
137                 getPath("InputCustomImportOrderListRules.java"), expected);
138     }
139 
140     @Test
141     public void testStaticStandardThirdListCustomRulesWhitespace() throws Exception {
142         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
143 
144         verifyWithInlineConfigParser(
145                 getPath("InputCustomImportOrderListRulesWhitespace.java"), expected);
146     }
147 
148     @Test
149     public void testInputCustomImportOrderSingleLineList() throws Exception {
150         final String[] expected = {
151             "14:112: " + getCheckMessage(MSG_LINE_SEPARATOR,
152                 "java.util.Map"),
153             "15:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
154                 "com.google.common.annotations.Beta"),
155             "22:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
156                 "com.puppycrawl.tools.checkstyle.*"),
157             "26:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
158                 "picocli.*"),
159         };
160         verifyWithInlineConfigParser(
161                 getPath("InputCustomImportOrderSingleLineList.java"),
162             expected);
163     }
164 
165     /**
166      * Checks different combinations for same_package group.
167      */
168     @Test
169     public void testNonSpecifiedImports() throws Exception {
170         final String[] expected = {
171             "16:1: " + getCheckMessage(MSG_LEX, "java.awt.Button.ABORT",
172                 "java.io.File.createTempFile"),
173             "17:1: " + getCheckMessage(MSG_LEX, "java.awt.print.Paper.*",
174                 "java.io.File.createTempFile"),
175             "22:1: " + getCheckMessage(MSG_LEX, "java.awt.Dialog", "java.awt.Frame"),
176             "27:1: " + getCheckMessage(MSG_LEX, "java.io.File", "javax.swing.JTable"),
177             "28:1: " + getCheckMessage(MSG_LEX, "java.io.IOException", "javax.swing.JTable"),
178             "29:1: " + getCheckMessage(MSG_LEX, "java.io.InputStream", "javax.swing.JTable"),
179             "30:1: " + getCheckMessage(MSG_LEX, "java.io.Reader", "javax.swing.JTable"),
180             "32:1: " + getCheckMessage(MSG_ORDER, SAME, THIRD, "com.puppycrawl.tools.checkstyle.*"),
181             "34:1: " + getCheckMessage(MSG_NONGROUP_IMPORT, "com.google.common.collect.*"),
182             "35:1: " + getCheckMessage(MSG_LINE_SEPARATOR, "org.junit.*"),
183         };
184 
185         verifyWithInlineConfigParser(
186                 getPath("InputCustomImportOrderDefault4.java"), expected);
187     }
188 
189     @Test
190     public void testOrderRuleEmpty() throws Exception {
191         final String[] expected = {
192             "17:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.List"),
193         };
194 
195         verifyWithInlineConfigParser(
196                 getPath("InputCustomImportOrderEmptyRule.java"), expected);
197     }
198 
199     @Test
200     public void testOrderRuleWithOneGroup() throws Exception {
201         final String[] expected = {
202             "16:1: " + getCheckMessage(MSG_LEX, "java.awt.Button.ABORT",
203                     "java.io.File.createTempFile"),
204             "19:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.List"),
205             "19:1: " + getCheckMessage(MSG_LEX, "java.util.List", "javax.swing.WindowConstants.*"),
206             "20:1: " + getCheckMessage(MSG_LEX, "java.util.StringTokenizer",
207                     "javax.swing.WindowConstants.*"),
208             "21:1: " + getCheckMessage(MSG_LEX, "java.util.*", "javax.swing.WindowConstants.*"),
209             "22:1: " + getCheckMessage(MSG_LEX, "java.util.concurrent.AbstractExecutorService",
210                     "javax.swing.WindowConstants.*"),
211             "23:1: " + getCheckMessage(MSG_LEX, "java.util.concurrent.*",
212                     "javax.swing.WindowConstants.*"),
213             "26:1: " + getCheckMessage(MSG_LEX, "com.google.errorprone.annotations.*",
214                     "com.google.errorprone.annotations.concurrent.*"),
215             "28:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "com.google.common.base.*"),
216             "28:1: " + getCheckMessage(MSG_LEX, "com.google.common.base.*",
217                     "com.google.errorprone.annotations.concurrent.*"),
218         };
219 
220         verifyWithInlineConfigParser(
221                 getPath("InputCustomImportOrderDefault2.java"), expected);
222     }
223 
224     @Test
225     public void testStaticSamePackage() throws Exception {
226         final String[] expected = {
227             "17:1: " + getCheckMessage(MSG_LEX, "java.util.*", "java.util.StringTokenizer"),
228             "18:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.concurrent.*"),
229             "19:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC, "java.awt.Button.ABORT"),
230             "20:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC,
231                     "javax.swing.WindowConstants.*"),
232             "21:1: " + getCheckMessage(MSG_LEX, "com.puppycrawl.tools.*",
233                     "java.util.StringTokenizer"),
234             "22:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
235                     "java.util.concurrent.AbstractExecutorService"),
236             "23:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC,
237                     "java.io.File.createTempFile"),
238             "24:1: " + getCheckMessage(MSG_LEX, "com.*", "java.util.StringTokenizer"),
239         };
240 
241         verifyWithInlineConfigParser(
242                 getNonCompilablePath("InputCustomImportOrderSamePackage.java"),
243             expected);
244     }
245 
246     @Test
247     public void testWithoutLineSeparator() throws Exception {
248         final String[] expected = {
249             "17:1: " + getCheckMessage(MSG_LEX, "java.util.*", "java.util.StringTokenizer"),
250             "18:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.concurrent.*"),
251             "19:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC, "java.awt.Button.ABORT"),
252             "20:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC,
253                     "javax.swing.WindowConstants.*"),
254             "21:1: " + getCheckMessage(MSG_LEX, "com.puppycrawl.tools.*",
255                     "java.util.StringTokenizer"),
256             "22:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
257                     "java.util.concurrent.AbstractExecutorService"),
258             "23:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC,
259                     "java.io.File.createTempFile"),
260             "24:1: " + getCheckMessage(MSG_LEX, "com.*", "java.util.StringTokenizer"),
261         };
262 
263         verifyWithInlineConfigParser(
264                 getNonCompilablePath("InputCustomImportOrderSamePackage2.java"),
265             expected);
266     }
267 
268     @Test
269     public void testWithoutLineSeparator2() throws Exception {
270         final String[] expected = {
271             "16:1: " + getCheckMessage(MSG_LEX, "java.io.File.createTempFile",
272                 "javax.swing.WindowConstants.*"),
273             "20:1: " + getCheckMessage(MSG_LEX, "java.util.concurrent.locks.*",
274                 "java.util.concurrent.locks.AbstractOwnableSynchronizer.*"),
275         };
276 
277         verifyWithInlineConfigParser(
278                 getPath("InputCustomImportOrder_NoSeparator.java"), expected);
279     }
280 
281     @Test
282     public void testNoValid() throws Exception {
283         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
284 
285         verifyWithInlineConfigParser(
286                 getPath("InputCustomImportOrderNoValid.java"), expected);
287     }
288 
289     @Test
290     public void testPossibleIndexOutOfBoundsException() throws Exception {
291         final String[] expected = {
292             "17:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, THIRD, "org.w3c.dom.Node"),
293         };
294 
295         verifyWithInlineConfigParser(
296                 getPath("InputCustomImportOrderPossibleIndexOutOfBoundsException.java"), expected);
297     }
298 
299     @Test
300     public void testDefaultPackage2() throws Exception {
301 
302         final String[] expected = {
303             "19:1: " + getCheckMessage(MSG_LEX, "java.awt.Button.ABORT",
304                     "java.io.File.createTempFile"),
305             "22:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.Button"),
306             "23:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.Frame"),
307             "24:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.Dialog"),
308             "25:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.awt.event.ActionEvent"),
309             "26:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "javax.swing.JComponent"),
310             "27:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "javax.swing.JTable"),
311             "28:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.File"),
312             "29:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.IOException"),
313             "30:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.InputStream"),
314             "31:1: " + getCheckMessage(MSG_ORDER, STD, THIRD, "java.io.Reader"),
315             "35:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "com.google.common.*"),
316             "35:1: " + getCheckMessage(MSG_LEX, "com.google.common.*", "com.puppycrawl.tools.*"),
317         };
318 
319         verifyWithInlineConfigParser(
320                 getNonCompilablePath("InputCustomImportOrderDefaultPackage.java"),
321             expected);
322     }
323 
324     @Test
325     public void testWithoutThirdPartyPackage() throws Exception {
326         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
327 
328         verifyWithInlineConfigParser(
329                 getNonCompilablePath("InputCustomImportOrderThirdPartyPackage.java"), expected);
330     }
331 
332     @Test
333     public void testThirdPartyAndSpecialImports() throws Exception {
334         final String[] expected = {
335             "23:1: " + getCheckMessage(MSG_ORDER, THIRD, SPECIAL,
336                 "com.google.common.collect.HashMultimap"),
337         };
338 
339         verifyWithInlineConfigParser(
340                 getNonCompilablePath("InputCustomImportOrderThirdPartyAndSpecial.java"), expected);
341     }
342 
343     @Test
344     public void testCompareImports() throws Exception {
345         final String[] expected = {
346             "16:1: " + getCheckMessage(MSG_LEX, "java.util.Map",
347                 "java.util.Map.Entry"),
348         };
349 
350         verifyWithInlineConfigParser(
351                 getPath("InputCustomImportOrderCompareImports.java"), expected);
352     }
353 
354     @Test
355     public void testFindBetterPatternMatch() throws Exception {
356         final String[] expected = {
357             "20:1: " + getCheckMessage(MSG_ORDER, THIRD, SPECIAL,
358                 "com.google.common.annotations.Beta"),
359         };
360 
361         verifyWithInlineConfigParser(
362                 getPath("InputCustomImportOrderFindBetterPatternMatch.java"), expected);
363     }
364 
365     @Test
366     public void testBeginTreeClear() throws Exception {
367         final DefaultConfiguration checkConfig =
368             createModuleConfig(CustomImportOrderCheck.class);
369         checkConfig.addProperty("specialImportsRegExp", "com");
370         checkConfig.addProperty("separateLineBetweenGroups", "false");
371         checkConfig.addProperty("customImportOrderRules",
372             "STANDARD_JAVA_PACKAGE###SPECIAL_IMPORTS");
373         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
374         final Checker checker = createChecker(checkConfig);
375         final String fileName1 = getPath("InputCustomImportOrderImportsContainingJava.java");
376         final String fileName2 = getPath("InputCustomImportOrderNoValid.java");
377         final File[] files = {
378             new File(fileName1),
379             new File(fileName2),
380         };
381         verify(checker, files, fileName1, expected);
382     }
383 
384     @Test
385     public void testImportsContainingJava() throws Exception {
386         final String[] expected = {
387             "17:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
388                     "com.google.errorprone.annotations.*"),
389         };
390 
391         verifyWithInlineConfigParser(
392                 getPath("InputCustomImportOrderImportsContainingJava.java"), expected);
393     }
394 
395     @Test
396     public void testGetAcceptableTokens() {
397         final CustomImportOrderCheck testCheckObject =
398                 new CustomImportOrderCheck();
399         final int[] actual = testCheckObject.getAcceptableTokens();
400         final int[] expected = {
401             TokenTypes.IMPORT,
402             TokenTypes.STATIC_IMPORT,
403             TokenTypes.PACKAGE_DEF,
404         };
405 
406         assertWithMessage("Default acceptable tokens are invalid")
407             .that(actual)
408             .isEqualTo(expected);
409     }
410 
411     @Test
412     // UT uses Reflection to avoid removing null-validation from static method,
413     // which is a candidate for utility method in the future
414     public void testGetFullImportIdent() throws Exception {
415         final Class<?> clazz = CustomImportOrderCheck.class;
416         final Object t = TestUtil.instantiate(clazz);
417         final Object actual = TestUtil.invokeMethod(t, "getFullImportIdent",
418                 Object.class, (Object) null);
419 
420         final String expected = "";
421         assertWithMessage("Invalid getFullImportIdent result")
422             .that(actual)
423             .isEqualTo(expected);
424     }
425 
426     @Test
427     public void testSamePackageDepth2() throws Exception {
428         final String[] expected = {
429             "20:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.*"),
430             "21:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.List"),
431             "22:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.StringTokenizer"),
432             "23:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.concurrent.*"),
433             "24:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
434                     "java.util.concurrent.AbstractExecutorService"),
435             "25:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
436                     "java.util.concurrent.locks.LockSupport"),
437             "26:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.regex.Pattern"),
438             "27:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.regex.Matcher"),
439         };
440 
441         verifyWithInlineConfigParser(
442                 getNonCompilablePath("InputCustomImportOrderSamePackageDepth25.java"),
443             expected);
444     }
445 
446     @Test
447     public void testSamePackageDepth3() throws Exception {
448         final String[] expected = {
449             "23:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME, "java.util.concurrent.*"),
450             "24:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
451                 "java.util.concurrent.AbstractExecutorService"),
452             "25:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
453                 "java.util.concurrent.locks.LockSupport"),
454             };
455 
456         verifyWithInlineConfigParser(
457                 getNonCompilablePath("InputCustomImportOrderSamePackageDepth252.java"),
458             expected);
459     }
460 
461     @Test
462     public void testSamePackageDepth4() throws Exception {
463         final String[] expected = {
464             "25:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SAME,
465                 "java.util.concurrent.locks.LockSupport"),
466             };
467 
468         verifyWithInlineConfigParser(
469                 getNonCompilablePath("InputCustomImportOrderSamePackageDepth253.java"),
470             expected);
471     }
472 
473     @Test
474     public void testSamePackageDepthLongerThenActualPackage() throws Exception {
475         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
476 
477         verifyWithInlineConfigParser(
478                 getNonCompilablePath("InputCustomImportOrderSamePackageDepth254.java"),
479                 expected);
480     }
481 
482     @Test
483     public void testSamePackageDepthNegative() {
484 
485         final CheckstyleException exc =
486                 getExpectedThrowable(CheckstyleException.class, () -> {
487                     final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
488                     verifyWithInlineConfigParser(
489                             getPath("InputCustomImportOrderDefault5.java"), expected);
490                 }, "exception expected");
491         assertWithMessage("Invalid exception message")
492             .that(exc)
493             .hasMessageThat()
494             .isEqualTo("cannot initialize module com.puppycrawl.tools.checkstyle.TreeWalker - "
495                     + "cannot initialize module com.puppycrawl.tools.checkstyle.checks"
496                     + ".imports.CustomImportOrderCheck");
497         assertWithMessage("Invalid exception message")
498             .that(exc.getCause().getCause().getCause().getCause().getMessage())
499             .isEqualTo("SAME_PACKAGE rule parameter should be positive integer: "
500                     + "SAME_PACKAGE(-1)");
501     }
502 
503     @Test
504     public void testSamePackageDepthZero() {
505         final CheckstyleException exc =
506                 getExpectedThrowable(CheckstyleException.class, () -> {
507                     final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
508                     verifyWithInlineConfigParser(
509                             getPath("InputCustomImportOrderDefault6.java"), expected);
510                 }, "exception expected");
511         assertWithMessage("Invalid exception message")
512             .that(exc.getMessage())
513             .isEqualTo("cannot initialize module com.puppycrawl.tools.checkstyle.TreeWalker - "
514                     + "cannot initialize module com.puppycrawl.tools.checkstyle.checks"
515                     + ".imports.CustomImportOrderCheck");
516         assertWithMessage("Invalid exception message")
517             .that(exc.getCause().getCause().getCause().getCause().getMessage())
518             .isEqualTo("SAME_PACKAGE rule parameter should be positive integer: "
519                     + "SAME_PACKAGE(0)");
520     }
521 
522     @Test
523     public void testUnsupportedRule() {
524         final CheckstyleException exc =
525                 getExpectedThrowable(CheckstyleException.class, () -> {
526                     final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
527                     verifyWithInlineConfigParser(
528                             getPath("InputCustomImportOrderDefault7.java"), expected);
529                 }, "exception expected");
530         assertWithMessage("Invalid exception message")
531             .that(exc.getMessage())
532             .isEqualTo("cannot initialize module com.puppycrawl.tools.checkstyle.TreeWalker - "
533                     + "cannot initialize module com.puppycrawl.tools.checkstyle.checks"
534                     + ".imports.CustomImportOrderCheck");
535         assertWithMessage("Invalid exception message")
536             .that(exc.getCause().getCause().getCause().getCause().getMessage())
537             .isEqualTo("Unexpected rule: UNSUPPORTED_RULE");
538     }
539 
540     @Test
541     public void testSamePackageDepthNotInt() {
542         final CheckstyleException exc =
543                 getExpectedThrowable(CheckstyleException.class, () -> {
544                     final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
545                     verifyWithInlineConfigParser(
546                             getPath("InputCustomImportOrderDefault8.java"), expected);
547                 }, "exception expected");
548         assertWithMessage("Invalid exception message")
549             .that(exc.getMessage())
550             .isEqualTo("cannot initialize module com.puppycrawl.tools.checkstyle.TreeWalker - "
551                     + "cannot initialize module com.puppycrawl.tools.checkstyle.checks"
552                     + ".imports.CustomImportOrderCheck");
553         assertWithMessage("Invalid exception message")
554             .that(exc.getCause().getCause().getCause().getCause().getMessage())
555             .isEqualTo("For input string: \"INT_IS_REQUIRED_HERE\"");
556     }
557 
558     @Test
559     public void testNoImports() throws Exception {
560         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
561 
562         verifyWithInlineConfigParser(
563                 getPath("InputCustomImportOrder_NoImports.java"), expected);
564     }
565 
566     @Test
567     public void testDefaultConfiguration() throws Exception {
568         final String[] expected = {
569             "20:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.awt.Button"),
570             "32:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.io.*"),
571             "34:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "com.google.common.collect.*"),
572         };
573         verifyWithInlineConfigParser(
574                 getPath("InputCustomImportOrderDefault9.java"), expected);
575     }
576 
577     @Test
578     public void testRulesWithOverlappingPatterns() throws Exception {
579         final String[] expected = {
580             "23:1: " + getCheckMessage(MSG_ORDER, THIRD, STD,
581                 "com.puppycrawl.tools.checkstyle.checks.javadoc.JavadocNodeImpl"),
582             "27:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
583                 "com.puppycrawl.tools.checkstyle.checks.javadoc.AbstractJavadocCheck"),
584             "33:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
585                 "com.puppycrawl.tools.checkstyle.checks.javadoc.InvalidJavadocTag"),
586             "35:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD,
587                 "com.puppycrawl.tools.checkstyle.checks.javadoc.WriteTagCheck"),
588             "39:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SPECIAL,
589                 "com.puppycrawl.tools.checkstyle.checks.javadoc.JavadocTag"),
590             "40:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD,
591                 "com.puppycrawl.tools.checkstyle.checks.javadoc.JavadocMethodCheck"),
592             "41:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD,
593                 "com.puppycrawl.tools.checkstyle.checks.javadoc.NonEmptyAtclauseDescriptionCheck"),
594             };
595 
596         verifyWithInlineConfigParser(
597                 getPath("InputCustomImportOrder_OverlappingPatterns.java"), expected);
598     }
599 
600     @Test
601     public void testMultiplePatternMatchesSecondPatternIsLonger() throws Exception {
602         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
603         verifyWithInlineConfigParser(
604                 getPath("InputCustomImportOrder_MultiplePatternMatches.java"),
605             expected);
606     }
607 
608     @Test
609     public void testMultiplePatternMatchesFirstPatternHasLaterPosition() throws Exception {
610         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
611         verifyWithInlineConfigParser(
612                 getPath("InputCustomImportOrder_MultiplePatternMatches2.java"),
613             expected);
614     }
615 
616     @Test
617     public void testMultiplePatternMatchesFirstPatternHasEarlierPosition() throws Exception {
618         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
619         verifyWithInlineConfigParser(
620                 getPath("InputCustomImportOrder_MultiplePatternMatches3.java"),
621             expected);
622     }
623 
624     @Test
625     public void testMultiplePatternMultipleImportFirstPatternHasLaterPosition() throws Exception {
626         final String[] expected = {
627             "16:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD, "org.junit.Test"),
628         };
629         verifyWithInlineConfigParser(
630                 getPath("InputCustomImportOrder_MultiplePatternMultipleImport.java"),
631             expected);
632     }
633 
634     @Test
635     public void testNoPackage() throws Exception {
636         final String[] expected = {
637             "17:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.*"),
638             "19:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.HashMap"),
639             "23:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "javax.net.ServerSocketFactory"),
640             "26:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "javax.net.SocketFactory"),
641         };
642         verifyWithInlineConfigParser(
643                 getNonCompilablePath("InputCustomImportOrderNoPackage.java"),
644             expected);
645     }
646 
647     @Test
648     public void testNoPackage2() throws Exception {
649         final String[] expected = {
650             "18:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
651                 "com.sun.accessibility.internal.resources.*"),
652             "22:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.Arrays"),
653             "30:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
654                 "org.apache.commons.beanutils.converters.ArrayConverter"),
655         };
656         verifyWithInlineConfigParser(
657                 getNonCompilablePath("InputCustomImportOrderNoPackage2.java"),
658             expected);
659     }
660 
661     @Test
662     public void testNoPackage3() throws Exception {
663         final String[] expected = {
664             "17:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
665                 "java.util.Map"),
666             "25:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
667                 "org.apache.*"),
668             "29:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
669                 "antlr.*"),
670         };
671         verifyWithInlineConfigParser(
672                 getNonCompilablePath("InputCustomImportOrderNoPackage3.java"),
673             expected);
674     }
675 
676     @Test
677     public void testInputCustomImportOrderSingleLine() throws Exception {
678         final String[] expected = {
679             "14:112: " + getCheckMessage(MSG_LINE_SEPARATOR,
680                 "java.util.Map"),
681             "15:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
682                 "com.google.common.annotations.Beta"),
683             "22:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
684                 "com.puppycrawl.tools.checkstyle.*"),
685             "26:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
686                 "picocli.*"),
687         };
688         verifyWithInlineConfigParser(
689                 getPath("InputCustomImportOrderSingleLine.java"),
690             expected);
691     }
692 
693     @Test
694     public void testInputCustomImportOrderSingleLine2() throws Exception {
695         final String[] expected = {
696             "14:118: " + getCheckMessage(MSG_LINE_SEPARATOR,
697                 "java.util.Map"),
698         };
699         verifyWithInlineConfigParser(
700                 getNonCompilablePath("InputCustomImportOrderSingleLine2.java"),
701             expected);
702     }
703 
704     @Test
705     public void testInputCustomImportOrderThirdPartyAndSpecial2() throws Exception {
706         final String[] expected = {
707             "21:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
708                 "javax.swing.WindowConstants.*"),
709             "24:1: " + getCheckMessage(MSG_LINE_SEPARATOR,
710                 "java.awt.Button"),
711             "28:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
712                 "java.awt.Dialog"),
713             "34:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
714                 "com.google.common.*"),
715             "40:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
716                 "org.apache.commons.collections.*"),
717             "45:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
718                 "com.puppycrawl.tools.checkstyle.checks.imports.AbstractImportRule"),
719             "51:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
720                 "antlr.Token"),
721             "53:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
722                 "antlr.collections.AST"),
723         };
724         verifyWithInlineConfigParser(
725                 getNonCompilablePath("InputCustomImportOrderThirdPartyAndSpecial2.java"), expected);
726     }
727 
728     @Test
729     public void testInputCustomImportOrderMultipleViolationsSameLine() throws Exception {
730         final String[] expected = {
731             "17:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC,
732                 "java.util.Collections.*"),
733             "18:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STATIC,
734                 "java.lang.String.CASE_INSENSITIVE_ORDER"),
735             "21:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP,
736                 "java.net.Socket"),
737             "21:1: " + getCheckMessage(MSG_LEX, "java.net.Socket",
738                 "java.util.*"),
739         };
740         verifyWithInlineConfigParser(
741                 getNonCompilablePath("InputCustomImportOrderViolationsSameLine.java"),
742             expected);
743     }
744 
745     @Test
746     public void testInputCustomImportOrderSpanMultipleLines() throws Exception {
747         final String[] expected = {
748             "30:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.BitSet"),
749             "45:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "java.util.HashSet"),
750             "49:1: " + getCheckMessage(MSG_LINE_SEPARATOR, "org.apache.tools.ant.*"),
751             "54:1: " + getCheckMessage(MSG_LINE_SEPARATOR, "com.puppycrawl.tools.checkstyle.*"),
752             "58:1: " + getCheckMessage(MSG_LINE_SEPARATOR, "picocli.*"),
753             "61:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "picocli.CommandLine"),
754         };
755         verifyWithInlineConfigParser(
756                 getPath("InputCustomImportOrderSpanMultipleLines.java"), expected);
757     }
758 
759     @Test
760     public void testInputCustomImportOrderEclipseDefaultPositive() throws Exception {
761         final String[] expected = {
762             "22:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD, "java.awt.Button"),
763             "23:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD, "java.awt.Dialog"),
764             "24:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, STD, "java.io.InputStream"),
765             "26:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SPECIAL, "javax.swing.JComponent"),
766             "27:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, SPECIAL, "javax.swing.JTable"),
767             "29:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, THIRD, "org.junit.Test"),
768             "30:1: " + getCheckMessage(MSG_NONGROUP_EXPECTED, THIRD,
769                     "org.mockito.Mock"),
770             "34:1: " + getCheckMessage(MSG_SEPARATED_IN_GROUP, "sun.tools.java.ArrayType"),
771         };
772         verifyWithInlineConfigParser(
773                 getNonCompilablePath("InputCustomImportOrderEclipseDefaultPositive.java"),
774                 expected);
775     }
776 
777     @Test
778     public void testInputCustomImportOrderSpecialImportsRegExp() throws Exception {
779         final String[] expected = CommonUtil.EMPTY_STRING_ARRAY;
780         verifyWithInlineConfigParser(
781                 getPath("InputCustomImportOrderSpecialImportsRegExp.java"),
782                 expected);
783     }
784 }