forked from CGM_Public/pretix_original
Auto-detect common typos in email addresses
This commit is contained in:
@@ -20,7 +20,8 @@ class ContactForm(forms.Form):
|
||||
email = forms.EmailField(label=_('E-mail'),
|
||||
help_text=_('Make sure to enter a valid email address. We will send you an order '
|
||||
'confirmation including a link that you need in case you want to make '
|
||||
'modifications to your order or download your ticket later.'))
|
||||
'modifications to your order or download your ticket later.'),
|
||||
widget=forms.EmailInput(attrs={'data-typocheck-target': '1'}))
|
||||
|
||||
|
||||
class InvoiceAddressForm(forms.ModelForm):
|
||||
@@ -30,6 +31,8 @@ class InvoiceAddressForm(forms.ModelForm):
|
||||
fields = ('company', 'name', 'street', 'zipcode', 'city', 'country', 'vat_id')
|
||||
widgets = {
|
||||
'street': forms.Textarea(attrs={'rows': 2, 'placeholder': _('Street and Number')}),
|
||||
'company': forms.TextInput(attrs={'data-typocheck-source': '1'}),
|
||||
'name': forms.TextInput(attrs={'data-typocheck-source': '1'}),
|
||||
}
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
@@ -76,7 +79,8 @@ class QuestionsForm(forms.Form):
|
||||
self.fields['attendee_name'] = forms.CharField(
|
||||
max_length=255, required=event.settings.attendee_names_required,
|
||||
label=_('Attendee name'),
|
||||
initial=(cartpos.attendee_name if cartpos else orderpos.attendee_name)
|
||||
initial=(cartpos.attendee_name if cartpos else orderpos.attendee_name),
|
||||
widget=forms.TextInput(attrs={'data-typocheck-source': '1'}),
|
||||
)
|
||||
if item.admission and event.settings.attendee_emails_asked:
|
||||
self.fields['attendee_email'] = forms.EmailField(
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
<script type="text/javascript" src="{% static "pretixbase/js/asynctask.js" %}"></script>
|
||||
<script type="text/javascript" src="{% static "pretixbase/js/asyncdownload.js" %}"></script>
|
||||
<script type="text/javascript" src="{% static "pretixpresale/js/ui/cart.js" %}"></script>
|
||||
<script type="text/javascript" src="{% static "pretixpresale/js/ui/typocheck.js" %}"></script>
|
||||
<script type="text/javascript" src="{% static "lightbox/js/lightbox.min.js" %}"></script>
|
||||
{% endcompress %}
|
||||
<meta name="referrer" content="origin">
|
||||
|
||||
@@ -74,6 +74,12 @@
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
<div class="alert alert-warning typo-alert">
|
||||
<strong>{% trans "Are you sure your email address is correct?" %}</strong><br>
|
||||
{% blocktrans trimmed with entered="<span data-typodisplay></span>" suggestion="<span data-typosuggest></span>" %}
|
||||
You entered "{{ entered }}". Did you mean "{{ suggestion }}"?
|
||||
{% endblocktrans %}
|
||||
</div>
|
||||
<div class="row checkout-button-row">
|
||||
<div class="col-md-4">
|
||||
<a class="btn btn-block btn-default btn-lg"
|
||||
|
||||
79
src/pretix/static/pretixpresale/js/ui/typocheck.js
Normal file
79
src/pretix/static/pretixpresale/js/ui/typocheck.js
Normal file
@@ -0,0 +1,79 @@
|
||||
/*global $,gettext,ngettext */
|
||||
|
||||
function typocheck() {
|
||||
var $target = $("input[data-typocheck-target]"),
|
||||
$sources = $("input[data-typocheck-source]"),
|
||||
orig_val = $target.val(),
|
||||
words = [];
|
||||
|
||||
function regexEscape(str) {
|
||||
return str.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g, "\\$&");
|
||||
}
|
||||
|
||||
$sources.each(function () {
|
||||
$.each($(this).val().toLowerCase().replace('-', '').split(' '), function (i, w) {
|
||||
if (w) {
|
||||
words.push(w);
|
||||
}
|
||||
});
|
||||
});
|
||||
words.push(
|
||||
'@gmail.', '@web.', '@gmx.', '@hotmail.', '@live.', '@outlook.', '@yahoo.', '@mail.', '@msn.', '@me.',
|
||||
'@verizon.', '@mac.', '@email.', '@icloud.', '@inbox.', '@rocketmail.', '@bt.', '@orange.',
|
||||
'@online.', '@t-online.'
|
||||
);
|
||||
|
||||
var word, patterns, i, j, k, r,
|
||||
val = orig_val;
|
||||
for (i = 0; i < words.length; i++) {
|
||||
word = words[i];
|
||||
patterns = [];
|
||||
for (j = 0; j < word.length; j++) {
|
||||
if (j > 0) {
|
||||
patterns.push(regexEscape(word.slice(0, j)) + '.' + regexEscape(word.slice(j)));
|
||||
}
|
||||
if (j > 0 || word.slice(0, 1) !== '@') {
|
||||
patterns.push(regexEscape(word.slice(0, j)) + '.' + regexEscape(word.slice(j + 1)));
|
||||
patterns.push(regexEscape(word.slice(0, j)) + regexEscape(word.slice(j + 1, j + 2)) + regexEscape(word.slice(j, j + 1)) + regexEscape(word.slice(j + 2)));
|
||||
}
|
||||
patterns.push(regexEscape(word.slice(0, j)) + regexEscape(word.slice(j + 1)));
|
||||
}
|
||||
|
||||
// Remove conflicting patterns (i.e. gmail.com shouldn't correct email.com)
|
||||
for (j = patterns.length - 1; j >= 0; j--) {
|
||||
r = new RegExp(patterns[j]);
|
||||
for (k = 0; k < words.length; k++) {
|
||||
if (k === i) {
|
||||
continue;
|
||||
}
|
||||
if (words[k] === '@mail.com') {
|
||||
console.log(words[k], r, words[k].match(r));
|
||||
}
|
||||
if (words[k].match(r)) {
|
||||
patterns.splice(j, 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
val = val.replace(new RegExp('(' + patterns.join('|') + ')', 'i'), word);
|
||||
}
|
||||
val = val.replace(/gmail\.(?!com$)[a-z]*$/i, 'gmail.com');
|
||||
|
||||
var changed = (val.toLowerCase() != orig_val.toLowerCase());
|
||||
$(".typo-alert").toggle(changed).find("[data-typosuggest]").text(val);
|
||||
$(".typo-alert").find("[data-typodisplay]").text(orig_val);
|
||||
}
|
||||
|
||||
$(document).ready(function () {
|
||||
if ($("input[data-typocheck-target]").length === 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
$('body').on('change', 'input[data-typocheck-target], input[data-typocheck-source]', function () {
|
||||
typocheck();
|
||||
});
|
||||
$(".typo-alert span[data-typosuggest]").click(function () {
|
||||
$("input[data-typocheck-target]").val($(this).text());
|
||||
$(".typo-alert").slideUp();
|
||||
})
|
||||
typocheck();
|
||||
});
|
||||
@@ -116,6 +116,11 @@ body.loading .container {
|
||||
-webkit-transition: opacity .5s ease-in-out;
|
||||
}
|
||||
|
||||
.typo-alert span[data-typosuggest] {
|
||||
text-decoration: underline;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.info-row {
|
||||
& > .fa {
|
||||
font-size: 26px;
|
||||
|
||||
Reference in New Issue
Block a user