1 24 package org.riotfamily.common.web.util; 25 26 import java.util.regex.Matcher ; 27 import java.util.regex.Pattern ; 28 29 import org.apache.commons.logging.Log; 30 import org.apache.commons.logging.LogFactory; 31 32 39 public final class EmailValidationUtils { 40 41 private static Log log = LogFactory.getLog(EmailValidationUtils.class); 42 43 private static final String SPECIAL_CHARS = "\\(\\)<>@,;:\\\\\\\"\\.\\[\\]"; 44 private static final String VALID_CHARS = "[^\\s" + SPECIAL_CHARS + "]"; 45 private static final String QUOTED_USER = "(\"[^\"]*\")"; 46 private static final String ATOM = VALID_CHARS + '+'; 47 private static final String WORD = "(" + ATOM + "|" + QUOTED_USER + ")"; 48 49 private static final String LEGAL_ASCII_PATTERN = "^[\\x00-\\x7F]+$"; 50 private static final String EMAIL_PATTERN = "^(.+)@(.+)$"; 51 private static final String IP_DOMAIN_PATTERN = 52 "^(\\d{1,3})[.](\\d{1,3})[.](\\d{1,3})[.](\\d{1,3})$"; 53 54 private static final String USER_PATTERN = "^" + WORD + "(\\.|" 55 + WORD + ")*$"; 56 57 private static final String DOMAIN_PATTERN = "^" + ATOM + "(\\." 58 + ATOM + ")*$"; 59 60 private static final String ATOM_PATTERN = "(" + ATOM + ")"; 61 62 private static final String ADDR_PATTERN = "^[^<]*<([^>]*)>\\s*$"; 63 64 65 66 private static Pattern legalAsciiPattern = Pattern.compile(LEGAL_ASCII_PATTERN); 67 private static Pattern emailPattern = Pattern.compile(EMAIL_PATTERN); 68 private static Pattern ipDomainPattern = Pattern.compile(IP_DOMAIN_PATTERN); 69 private static Pattern userPattern = Pattern.compile(USER_PATTERN); 70 private static Pattern domainPattern = Pattern.compile(DOMAIN_PATTERN); 71 private static Pattern atomPattern = Pattern.compile(ATOM_PATTERN); 72 private static Pattern addrPattern = Pattern.compile(ADDR_PATTERN); 73 74 75 private EmailValidationUtils() { 76 } 77 78 84 public static boolean isValid(String email) { 85 if (email == null) { 86 log.debug("Address is null"); 87 return false; 88 } 89 Matcher addrMatcher = addrPattern.matcher(email); 90 if (addrMatcher.matches()) { 91 email = addrMatcher.group(1); 92 log.debug("Extracted machine part from address: " + email); 93 } 94 95 if (!legalAsciiPattern.matcher(email).matches()) { 96 log.debug("Address must only contain ASCII characters"); 97 return false; 98 } 99 100 Matcher emailMatcher = emailPattern.matcher(email); 102 if (!emailMatcher.matches()) { 103 log.debug("Invalid address structure"); 104 return false; 105 } 106 107 if (email.endsWith(".")) { 108 log.debug("Address must not end with a dot"); 109 return false; 110 } 111 112 if (!isValidUser(emailMatcher.group(1))) { 113 log.debug("Invalid user"); 114 return false; 115 } 116 117 if (!isValidDomain(emailMatcher.group(2))) { 118 log.debug("Invalid domain"); 119 return false; 120 } 121 log.debug("Address is valid"); 122 return true; 123 } 124 125 129 private static boolean isValidDomain(String domain) { 130 boolean symbolic = false; 131 132 Matcher ipAddressMatcher = ipDomainPattern.matcher(domain); 133 if (ipAddressMatcher.matches()) { 134 if (!isValidIpAddress(ipAddressMatcher)) { 135 return false; 136 } 137 } 138 else { 139 symbolic = domainPattern.matcher(domain).matches(); 141 } 142 143 if (symbolic) { 144 if (!isValidSymbolicDomain(domain)) { 145 return false; 146 } 147 } 148 else { 149 return false; 150 } 151 152 return true; 153 } 154 155 159 private static boolean isValidUser(String user) { 160 return userPattern.matcher(user).matches(); 161 } 162 163 167 private static boolean isValidIpAddress(Matcher ipAddressMatcher) { 168 for (int i = 1; i <= 4; i++) { 169 String ipSegment = ipAddressMatcher.group(i); 170 if (ipSegment == null || ipSegment.length() <= 0) { 171 return false; 172 } 173 174 int iIpSegment = 0; 175 176 try { 177 iIpSegment = Integer.parseInt(ipSegment); 178 } 179 catch (NumberFormatException e) { 180 return false; 181 } 182 183 if (iIpSegment > 255) { 184 return false; 185 } 186 } 187 return true; 188 } 189 190 194 private static boolean isValidSymbolicDomain(String domain) { 195 String [] domainSegment = new String [10]; 196 boolean match = true; 197 int i = 0; 198 Matcher atomMatcher = atomPattern.matcher(domain); 199 while (match) { 200 match = atomMatcher.find(); 201 if (match) { 202 domainSegment[i] = atomMatcher.group(1); 203 int l = domainSegment[i].length() + 1; 204 domain = 205 (l >= domain.length()) 206 ? "" 207 : domain.substring(l); 208 209 i++; 210 } 211 } 212 213 int len = i; 214 if (domainSegment[len - 1].length() < 2 215 || domainSegment[len - 1].length() > 4) { 216 217 return false; 218 } 219 220 if (len < 2) { 222 return false; 223 } 224 225 return true; 226 } 227 228 } 229 | Popular Tags |