public SPF1Record parse(String spfRecord) throws PermErrorException,
NoneException, NeutralException {
log.debug("Start parsing SPF-Record: " + spfRecord);
SPF1Record result = new SPF1Record();
// check the version "header"
if (spfRecord.toLowerCase().startsWith(SPF1Constants.SPF_VERSION1 + " ") || spfRecord.equalsIgnoreCase(SPF1Constants.SPF_VERSION1)) {
if (!spfRecord.toLowerCase().startsWith(SPF1Constants.SPF_VERSION1 + " ")) throw new NeutralException("Empty SPF Record");
} else {
throw new NoneException("No valid SPF Record: " + spfRecord);
}
// extract terms
String[] terms = termsSeparatorPattern.split(spfRecord.replaceFirst(
SPF1Constants.SPF_VERSION1, ""));
// cycle terms
for (int i = 0; i < terms.length; i++) {
if (terms[i].length() > 0) {
Matcher termMatcher = termPattern.matcher(terms[i]);
if (!termMatcher.matches()) {
throw new PermErrorException("Term [" + terms[i]
+ "] is not syntactically valid: "
+ termPattern.pattern());
}
// true if we matched a modifier, false if we matched a
// directive
String modifierString = termMatcher
.group(TERM_STEP_REGEX_MODIFIER_POS);
if (modifierString != null) {
// MODIFIER
Modifier mod = (Modifier) lookupAndCreateTerm(termMatcher,
TERM_STEP_REGEX_MODIFIER_POS);
if (mod.enforceSingleInstance()) {
Iterator it = result.getModifiers().iterator();
while (it.hasNext()) {
if (it.next().getClass().equals(mod.getClass())) {
throw new PermErrorException("More than one "
+ modifierString
+ " found in SPF-Record");
}
}
}
result.getModifiers().add(mod);
} else {
// DIRECTIVE
String qualifier = termMatcher
.group(TERM_STEP_REGEX_QUALIFIER_POS);
Object mech = lookupAndCreateTerm(termMatcher,
TERM_STEP_REGEX_MECHANISM_POS);
result.getDirectives().add(
new Directive(qualifier, (Mechanism) mech, log.getChildLogger(qualifier+"directive")));
}
}