From 7973aeab453f8cc46037a9c0f948e07bc430d7b0 Mon Sep 17 00:00:00 2001 From: Richard Schreiber Date: Thu, 25 Jun 2026 10:38:32 +0200 Subject: [PATCH] Check for existing codes instead of failing on db-level --- src/pretix/base/services/modelimport.py | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/src/pretix/base/services/modelimport.py b/src/pretix/base/services/modelimport.py index 5fee363a08..1ba202e9f8 100644 --- a/src/pretix/base/services/modelimport.py +++ b/src/pretix/base/services/modelimport.py @@ -27,7 +27,7 @@ from django.conf import settings as django_settings from django.core.exceptions import ValidationError from django.db import transaction from django.utils.timezone import now -from django.utils.translation import gettext as _ +from django.utils.translation import gettext as _, ngettext from pretix.base.i18n import language from pretix.base.modelimport import DataImportError, ImportColumn, parse_csv @@ -297,6 +297,20 @@ def import_vouchers(event: Event, fileid: str, settings: dict, locale: str, user raise DataImportError( _('Invalid data in row {row}: {message}').format(row=i+1, message=str(e)) ) + existing_codes = Voucher.objects.filter( + event=event, + code__in=codes, + ).values_list("code", flat=True) + if len(existing_codes): + raise DataImportError( + ngettext( + 'Voucher codes must be unique. Import contains existing voucher code {code}.', + 'Voucher codes must be unique. Import contains existing voucher codes {code}.', + len(existing_codes) + ).format( + code=", ".join(existing_codes) + ) + ) with transaction.atomic(): # We don't support quotas here, so we only need to lock if seats are in use