1 /////////////////////////////////////////////////////////////////////////////////////////////// 2 // checkstyle: Checks Java source code and other text files for adherence to a set of rules. 3 // Copyright (C) 2001-2024 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.regexp; 21 22 import com.puppycrawl.tools.checkstyle.PropertyType; 23 import com.puppycrawl.tools.checkstyle.StatelessCheck; 24 import com.puppycrawl.tools.checkstyle.XdocsPropertyType; 25 import com.puppycrawl.tools.checkstyle.api.AbstractCheck; 26 import com.puppycrawl.tools.checkstyle.api.DetailAST; 27 import com.puppycrawl.tools.checkstyle.utils.CommonUtil; 28 29 /** 30 * <p> 31 * Checks that a specified pattern matches a single-line in Java files. 32 * </p> 33 * <p> 34 * This class is variation on 35 * <a href="https://checkstyle.org/checks/regexp/regexpsingleline.html#RegexpSingleline"> 36 * RegexpSingleline</a> 37 * for detecting single-lines that match a supplied regular expression in Java files. 38 * It supports suppressing matches in Java comments. 39 * </p> 40 * <ul> 41 * <li> 42 * Property {@code format} - Specify the format of the regular expression to match. 43 * Type is {@code java.util.regex.Pattern}. 44 * Default value is {@code "$."}. 45 * </li> 46 * <li> 47 * Property {@code ignoreCase} - Control whether to ignore case when searching. 48 * Type is {@code boolean}. 49 * Default value is {@code false}. 50 * </li> 51 * <li> 52 * Property {@code ignoreComments} - Control whether to ignore text in comments when searching. 53 * Type is {@code boolean}. 54 * Default value is {@code false}. 55 * </li> 56 * <li> 57 * Property {@code maximum} - Specify the maximum number of matches required in each file. 58 * Type is {@code int}. 59 * Default value is {@code 0}. 60 * </li> 61 * <li> 62 * Property {@code message} - Specify the message which is used to notify about 63 * violations, if empty then default (hard-coded) message is used. 64 * Type is {@code java.lang.String}. 65 * Default value is {@code null}. 66 * </li> 67 * <li> 68 * Property {@code minimum} - Specify the minimum number of matches required in each file. 69 * Type is {@code int}. 70 * Default value is {@code 0}. 71 * </li> 72 * </ul> 73 * <p> 74 * Parent is {@code com.puppycrawl.tools.checkstyle.TreeWalker} 75 * </p> 76 * <p> 77 * Violation Message Keys: 78 * </p> 79 * <ul> 80 * <li> 81 * {@code regexp.exceeded} 82 * </li> 83 * <li> 84 * {@code regexp.minimum} 85 * </li> 86 * </ul> 87 * 88 * @since 6.0 89 */ 90 @StatelessCheck 91 public class RegexpSinglelineJavaCheck extends AbstractCheck { 92 93 /** Specify the format of the regular expression to match. */ 94 @XdocsPropertyType(PropertyType.PATTERN) 95 private String format = "$."; 96 /** 97 * Specify the message which is used to notify about violations, 98 * if empty then default (hard-coded) message is used. 99 */ 100 private String message; 101 /** Specify the minimum number of matches required in each file. */ 102 private int minimum; 103 /** Specify the maximum number of matches required in each file. */ 104 private int maximum; 105 /** Control whether to ignore case when searching. */ 106 private boolean ignoreCase; 107 /** Control whether to ignore text in comments when searching. */ 108 private boolean ignoreComments; 109 110 @Override 111 public int[] getDefaultTokens() { 112 return getRequiredTokens(); 113 } 114 115 @Override 116 public int[] getAcceptableTokens() { 117 return getRequiredTokens(); 118 } 119 120 @Override 121 public int[] getRequiredTokens() { 122 return CommonUtil.EMPTY_INT_ARRAY; 123 } 124 125 // suppress deprecation until https://github.com/checkstyle/checkstyle/issues/11166 126 @SuppressWarnings("deprecation") 127 @Override 128 public void beginTree(DetailAST rootAST) { 129 MatchSuppressor suppressor = null; 130 if (ignoreComments) { 131 suppressor = new CommentSuppressor(getFileContents()); 132 } 133 134 final DetectorOptions options = DetectorOptions.newBuilder() 135 .reporter(this) 136 .suppressor(suppressor) 137 .format(format) 138 .message(message) 139 .minimum(minimum) 140 .maximum(maximum) 141 .ignoreCase(ignoreCase) 142 .build(); 143 final SinglelineDetector detector = new SinglelineDetector(options); 144 detector.processLines(getFileContents().getText()); 145 } 146 147 /** 148 * Setter to specify the format of the regular expression to match. 149 * 150 * @param format the format of the regular expression to match. 151 * @since 5.0 152 */ 153 public void setFormat(String format) { 154 this.format = format; 155 } 156 157 /** 158 * Setter to specify the message which is used to notify about violations, 159 * if empty then default (hard-coded) message is used. 160 * 161 * @param message the message to report for a match. 162 * @since 6.0 163 */ 164 public void setMessage(String message) { 165 this.message = message; 166 } 167 168 /** 169 * Setter to specify the minimum number of matches required in each file. 170 * 171 * @param minimum the minimum number of matches required in each file. 172 * @since 5.0 173 */ 174 public void setMinimum(int minimum) { 175 this.minimum = minimum; 176 } 177 178 /** 179 * Setter to specify the maximum number of matches required in each file. 180 * 181 * @param maximum the maximum number of matches required in each file. 182 * @since 5.0 183 */ 184 public void setMaximum(int maximum) { 185 this.maximum = maximum; 186 } 187 188 /** 189 * Setter to control whether to ignore case when searching. 190 * 191 * @param ignoreCase whether to ignore case when searching. 192 * @since 5.0 193 */ 194 public void setIgnoreCase(boolean ignoreCase) { 195 this.ignoreCase = ignoreCase; 196 } 197 198 /** 199 * Setter to control whether to ignore text in comments when searching. 200 * 201 * @param ignore whether to ignore text in comments when searching. 202 * @since 5.0 203 */ 204 public void setIgnoreComments(boolean ignore) { 205 ignoreComments = ignore; 206 } 207 208 }