From ea970be6f21fd1088b2072ffa32ad1f24a1077ee Mon Sep 17 00:00:00 2001 From: Raphael Michel Date: Wed, 28 Jun 2017 18:20:06 +0200 Subject: [PATCH] Allow to generate random slugs --- src/pretix/base/models/event.py | 4 +++- .../pretixcontrol/events/create_basics.html | 4 +++- src/pretix/control/urls.py | 1 + src/pretix/control/views/main.py | 19 +++++++++++++++++++ src/pretix/static/pretixcontrol/js/ui/main.js | 9 +++++++++ .../static/pretixcontrol/scss/_forms.scss | 3 +++ 6 files changed, 38 insertions(+), 2 deletions(-) diff --git a/src/pretix/base/models/event.py b/src/pretix/base/models/event.py index 94e234ad7..400fa07dc 100644 --- a/src/pretix/base/models/event.py +++ b/src/pretix/base/models/event.py @@ -67,7 +67,9 @@ class Event(LoggedModel): max_length=50, db_index=True, help_text=_( "Should be short, only contain lowercase letters and numbers, and must be unique among your events. " - "This will be used in order codes, invoice numbers, links and bank transfer references."), + "We recommend some kind of abbreviation or a date with less than 10 characters that can be easily " + "remembered, but you can also choose to use a random value. " + "This will be used in URLs, order codes, invoice numbers, and bank transfer references."), validators=[ RegexValidator( regex="^[a-zA-Z0-9.-]+$", diff --git a/src/pretix/control/templates/pretixcontrol/events/create_basics.html b/src/pretix/control/templates/pretixcontrol/events/create_basics.html index 4af38085d..cf54d1a79 100644 --- a/src/pretix/control/templates/pretixcontrol/events/create_basics.html +++ b/src/pretix/control/templates/pretixcontrol/events/create_basics.html @@ -5,7 +5,9 @@
{% trans "General information" %} {% bootstrap_field form.name layout="horizontal" %} - {% bootstrap_field form.slug layout="horizontal" %} + {% trans "Random" as rndlabel %} + {% url "control:events.add.slugrng" organizer=organizer.slug as rngurl %} + {% bootstrap_field form.slug layout="horizontal" addon_after='' addon_after_class='input-group-btn' %} {% bootstrap_field form.date_from layout="horizontal" %} {% bootstrap_field form.date_to layout="horizontal" %} {% bootstrap_field form.location layout="horizontal" %} diff --git a/src/pretix/control/urls.py b/src/pretix/control/urls.py index 24ce890ca..b6c4daac2 100644 --- a/src/pretix/control/urls.py +++ b/src/pretix/control/urls.py @@ -43,6 +43,7 @@ urlpatterns = [ name='organizer.team.edit'), url(r'^organizer/(?P[^/]+)/team/(?P[^/]+)/delete$', organizer.TeamDeleteView.as_view(), name='organizer.team.delete'), + url(r'^organizer/(?P[^/]+)/slugrng', main.SlugRNG.as_view(), name='events.add.slugrng'), url(r'^events/$', main.EventList.as_view(), name='events'), url(r'^events/add$', main.EventWizard.as_view(), name='events.add'), url(r'^events/typeahead/$', typeahead.event_list, name='events.typeahead'), diff --git a/src/pretix/control/views/main.py b/src/pretix/control/views/main.py index e61a414c3..d5ad490ea 100644 --- a/src/pretix/control/views/main.py +++ b/src/pretix/control/views/main.py @@ -2,9 +2,12 @@ from django.conf import settings from django.contrib import messages from django.core.urlresolvers import reverse from django.db import transaction +from django.http import JsonResponse from django.shortcuts import redirect +from django.utils.crypto import get_random_string from django.utils.functional import cached_property from django.utils.translation import ugettext_lazy as _ +from django.views import View from django.views.generic import ListView from formtools.wizard.views import SessionWizardView @@ -13,6 +16,7 @@ from pretix.control.forms.event import ( EventWizardBasicsForm, EventWizardCopyForm, EventWizardFoundationForm, ) from pretix.control.forms.filter import EventFilterForm +from pretix.control.permissions import OrganizerPermissionRequiredMixin class EventList(ListView): @@ -61,6 +65,8 @@ class EventWizard(SessionWizardView): def get_context_data(self, form, **kwargs): ctx = super().get_context_data(form, **kwargs) ctx['has_organizer'] = self.request.user.teams.filter(can_create_events=True).exists() + if self.steps.current == 'basics': + ctx['organizer'] = self.get_cleaned_data_for_step('foundation').get('organizer') return ctx def get_form_kwargs(self, step=None): @@ -121,3 +127,16 @@ class EventWizard(SessionWizardView): 'organizer': event.organizer.slug, 'event': event.slug, })) + + +class SlugRNG(OrganizerPermissionRequiredMixin, View): + + def get(self, request, *args, **kwargs): + # See Order.assign_code + charset = list('abcdefghjklmnpqrstuvwxyz3789') + for i in range(100): + val = get_random_string(length=settings.ENTROPY['order_code'], allowed_chars=charset) + if not self.request.organizer.events.filter(slug__iexact=val).exists(): + break + + return JsonResponse({'slug': val}) diff --git a/src/pretix/static/pretixcontrol/js/ui/main.js b/src/pretix/static/pretixcontrol/js/ui/main.js index 14e995d18..e3ca74085 100644 --- a/src/pretix/static/pretixcontrol/js/ui/main.js +++ b/src/pretix/static/pretixcontrol/js/ui/main.js @@ -102,6 +102,15 @@ $(function () { question_page_toggle_view(); } + // Event wizard + $("#event-slug-random-generate").click(function () { + var url = $(this).attr("data-rng-url"); + $("#id_basics-slug").val("Generating..."); + $.getJSON(url, function (data) { + $("#id_basics-slug").val(data.slug); + }); + }); + // Vouchers $("#voucher-bulk-codes-generate").click(function () { var num = $("#voucher-bulk-codes-num").val(); diff --git a/src/pretix/static/pretixcontrol/scss/_forms.scss b/src/pretix/static/pretixcontrol/scss/_forms.scss index d191d4cfb..e49a75708 100644 --- a/src/pretix/static/pretixcontrol/scss/_forms.scss +++ b/src/pretix/static/pretixcontrol/scss/_forms.scss @@ -151,3 +151,6 @@ pre.mail-preview { width: 1% !important; } } +.input-group-btn .btn { + padding-bottom: 7px; +}