X-Git-Url: http://www.aleph1.co.uk/gitweb/?p=yaffs-website;a=blobdiff_plain;f=vendor%2Fegulias%2Femail-validator%2Fsrc%2FEgulias%2FEmailValidator%2FParser%2FDomainPart.php;fp=vendor%2Fegulias%2Femail-validator%2Fsrc%2FEgulias%2FEmailValidator%2FParser%2FDomainPart.php;h=66a51fb4f273bb710f67316cfd8b3440d21d86eb;hp=0000000000000000000000000000000000000000;hb=a2bd1bf0c2c1f1a17d188f4dc0726a45494cefae;hpb=57c063afa3f66b07c4bbddc2d6129a96d90f0aad diff --git a/vendor/egulias/email-validator/src/Egulias/EmailValidator/Parser/DomainPart.php b/vendor/egulias/email-validator/src/Egulias/EmailValidator/Parser/DomainPart.php new file mode 100644 index 000000000..66a51fb4f --- /dev/null +++ b/vendor/egulias/email-validator/src/Egulias/EmailValidator/Parser/DomainPart.php @@ -0,0 +1,339 @@ +lexer->moveNext(); + + if ($this->lexer->token['type'] === EmailLexer::S_DOT) { + throw new \InvalidArgumentException('ERR_DOT_START'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_EMPTY) { + throw new \InvalidArgumentException('ERR_NODOMAIN'); + } + if ($this->lexer->token['type'] === EmailLexer::S_HYPHEN) { + throw new \InvalidArgumentException('ERR_DOMAINHYPHENEND'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_OPENPARENTHESIS) { + $this->warnings[] = EmailValidator::DEPREC_COMMENT; + $this->parseDomainComments(); + } + + $domain = $this->doParseDomainPart(); + + $prev = $this->lexer->getPrevious(); + $length = strlen($domain); + + if ($prev['type'] === EmailLexer::S_DOT) { + throw new \InvalidArgumentException('ERR_DOT_END'); + } + if ($prev['type'] === EmailLexer::S_HYPHEN) { + throw new \InvalidArgumentException('ERR_DOMAINHYPHENEND'); + } + if ($length > self::DOMAIN_MAX_LENGTH) { + $this->warnings[] = EmailValidator::RFC5322_DOMAIN_TOOLONG; + } + if ($prev['type'] === EmailLexer::S_CR) { + throw new \InvalidArgumentException('ERR_FWS_CRLF_END'); + } + $this->domainPart = $domain; + } + + public function getDomainPart() + { + return $this->domainPart; + } + + public function checkIPV6Tag($addressLiteral, $maxGroups = 8) + { + $prev = $this->lexer->getPrevious(); + if ($prev['type'] === EmailLexer::S_COLON) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_COLONEND; + } + + $IPv6 = substr($addressLiteral, 5); + //Daniel Marschall's new IPv6 testing strategy + $matchesIP = explode(':', $IPv6); + $groupCount = count($matchesIP); + $colons = strpos($IPv6, '::'); + + if (count(preg_grep('/^[0-9A-Fa-f]{0,4}$/', $matchesIP, PREG_GREP_INVERT)) !== 0) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_BADCHAR; + } + + if ($colons === false) { + // We need exactly the right number of groups + if ($groupCount !== $maxGroups) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_GRPCOUNT; + } + return; + } + + if ($colons !== strrpos($IPv6, '::')) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_2X2XCOLON; + return; + } + + if ($colons === 0 || $colons === (strlen($IPv6) - 2)) { + // RFC 4291 allows :: at the start or end of an address + //with 7 other groups in addition + ++$maxGroups; + } + + if ($groupCount > $maxGroups) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_MAXGRPS; + } elseif ($groupCount === $maxGroups) { + $this->warnings[] = EmailValidator::RFC5321_IPV6DEPRECATED; + } + } + + protected function doParseDomainPart() + { + $domain = ''; + $openedParenthesis = 0; + $openBrackets = false; + do { + $prev = $this->lexer->getPrevious(); + + $this->checkNotAllowedChars($this->lexer->token); + + if ($this->lexer->token['type'] === EmailLexer::S_OPENPARENTHESIS) { + $this->parseComments(); + $openedParenthesis += $this->getOpenedParenthesis(); + $this->lexer->moveNext(); + $tmpPrev = $this->lexer->getPrevious(); + if ($tmpPrev['type'] === EmailLexer::S_CLOSEPARENTHESIS) { + $openedParenthesis--; + } + } + if ($this->lexer->token['type'] === EmailLexer::S_CLOSEPARENTHESIS) { + if ($openedParenthesis === 0) { + throw new \InvalidArgumentException('ERR_UNOPENEDCOMMENT'); + } else { + $openedParenthesis--; + } + } + + $this->checkConsecutiveDots(); + $this->checkDomainPartExceptions($prev); + + if ($openBrackets = $this->hasBrackets($openBrackets)) { + $this->parseDomainLiteral(); + } + + $this->checkLabelLength($prev); + + if ($this->isFWS()) { + $this->parseFWS(); + } + + $domain .= $this->lexer->token['value']; + $this->lexer->moveNext(); + } while ($this->lexer->token); + + return $domain; + } + + private function checkNotAllowedChars($token) + { + $notAllowed = array(EmailLexer::S_BACKSLASH => true, EmailLexer::S_SLASH=> true); + if (isset($notAllowed[$token['type']])) { + throw new \InvalidArgumentException('ERR_DOMAIN_CHAR_NOT_ALLOWED'); + } + } + + protected function parseDomainLiteral() + { + if ($this->lexer->isNextToken(EmailLexer::S_COLON)) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_COLONSTRT; + } + if ($this->lexer->isNextToken(EmailLexer::S_IPV6TAG)) { + $lexer = clone $this->lexer; + $lexer->moveNext(); + if ($lexer->isNextToken(EmailLexer::S_DOUBLECOLON)) { + $this->warnings[] = EmailValidator::RFC5322_IPV6_COLONSTRT; + } + } + + return $this->doParseDomainLiteral(); + } + + protected function doParseDomainLiteral() + { + $IPv6TAG = false; + $addressLiteral = ''; + do { + if ($this->lexer->token['type'] === EmailLexer::C_NUL) { + throw new \InvalidArgumentException('ERR_EXPECTING_DTEXT'); + } + + if ($this->lexer->token['type'] === EmailLexer::INVALID || + $this->lexer->token['type'] === EmailLexer::C_DEL || + $this->lexer->token['type'] === EmailLexer::S_LF + ) { + $this->warnings[] = EmailValidator::RFC5322_DOMLIT_OBSDTEXT; + } + + if ($this->lexer->isNextTokenAny(array(EmailLexer::S_OPENQBRACKET, EmailLexer::S_OPENBRACKET))) { + throw new \InvalidArgumentException('ERR_EXPECTING_DTEXT'); + } + + if ($this->lexer->isNextTokenAny( + array(EmailLexer::S_HTAB, EmailLexer::S_SP, $this->lexer->token['type'] === EmailLexer::CRLF) + )) { + $this->warnings[] = EmailValidator::CFWS_FWS; + $this->parseFWS(); + } + + if ($this->lexer->isNextToken(EmailLexer::S_CR)) { + throw new \InvalidArgumentException('ERR_CR_NO_LF'); + } + if ($this->lexer->token['type'] === EmailLexer::S_BACKSLASH) { + $this->warnings[] = EmailValidator::RFC5322_DOMLIT_OBSDTEXT; + $addressLiteral .= $this->lexer->token['value']; + $this->lexer->moveNext(); + $this->validateQuotedPair(); + } + if ($this->lexer->token['type'] === EmailLexer::S_IPV6TAG) { + $IPv6TAG = true; + } + if ($this->lexer->token['type'] === EmailLexer::S_CLOSEQBRACKET) { + break; + } + + $addressLiteral .= $this->lexer->token['value']; + + } while ($this->lexer->moveNext()); + + $addressLiteral = str_replace('[', '', $addressLiteral); + $addressLiteral = $this->checkIPV4Tag($addressLiteral); + + if (false === $addressLiteral) { + return $addressLiteral; + } + + if (!$IPv6TAG) { + $this->warnings[] = EmailValidator::RFC5322_DOMAINLITERAL; + return $addressLiteral; + } + + $this->warnings[] = EmailValidator::RFC5321_ADDRESSLITERAL; + + $this->checkIPV6Tag($addressLiteral); + + return $addressLiteral; + } + + protected function checkIPV4Tag($addressLiteral) + { + $matchesIP = array(); + + // Extract IPv4 part from the end of the address-literal (if there is one) + if (preg_match( + '/\\b(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/', + $addressLiteral, + $matchesIP + ) > 0 + ) { + $index = strrpos($addressLiteral, $matchesIP[0]); + if ($index === 0) { + $this->warnings[] = EmailValidator::RFC5321_ADDRESSLITERAL; + return false; + } + // Convert IPv4 part to IPv6 format for further testing + $addressLiteral = substr($addressLiteral, 0, $index) . '0:0'; + } + + return $addressLiteral; + } + + protected function checkDomainPartExceptions($prev) + { + $invalidDomainTokens = array( + EmailLexer::S_DQUOTE => true, + EmailLexer::S_SEMICOLON => true, + EmailLexer::S_GREATERTHAN => true, + EmailLexer::S_LOWERTHAN => true, + ); + + if (isset($invalidDomainTokens[$this->lexer->token['type']])) { + throw new \InvalidArgumentException('ERR_EXPECTING_ATEXT'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_COMMA) { + throw new \InvalidArgumentException('ERR_COMMA_IN_DOMAIN'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_AT) { + throw new \InvalidArgumentException('ERR_CONSECUTIVEATS'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_OPENQBRACKET && $prev['type'] !== EmailLexer::S_AT) { + throw new \InvalidArgumentException('ERR_EXPECTING_ATEXT'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_HYPHEN && $this->lexer->isNextToken(EmailLexer::S_DOT)) { + throw new \InvalidArgumentException('ERR_DOMAINHYPHENEND'); + } + + if ($this->lexer->token['type'] === EmailLexer::S_BACKSLASH + && $this->lexer->isNextToken(EmailLexer::GENERIC)) { + throw new \InvalidArgumentException('ERR_EXPECTING_ATEXT'); + } + } + + protected function hasBrackets($openBrackets) + { + if ($this->lexer->token['type'] === EmailLexer::S_CLOSEBRACKET && !$openBrackets) { + throw new \InvalidArgumentException('ERR_EXPECTING_OPENBRACKET'); + } + + if ($this->lexer->token['type'] !== EmailLexer::S_OPENBRACKET) { + return false; + } + + try { + $this->lexer->find(EmailLexer::S_CLOSEBRACKET); + } catch (\RuntimeException $e) { + throw new \InvalidArgumentException('ERR_EXPECTING_DOMLIT_CLOSE'); + } + + return true; + } + + protected function checkLabelLength($prev) + { + if ($this->lexer->token['type'] === EmailLexer::S_DOT && + $prev['type'] === EmailLexer::GENERIC && + strlen($prev['value']) > 63 + ) { + $this->warnings[] = EmailValidator::RFC5322_LABEL_TOOLONG; + } + } + + protected function parseDomainComments() + { + $this->isUnclosedComment(); + while (!$this->lexer->isNextToken(EmailLexer::S_CLOSEPARENTHESIS)) { + $this->warnEscaping(); + $this->lexer->moveNext(); + } + + $this->lexer->moveNext(); + if ($this->lexer->isNextToken(EmailLexer::S_DOT)) { + throw new \InvalidArgumentException('ERR_EXPECTING_ATEXT'); + } + } +}