1 //////////////////////////////////////////////////////////////////////////////// 2 // checkstyle: Checks Java source code for adherence to a set of rules. 3 // Copyright (C) 2001-2019 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 java.util.Optional; 23 import java.util.regex.Pattern; 24 25 import com.puppycrawl.tools.checkstyle.api.AbstractViolationReporter; 26 27 /** 28 * Options for a detector. 29 */ 30 public final class DetectorOptions { 31 32 /** 33 * Flags to compile a regular expression with. 34 * See {@link Pattern#flags()}. 35 */ 36 private int compileFlags; 37 /** Used for reporting violations. */ 38 private AbstractViolationReporter reporter; 39 /** 40 * Format of the regular expression to check for. 41 */ 42 private String format; 43 /** The message to report on detection. If blank, then use the format. */ 44 private String message = ""; 45 /** Minimum number of times regular expression should occur in a file. */ 46 private int minimum; 47 /** Maximum number of times regular expression should occur in a file. */ 48 private int maximum; 49 /** Whether to ignore case when matching. */ 50 private boolean ignoreCase; 51 /** Used to determine whether to suppress a detected match. */ 52 private MatchSuppressor suppressor; 53 /** Pattern created from format. Lazily initialized. */ 54 private Pattern pattern; 55 56 /** Default constructor.*/ 57 private DetectorOptions() { 58 } 59 60 /** 61 * Returns new Builder object. 62 * @return Builder object. 63 */ 64 public static Builder newBuilder() { 65 return new DetectorOptions().new Builder(); 66 } 67 68 /** 69 * Format of the regular expression. 70 * @return format of the regular expression. 71 */ 72 public String getFormat() { 73 return format; 74 } 75 76 /** 77 * The violation reporter to use. 78 * @return the violation reporter to use. 79 */ 80 public AbstractViolationReporter getReporter() { 81 return reporter; 82 } 83 84 /** 85 * The message to report errors with. 86 * @return the message to report errors with. 87 */ 88 public String getMessage() { 89 return message; 90 } 91 92 /** 93 * The minimum number of allowed detections. 94 * @return the minimum number of allowed detections. 95 */ 96 public int getMinimum() { 97 return minimum; 98 } 99 100 /** 101 * The maximum number of allowed detections. 102 * @return the maximum number of allowed detections. 103 */ 104 public int getMaximum() { 105 return maximum; 106 } 107 108 /** 109 * The suppressor to use. 110 * @return the suppressor to use. 111 */ 112 public MatchSuppressor getSuppressor() { 113 return suppressor; 114 } 115 116 /** 117 * The pattern to use when matching. 118 * @return the pattern to use when matching. 119 */ 120 public Pattern getPattern() { 121 if (pattern == null) { 122 int options = compileFlags; 123 124 if (ignoreCase) { 125 options |= Pattern.CASE_INSENSITIVE; 126 } 127 pattern = Pattern.compile(format, options); 128 } 129 return pattern; 130 } 131 132 /** Class which implements Builder pattern to build DetectorOptions instance. */ 133 public final class Builder { 134 135 /** 136 * Specifies the violation reporter and returns Builder object. 137 * @param val for reporting violations. 138 * @return Builder object. 139 * @noinspection ReturnOfInnerClass 140 */ 141 public Builder reporter(AbstractViolationReporter val) { 142 reporter = val; 143 return this; 144 } 145 146 /** 147 * Specifies the compile flags to compile a regular expression with 148 * and returns Builder object. 149 * @param val the format to use when matching lines. 150 * @return Builder object. 151 * @noinspection ReturnOfInnerClass 152 */ 153 public Builder compileFlags(int val) { 154 compileFlags = val; 155 return this; 156 } 157 158 /** 159 * Specifies the format to use when matching lines and returns Builder object. 160 * @param val the format to use when matching lines. 161 * @return Builder object. 162 * @noinspection ReturnOfInnerClass 163 */ 164 public Builder format(String val) { 165 format = val; 166 return this; 167 } 168 169 /** 170 * Specifies message to use when reporting a match and returns Builder object. 171 * @param val message to use when reporting a match. 172 * @return Builder object. 173 * @noinspection ReturnOfInnerClass 174 */ 175 public Builder message(String val) { 176 message = val; 177 return this; 178 } 179 180 /** 181 * Specifies the minimum allowed number of detections and returns Builder object. 182 * @param val the minimum allowed number of detections. 183 * @return Builder object. 184 * @noinspection ReturnOfInnerClass 185 */ 186 public Builder minimum(int val) { 187 minimum = val; 188 return this; 189 } 190 191 /** 192 * Specifies the maximum allowed number of detections and returns Builder object. 193 * @param val the maximum allowed number of detections. 194 * @return Builder object. 195 * @noinspection ReturnOfInnerClass 196 */ 197 public Builder maximum(int val) { 198 maximum = val; 199 return this; 200 } 201 202 /** 203 * Specifies whether to ignore case when matching and returns Builder object. 204 * @param val whether to ignore case when matching. 205 * @return Builder object. 206 * @noinspection ReturnOfInnerClass, BooleanParameter 207 */ 208 public Builder ignoreCase(boolean val) { 209 ignoreCase = val; 210 return this; 211 } 212 213 /** 214 * Specifies the suppressor to use and returns Builder object. 215 * @param val the suppressor to use. 216 * @return current instance 217 * @noinspection ReturnOfInnerClass 218 */ 219 public Builder suppressor(MatchSuppressor val) { 220 suppressor = val; 221 return this; 222 } 223 224 /** 225 * Returns new DetectorOptions instance. 226 * @return DetectorOptions instance. 227 */ 228 public DetectorOptions build() { 229 message = Optional.ofNullable(message).orElse(""); 230 suppressor = Optional.ofNullable(suppressor).orElse(NeverSuppress.INSTANCE); 231 return DetectorOptions.this; 232 } 233 234 } 235 236 }