|
1 | 1 | # Copyright (C) Lutra Consulting Limited |
2 | 2 | # |
3 | 3 | # SPDX-License-Identifier: AGPL-3.0-only OR LicenseRef-MerginMaps-Commercial |
4 | | -import re |
| 4 | + |
| 5 | +import regex |
5 | 6 | import safe |
6 | 7 | from flask_wtf import FlaskForm |
7 | 8 | from sqlalchemy import func |
|
17 | 18 |
|
18 | 19 | from .models import MAX_USERNAME_LENGTH, User |
19 | 20 | from ..app import UpdateForm, CustomStringField |
20 | | -from .utils import get_email_domain |
21 | 21 |
|
22 | 22 |
|
23 | 23 | def username_validation(form, field): |
@@ -57,19 +57,20 @@ class ExtendedEmail(Email): |
57 | 57 | because they make our email sending service to fail |
58 | 58 | """ |
59 | 59 |
|
| 60 | + EMAIL_PATTERN = regex.compile( |
| 61 | + r"""(?i)^[\x60#&*\/=?^{!}~'_\p{L}0-9\-\+]+ |
| 62 | + (\.[\x60#&*\/=?^{!}~'_\p{L}0-9\-\+]+)*\.?@ |
| 63 | + ([_a-z0-9-]+(\.[_a-z0-9-]+)*\.) |
| 64 | + [a-z0-9-]*[a-z0-9]{2,}$""", |
| 65 | + regex.VERBOSE, |
| 66 | + ) |
| 67 | + |
60 | 68 | def __call__(self, form, field): |
61 | 69 | super().__call__(form, field) |
62 | 70 |
|
63 | | - if re.search(r"[|'—]", field.data): |
64 | | - raise ValidationError( |
65 | | - f"Email address '{field.data}' contains an invalid character." |
66 | | - ) |
67 | | - |
68 | | - domain = get_email_domain(field.data) |
69 | | - if not domain.isascii(): |
70 | | - raise ValidationError( |
71 | | - f"Email address '{field.data}' contains non-ASCII characters in the domain part." |
72 | | - ) |
| 71 | + value = field.data.strip() |
| 72 | + if not self.EMAIL_PATTERN.match(value): |
| 73 | + raise ValidationError(f"Email address '{value}' is invalid.") |
73 | 74 |
|
74 | 75 |
|
75 | 76 | class PasswordValidator: |
|
0 commit comments