1
2
3
4
5 package com.qulice.checkstyle;
6
7 import com.puppycrawl.tools.checkstyle.api.AbstractCheck;
8 import com.puppycrawl.tools.checkstyle.api.DetailAST;
9 import com.puppycrawl.tools.checkstyle.api.TokenTypes;
10 import java.util.regex.Matcher;
11 import java.util.regex.Pattern;
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30 public final class UnnecessaryJavaLangCheck extends AbstractCheck {
31
32
33
34
35
36
37 private static final Pattern PREFIX =
38 Pattern.compile("\\bjava\\.lang\\.[A-Z]");
39
40
41
42
43
44 private char[][] lines;
45
46
47
48
49 public UnnecessaryJavaLangCheck() {
50
51 }
52
53 @Override
54 public int[] getDefaultTokens() {
55 return new int[] {
56 TokenTypes.STRING_LITERAL,
57 TokenTypes.TEXT_BLOCK_CONTENT,
58 };
59 }
60
61 @Override
62 public int[] getAcceptableTokens() {
63 return this.getDefaultTokens();
64 }
65
66 @Override
67 public int[] getRequiredTokens() {
68 return new int[0];
69 }
70
71 @Override
72 public void beginTree(final DetailAST root) {
73 final String[] source = this.getLines();
74 this.lines = new char[source.length][];
75 for (int pos = 0; pos < source.length; ++pos) {
76 this.lines[pos] = source[pos].toCharArray();
77 }
78 }
79
80 @Override
81 public void visitToken(final DetailAST ast) {
82 if (ast.getType() == TokenTypes.STRING_LITERAL) {
83 this.blank(
84 ast.getLineNo(), ast.getColumnNo(), ast.getText().length()
85 );
86 } else {
87 this.blankBlock(ast);
88 }
89 }
90
91 @Override
92 public void finishTree(final DetailAST root) {
93 for (int pos = 0; pos < this.lines.length; ++pos) {
94 final Matcher matcher =
95 UnnecessaryJavaLangCheck.PREFIX.matcher(
96 String.valueOf(this.lines[pos])
97 );
98 while (matcher.find()) {
99 this.log(
100 pos + 1,
101 "Unnecessary java.lang. prefix, use the simple class name"
102 );
103 }
104 }
105 }
106
107 private void blankBlock(final DetailAST ast) {
108 final String text = ast.getText();
109 int span = 0;
110 for (int pos = 0; pos < text.length(); ++pos) {
111 if (text.charAt(pos) == '\n') {
112 ++span;
113 }
114 }
115 final int first = ast.getLineNo();
116 for (int line = first; line <= first + span; ++line) {
117 final int index = line - 1;
118 if (index >= 0 && index < this.lines.length) {
119 this.blank(line, 0, this.lines[index].length);
120 }
121 }
122 }
123
124 private void blank(final int line, final int column, final int length) {
125 final int index = line - 1;
126 if (index >= 0 && index < this.lines.length) {
127 final char[] chars = this.lines[index];
128 final int from = Math.max(0, Math.min(column, chars.length));
129 final int upto = Math.min(column + length, chars.length);
130 for (int pos = from; pos < upto; ++pos) {
131 chars[pos] = ' ';
132 }
133 }
134 }
135 }