001//////////////////////////////////////////////////////////////////////////////// 002// checkstyle: Checks Java source code for adherence to a set of rules. 003// Copyright (C) 2001-2015 the original author or authors. 004// 005// This library is free software; you can redistribute it and/or 006// modify it under the terms of the GNU Lesser General Public 007// License as published by the Free Software Foundation; either 008// version 2.1 of the License, or (at your option) any later version. 009// 010// This library is distributed in the hope that it will be useful, 011// but WITHOUT ANY WARRANTY; without even the implied warranty of 012// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 013// Lesser General Public License for more details. 014// 015// You should have received a copy of the GNU Lesser General Public 016// License along with this library; if not, write to the Free Software 017// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 018//////////////////////////////////////////////////////////////////////////////// 019 020package com.puppycrawl.tools.checkstyle.checks.coding; 021 022import java.util.regex.Pattern; 023 024import org.apache.commons.lang3.ArrayUtils; 025 026import com.puppycrawl.tools.checkstyle.api.DetailAST; 027import com.puppycrawl.tools.checkstyle.checks.AbstractFormatCheck; 028import com.puppycrawl.tools.checkstyle.utils.TokenUtils; 029 030/** 031 * <p> 032 * Checks for illegal token text. 033 * </p> 034 * <p> An example of how to configure the check to forbid String literals 035 * containing {@code "a href"} is: 036 * </p> 037 * <pre> 038 * <module name="IllegalTokenText"> 039 * <property name="tokens" value="STRING_LITERAL"/> 040 * <property name="format" value="a href"/> 041 * </module> 042 * </pre> 043 * <p> An example of how to configure the check to forbid leading zeros in an 044 * integer literal, other than zero and a hex literal is: 045 * </p> 046 * <pre> 047 * <module name="IllegalTokenText"> 048 * <property name="tokens" value="NUM_INT,NUM_LONG"/> 049 * <property name="format" value="^0[^lx]"/> 050 * <property name="ignoreCase" value="true"/> 051 * </module> 052 * </pre> 053 * @author Rick Giles 054 */ 055public class IllegalTokenTextCheck 056 extends AbstractFormatCheck { 057 058 /** 059 * A key is pointing to the warning message text in "messages.properties" 060 * file. 061 */ 062 public static final String MSG_KEY = "illegal.token.text"; 063 064 /** 065 * Custom message for report if illegal regexp found 066 * ignored if empty. 067 */ 068 private String message = ""; 069 070 /** 071 * Instantiates a new instance. 072 */ 073 public IllegalTokenTextCheck() { 074 // the empty language 075 super("$^"); 076 } 077 078 @Override 079 public int[] getDefaultTokens() { 080 return ArrayUtils.EMPTY_INT_ARRAY; 081 } 082 083 @Override 084 public int[] getAcceptableTokens() { 085 return TokenUtils.getAllTokenIds(); 086 } 087 088 @Override 089 public int[] getRequiredTokens() { 090 return ArrayUtils.EMPTY_INT_ARRAY; 091 } 092 093 @Override 094 public void visitToken(DetailAST ast) { 095 final String text = ast.getText(); 096 if (getRegexp().matcher(text).find()) { 097 String customMessage = message; 098 if (customMessage.isEmpty()) { 099 customMessage = MSG_KEY; 100 } 101 log( 102 ast.getLineNo(), 103 ast.getColumnNo(), 104 customMessage, 105 getFormat()); 106 } 107 } 108 109 /** 110 * Setter for message property. 111 * @param message custom message which should be used 112 * to report about violations. 113 */ 114 public void setMessage(String message) { 115 if (message == null) { 116 this.message = ""; 117 } 118 else { 119 this.message = message; 120 } 121 } 122 123 /** 124 * Set whether or not the match is case sensitive. 125 * @param caseInsensitive true if the match is case insensitive. 126 */ 127 public void setIgnoreCase(boolean caseInsensitive) { 128 if (caseInsensitive) { 129 setCompileFlags(Pattern.CASE_INSENSITIVE); 130 } 131 } 132}