MCPcopy Index your code
hub / github.com/JoshData/python-email-validator / split_email

Function split_email

email_validator/syntax.py:14–198  ·  view source on GitHub ↗
(email: str)

Source from the content-addressed store, hash-verified

12
13
14def split_email(email: str) -> Tuple[Optional[str], str, str, bool]:
15 # Return the display name, unescaped local part, and domain part
16 # of the address, and whether the local part was quoted. If no
17 # display name was present and angle brackets do not surround
18 # the address, display name will be None; otherwise, it will be
19 # set to the display name or the empty string if there were
20 # angle brackets but no display name.
21
22 # Typical email addresses have a single @-sign and no quote
23 # characters, but the awkward "quoted string" local part form
24 # (RFC 5321 4.1.2) allows @-signs and escaped quotes to appear
25 # in the local part if the local part is quoted.
26
27 # A `display name <addr>` format is also present in MIME messages
28 # (RFC 5322 3.4) and this format is also often recognized in
29 # mail UIs. It's not allowed in SMTP commands or in typical web
30 # login forms, but parsing it has been requested, so it's done
31 # here as a convenience. It's implemented in the spirit but not
32 # the letter of RFC 5322 3.4 because MIME messages allow newlines
33 # and comments as a part of the CFWS rule, but this is typically
34 # not allowed in mail UIs (although comment syntax was requested
35 # once too).
36 #
37 # Display names are either basic characters (the same basic characters
38 # permitted in email addresses, but periods are not allowed and spaces
39 # are allowed; see RFC 5322 Appendix A.1.2), or or a quoted string with
40 # the same rules as a quoted local part. (Multiple quoted strings might
41 # be allowed? Unclear.) Optional space (RFC 5322 3.4 CFWS) and then the
42 # email address follows in angle brackets.
43 #
44 # An initial quote is ambiguous between starting a display name or
45 # a quoted local part --- fun.
46 #
47 # We assume the input string is already stripped of leading and
48 # trailing CFWS.
49
50 def split_string_at_unquoted_special(text: str, specials: Tuple[str, ...]) -> Tuple[str, str]:
51 # Split the string at the first character in specials (an @-sign
52 # or left angle bracket) that does not occur within quotes and
53 # is not followed by a Unicode combining character.
54 # If no special character is found, raise an error.
55 inside_quote = False
56 escaped = False
57 left_part = ""
58 for i, c in enumerate(text):
59 # < plus U+0338 (Combining Long Solidus Overlay) normalizes to
60 # ≮ U+226E (Not Less-Than), and it would be confusing to treat
61 # the < as the start of "<email>" syntax in that case. Likewise,
62 # if anything combines with an @ or ", we should probably not
63 # treat it as a special character.
64 if unicodedata.normalize("NFC", text[i:])[0] != c:
65 left_part += c
66
67 elif inside_quote:
68 left_part += c
69 if c == '\\' and not escaped:
70 escaped = True
71 elif c == '"' and not escaped:

Callers 1

validate_emailFunction · 0.85

Calls 5

unquote_quoted_stringFunction · 0.85
safe_character_displayFunction · 0.85
EmailSyntaxErrorClass · 0.85
check_unsafe_charsFunction · 0.85

Tested by

no test coverage detected