Compare commits

..
Author SHA1 Message Date
Raphael Michel f7863c9fee Bump version to 2026.8.0 2026-09-30 10:50:03 +02:00
Raphael Michel fc3150fecc Revert "DE: Update Wordlist"
This reverts commit 89318bcc24.
2026-09-30 10:49:57 +02:00
Martin Gross 89318bcc24 DE: Update Wordlist 2026-09-30 10:24:13 +02:00
dependabot[bot] a388391f06 Update pyjwt requirement from ==2.14.* to ==2.15.* (#6620) 2026-09-30 10:12:38 +02:00
Raphael Michel b4d000379c Translations: Update German (informal) (de_Informal)
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de_Informal/

powered by weblate
2026-09-30 10:10:52 +02:00
Phin Wolkwitz ba9bba49c6 Translations: Update German (informal) (de_Informal)
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de_Informal/

powered by weblate
2026-09-30 10:10:52 +02:00
Daniel Musketa 824624cce6 Translations: Update German (informal) (de_Informal)
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de_Informal/

powered by weblate
2026-09-30 10:10:52 +02:00
Phin Wolkwitz 8601f62581 Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Daniel Musketa 7547d64dea Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Matthias Schrumpf d1186c83ef Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Raphael Michel e4782ff217 Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Matthias Schrumpf 3328dc28c7 Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Raphael Michel 6c83b4288a Translations: Update German (informal) (de_Informal)
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de_Informal/

powered by weblate
2026-09-30 10:10:52 +02:00
Raphael Michel 6ff37796c3 Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Raphael Michel fa60c320b9 Translations: Update German (informal) (de_Informal)
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de_Informal/

powered by weblate
2026-09-30 10:10:52 +02:00
Raphael Michel ca9d9faef4 Translations: Update German
Currently translated at 100.0% (6442 of 6442 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-30 10:10:52 +02:00
Raphael Michel 9718d1ee83 Translations: Update wordlist 2026-09-30 10:09:23 +02:00
pajowu 7bdb2c1555 Email: always use quoted-printable (#6617) 2026-09-30 09:54:21 +02:00
Raphael Michel da6753b53f Update po files
[CI skip]

Signed-off-by: Raphael Michel <michel@pretix.eu>
2026-09-30 09:26:26 +02:00
CVZ-es 33df9d13be Translations: Update French
Currently translated at 100.0% (6419 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/fr/

powered by weblate
2026-09-30 09:25:43 +02:00
Nate Horst 582f9ac642 Translations: Update Thai
Currently translated at 81.1% (5206 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-30 09:25:00 +02:00
Translate pretix user 594 5ce2957965 Translations: Update Russian
Currently translated at 20.0% (1285 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/ru/

powered by weblate
2026-09-30 09:25:00 +02:00
Ыукпун eb9d6ad9a3 Translations: Update Russian
Currently translated at 20.0% (1285 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/ru/

powered by weblate
2026-09-30 09:25:00 +02:00
Raphael Michel d339e1d594 Hotfix: Perform validation on the selected step, not on all steps before 2026-09-29 20:11:51 +02:00
Raphael Michel cb15559ac6 Scheduled export: Fix copying of email subject and text (Z#23221224) (#6616) 2026-09-29 16:44:42 +02:00
pajowu 3c95f1fee7 Add HERMA 9012 90 x 90mm Badge format (Z#23248189) (#6619) 2026-09-29 16:44:02 +02:00
Richard Schreiber 6a380c9356 Presale: add js-helper to disable submit for x seconds (#6592)
* Presale: add js-helper to disable submit for x seconds

* Remove disabled-class from button, if any

* Use Intl.RelativeTimeFormat for time formatting
2026-09-29 16:36:09 +02:00
Kara Engelhardt eeea01b31a Fix linter errors 2026-09-29 15:34:26 +02:00
Kara Engelhardt 470621b5cb Add missing licenseheader 2026-09-29 15:34:23 +02:00
dependabot[bot] 5802153101 Update sentry-sdk requirement from ==2.69.* to ==2.70.* (#6600)
Updates the requirements on [sentry-sdk](https://github.com/getsentry/sentry-python) to permit the latest version.
- [Release notes](https://github.com/getsentry/sentry-python/releases)
- [Changelog](https://github.com/getsentry/sentry-python/blob/master/CHANGELOG.md)
- [Commits](https://github.com/getsentry/sentry-python/compare/2.69.0...2.70.0)

---
updated-dependencies:
- dependency-name: sentry-sdk
  dependency-version: 2.70.0
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-29 15:33:24 +02:00
Nate Horst e9f89d5d92 Translations: Update Thai
Currently translated at 70.0% (4494 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-29 15:33:15 +02:00
Nate Horst 695689ed06 Translations: Update Thai
Currently translated at 98.8% (257 of 260 strings)

Translation: pretix/pretix (JavaScript parts)
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix-js/th/

powered by weblate
2026-09-29 15:33:15 +02:00
Nate Horst 12d405d861 Translations: Update Thai
Currently translated at 69.5% (4463 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-29 15:33:15 +02:00
Nate Horst 649eee3025 Translations: Update Thai
Currently translated at 65.8% (4230 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-29 15:33:15 +02:00
Tim 149b4f23aa Translations: Update Spanish
Currently translated at 100.0% (6419 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/es/

powered by weblate
2026-09-29 15:33:15 +02:00
Nate Horst fa40ccc623 Translations: Update Thai
Currently translated at 55.9% (3593 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-29 15:33:15 +02:00
Mira Weller 2ba74b1697 Fix various redirects for events on MODE_ORG_ALT_DOMAIN 2026-09-29 14:34:49 +02:00
Mira Weller e54cd6af44 Fix redirect to customer login page when:
- event on custom domain (MODE_EVENT_DOMAIN or MODE_ORG_ALT_DOMAIN)
- organizer on system domain
2026-09-29 14:34:49 +02:00
Mira Weller d2b58d428e Fix customer logout when:
- event on custom domain (MODE_EVENT_DOMAIN or MODE_ORG_ALT_DOMAIN)
- organizer on system domain
2026-09-29 14:34:49 +02:00
Raphael Michel 74332faa7b [SECURITY] API: Fix session validation for uploaded files (CVE-2026-101269, Z#23247174) 2026-09-29 14:30:54 +02:00
Mira Weller bbf391f7d5 Block out of bounds image crop dimensions (Z#23245937 / PRT-009) 2026-09-29 14:30:54 +02:00
Mira Weller d78d5b52fa Prevent parsing non-standard-compliant JSON float values (Z#23245937 / PRT-021) 2026-09-29 14:30:54 +02:00
Mira Weller 9c0fef3d72 Fix potential infinite loop in pdf render (Z#23245937 / PRT-021) 2026-09-29 14:30:54 +02:00
Mira Weller c7d6630979 Fix inefficient loop in compute_validity (Z#23245937 / PRT-013) 2026-09-29 14:30:53 +02:00
Raphael Michel 4edd3c4654 [SECURITY] OAuth: Disable existing tokens when deactivating Application (CVE-2026-101271, Z#23247296) 2026-09-29 14:30:53 +02:00
Mira Weller b1ae638394 [SECURITY] Escape help texts (CVE-2026-101270) 2026-09-29 14:30:53 +02:00
Raphael Michel ae9bb68645 [SECURITY] Fix customer session fixation on cross-domain login (CVE-2026-101268, Z#23247268) 2026-09-29 14:30:53 +02:00
Raphael Michel 48f5a7c8cc [SECURITY] Fix information leak in widgets.json on dashboard (CVE-2026-101267, Z#23247172)
Thanks to Wenhao Wu, Southeast University
2026-09-29 14:30:53 +02:00
Raphael Michel d43032274b [SECURITY] Fix checkout validation bypass (CVE-2026-101266, Z#23245008) 2026-09-29 14:30:53 +02:00
Raphael Michel ae9a744fd9 Revert "Always base64-encode email attachments (Z#23242540) (#6476)"
This reverts commit ff4d3cd403.
2026-09-29 14:07:57 +02:00
pajowu ff4d3cd403 Always base64-encode email attachments (Z#23242540) (#6476)
It might sound unneccesary to base64-encode plaintext attachments, but some smtp providers modify them otherwise
2026-09-29 12:27:43 +02:00
pajowu 3440ee16f2 Plugin List: Apply search filter if prefilled by browser (#6543)
* Plugin List: Apply searchfilter if prefilled by browser

Browsers often prefill the form fields, e.g. with their old content when reloading or going back from the previous page. However these filters were not applied until you changed one of the form fields

* Fix linting errors in plugins.js

* Apply review suggestions
2026-09-29 11:51:29 +02:00
pajowu 43e5b62db3 Banktransfer: Make actionvie atomic (Z#23246414) (#6604) 2026-09-29 11:51:12 +02:00
dependabot[bot] b249c7b417 Bump markdown from 3.10.3 to 3.11 (#6608)
Bumps [markdown](https://github.com/Python-Markdown/markdown) from 3.10.3 to 3.11.
- [Release notes](https://github.com/Python-Markdown/markdown/releases)
- [Changelog](https://github.com/Python-Markdown/markdown/blob/master/docs/changelog.md)
- [Commits](https://github.com/Python-Markdown/markdown/compare/3.10.3...3.11.0)

---
updated-dependencies:
- dependency-name: markdown
  dependency-version: '3.11'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-29 10:17:48 +02:00
dependabot[bot] b68c324389 Update flake8 requirement from ==7.3.* to ==7.4.* (#6609)
Updates the requirements on [flake8](https://github.com/pycqa/flake8) to permit the latest version.
- [Commits](https://github.com/pycqa/flake8/compare/7.3.0...7.4.1)

---
updated-dependencies:
- dependency-name: flake8
  dependency-version: 7.4.1
  dependency-type: direct:development
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-29 10:17:29 +02:00
Aodhán Burke 4b320b6dab Fix typo: then -> than (#6615) 2026-09-29 10:16:54 +02:00
Richard Schreiber df74cbf5fc Remove Vue2-based widget (#6610)
* Remove Vue2-based widget

* move floatformat.js

* Delete docready.js

* Update widget.py
2026-09-29 10:14:21 +02:00
pajowu c875d758f9 Fix crash on too old time machine date (Z#23245824) (#6599)
* Fix crash on too old time machine date (Z#23245824)

dateutil.parser seems to reject dates with second-precision timezone-offsets, which datetime produces for some dates aroung the year 200. datetime.fromisoformat has no problem parsing them

* Review comments

* Add min date
2026-09-28 17:28:26 +02:00
Martin Gross 2ebdd048c2 PayPal2: Drop maximum length of client ID (Rel: #6424) 2026-09-28 16:12:55 +02:00
Raphael Michel ca40b09080 Fix API documentation bug 2026-09-28 15:46:41 +02:00
pajowuandRaphael Michel 558bf910fd Use fragment_product_list in voucher redemption view (Z#23246929) (#6567)
* Use fragment_product_list in voucher redemption view (Z#23246929)

* Formatting

* Fix usage in templates

* Review comments

* handle form prefix in fragment_product_list.html

---------

Co-authored-by: Raphael Michel <michel@pretix.eu>
2026-09-28 13:01:15 +02:00
pajowu 7e1e472691 Monkeypatch stock csrfmiddleware (#6401)
* Monkeypatch stock csrfmiddleware

* Add test for ensure_csrf_cookie
2026-09-28 11:46:23 +02:00
Richard Schreiber b06c9ef463 Control: do not fail on missing reason when user confirm (#6602) 2026-09-28 11:43:52 +02:00
pajowu 2af8d29ca9 Add pdf render tests (#6566)
* Add pdf tests

* pdf tests: Save temporary pdfs for failed test debugging

* Review comments
2026-09-25 16:54:58 +02:00
Raphael Michel 2791d5e49e Celery: Fix missing log if workers are recycled due to RAM usage (#6588) 2026-09-25 08:56:49 +02:00
Richard Schreiber ed68719731 Widget: fix calendar view showing old events due to non-unique key (Z#23247433) (#6585)
* Widget: fix calendar view showing old events due to cache-key (Z#23247433)

* Update EventCalendarCell.vue
2026-09-24 12:00:57 +02:00
9aeb4b9731 Organizer API: Add endpoint for event-meta-properties
* Add API-endpoint for event-meta-properties

* Add new doc-file to index, fix spelling and description

* Fix logentry

* Fix logentry again

* validate and add tests

* add meta_properties from organizer only

* fix choices validation

* filter unknown keys from choices due to django-formsets

* Apply batched suggestions from code review

Co-authored-by: Richard Schreiber <wiffbi@gmail.com>

* add safe-guard normalization to None to to_representation

* Apply batched suggestions from code review

Co-authored-by: Raphael Michel <mail@raphaelmichel.de>

* update tests to check for error-messages as well

* fix flake8

* fix permission tests

* Make ObjectListField more flexibel for re-use

* fix validation result

* Improve validation

* Change to I18nField for validation

* update MetaPropertyDictField

* fix docs for i18n strings

* make label_child configurable if MetaPropertyDictField should contain non-localized stuff

* undo test changes in events test

* fix flake8

* Apply batched suggestions from code review

Co-authored-by: Raphael Michel <mail@raphaelmichel.de>

* improve code formatting

---------

Co-authored-by: Richard Schreiber <schreiber@rami.io>
Co-authored-by: Richard Schreiber <schreiber@pretix.eu>
Co-authored-by: Richard Schreiber <wiffbi@gmail.com>
Co-authored-by: Raphael Michel <mail@raphaelmichel.de>
2026-09-24 10:51:23 +02:00
Minding 9324887790 Translate OAuth buttons (#6590)
* Translate OAuth buttons

* Revert .po changes
2026-09-24 09:52:47 +02:00
Nate Horst d353384555 Translations: Update Thai
Currently translated at 53.0% (3407 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-24 09:16:49 +02:00
Raphael Michel b8f8e49cce API: Add additional tests for modifying meta data (Z#23247634) 2026-09-23 19:01:52 +02:00
Raphael Michel 806d0a5748 User details: Show list of 2FA devices and allow to reset drift (#6569)
* User details: Show list of 2FA devices

* Add reset button

* Reset throttle

* Refactoring

* Fix delete paths in tests
2026-09-23 17:51:10 +02:00
Raphael Michel 69e541e5af Product list: Fix edge case in dependent availabilities (Z#23243701) (#6532) 2026-09-23 17:22:54 +02:00
Raphael Michel 0723e6015c Event header: Remove date directly above other date (Z#23245589) (#6524)
* Event header: Fix wrapping of date in h2 header (Z#23245589)

This was already correct if the header was a h1

* Revert "Event header: Fix wrapping of date in h2 header (Z#23245589)"

This reverts commit 3d25316fe3.

* Event header: Remove date directly above other date

This removes the date from the <h2> option used when a header image is
uploaded and the header should still be shown. Rendering the date here
makes little sense, since the infobox with the date is always just a few
lines below. It still makes sense for the <h1> option where it becomes
part of the site header.
2026-09-23 15:54:47 +02:00
Raphael Michel b8e1ab8258 Voucher API: Add search parameter (Z#23240589) (#6523) 2026-09-23 15:54:44 +02:00
Raphael Michel 81764278ae Email settings: Collapse attendee texts if unused (Z#23243417) (#6535) 2026-09-23 14:00:56 +02:00
Nate Horst f3068e627a Translations: Update Thai
Currently translated at 52.2% (3356 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-23 11:41:45 +02:00
Nate Horst 993a3f96e9 Translations: Update Thai
Currently translated at 52.1% (3346 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-23 11:41:45 +02:00
Nate Horst 1af0b5e442 Translations: Update Thai
Currently translated at 51.8% (3330 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-23 11:41:45 +02:00
Nate Horst 71b6bf630f Translations: Update Thai
Currently translated at 45.6% (2930 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-23 11:41:45 +02:00
Raphael MichelandMartin Gross 59026da06b Delete PayPal integration v1 (#6530)
* Delete PayPal integration v1

Leaving only migrations behind

* Try to fix CI

* Fix tests some more

* Rename more plugin name instances in tests and docs

---------

Co-authored-by: Martin Gross <martin@pc-coholic.de>
2026-09-23 11:38:16 +02:00
Raphael Michel b3e0892d76 Conditionally import sentry SDK during error page rendering 2026-09-23 11:33:05 +02:00
Raphael Michel 3029a6839b Prevent Sentry SDK from being loaded during tests 2026-09-23 11:29:28 +02:00
Raphael Michel a826b0a1bd Customer area: Hide password change link for SSO users (fixes #6572) (#6580) 2026-09-22 15:22:43 +02:00
Raphael Michel 7d7474c07d Refund form: Do not allow individual negative amounts (#6579) 2026-09-22 12:47:06 +02:00
Raphael Michel 58023381b9 Merge branch 'refund-offset-perm-check' into 'master'
Offset refund: Do not allow to offset to order without access to

See merge request pretix/pretix!52
2026-09-22 12:46:20 +02:00
Raphael Michel e5c44e7aed Offset refund: Do not allow to offset to order without access to 2026-09-22 12:46:20 +02:00
Raphael Michel d77a179606 2FA: Show info on throttled request (#6581)
* 2FA: Show info on throttled request

* Round up the time
2026-09-22 10:38:26 +02:00
Raphael Michel 29614db1e2 InvoiceShredder: Fix shredding of new fields (#6577)
* InvoiceShredder: Fix shredding of new fields

* Update src/pretix/base/migrations/0311_fix_unshredded_invoices.py
2026-09-22 10:37:58 +02:00
Raphael Michel 365051cc21 Event metadata: Fix server-side validation of write protection (#6578) 2026-09-22 10:00:15 +02:00
Raphael Michel 5c6b0eef6f Plugin configuration: Allow organizers to see all events (#6576) 2026-09-22 09:51:18 +02:00
Raphael Michel bc0a6b662b Checkout: Fix VAT ID revalidation after country change (#6575) 2026-09-22 09:51:10 +02:00
dependabot[bot]andRichard Schreiber 0bc1aed1a0 Update pypdf requirement from ==6.11.* to ==6.19.* (#6570)
* Update pypdf requirement from ==6.11.* to ==6.18.*

Updates the requirements on [pypdf](https://github.com/py-pdf/pypdf) to permit the latest version.
- [Release notes](https://github.com/py-pdf/pypdf/releases)
- [Changelog](https://github.com/py-pdf/pypdf/blob/main/CHANGELOG.md)
- [Commits](https://github.com/py-pdf/pypdf/compare/6.11.0...6.18.1)

---
updated-dependencies:
- dependency-name: pypdf
  dependency-version: 6.18.1
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>

* Update pyproject.toml

---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Richard Schreiber <schreiber@pretix.eu>
2026-09-22 09:38:28 +02:00
Rita Gimenez 0eaa5a081c Translations: Update Catalan
Currently translated at 29.4% (1892 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/ca/

powered by weblate
2026-09-21 14:56:27 +02:00
Nate Horst 688c434c4f Translations: Update Thai
Currently translated at 37.1% (2387 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/th/

powered by weblate
2026-09-21 14:56:27 +02:00
dependabot[bot]andRaphael Michel c0474604a1 Update isort requirement from ==8.0.* to ==9.0.* (#6510)
* Update isort requirement from ==8.0.* to ==9.0.*

Updates the requirements on [isort](https://github.com/PyCQA/isort) to permit the latest version.
- [Release notes](https://github.com/PyCQA/isort/releases)
- [Changelog](https://github.com/PyCQA/isort/blob/main/CHANGELOG.md)
- [Commits](https://github.com/PyCQA/isort/compare/8.0.0...9.0.1)

---
updated-dependencies:
- dependency-name: isort
  dependency-version: 9.0.1
  dependency-type: direct:development
...

Signed-off-by: dependabot[bot] <support@github.com>

* Run isort

---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Raphael Michel <michel@pretix.eu>
2026-09-21 14:56:14 +02:00
dependabot[bot] 1741d08c2c Update cryptography requirement from >=50.0.0 to >=50.0.1 (#6509)
Updates the requirements on [cryptography](https://github.com/pyca/cryptography) to permit the latest version.
- [Changelog](https://github.com/pyca/cryptography/blob/main/CHANGELOG.rst)
- [Commits](https://github.com/pyca/cryptography/compare/50.0.0...50.0.1)

---
updated-dependencies:
- dependency-name: cryptography
  dependency-version: 50.0.1
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-21 14:14:06 +02:00
dependabot[bot] 6bbd808aaa Bump postcss-selector-parser from 7.1.1 to 7.1.5 (#6513)
Bumps [postcss-selector-parser](https://github.com/postcss/postcss-selector-parser) from 7.1.1 to 7.1.5.
- [Release notes](https://github.com/postcss/postcss-selector-parser/releases)
- [Changelog](https://github.com/postcss/postcss-selector-parser/blob/main/CHANGELOG.md)
- [Commits](https://github.com/postcss/postcss-selector-parser/compare/v7.1.1...7.1.5)

---
updated-dependencies:
- dependency-name: postcss-selector-parser
  dependency-version: 7.1.5
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-21 14:13:46 +02:00
dependabot[bot] aa90c5b3b1 Bump @humanfs/node from 0.16.7 to 0.16.8 (#6517)
Bumps [@humanfs/node](https://github.com/humanwhocodes/humanfs/tree/HEAD/packages/node) from 0.16.7 to 0.16.8.
- [Release notes](https://github.com/humanwhocodes/humanfs/releases)
- [Changelog](https://github.com/humanwhocodes/humanfs/blob/main/packages/node/CHANGELOG.md)
- [Commits](https://github.com/humanwhocodes/humanfs/commits/node-v0.16.8/packages/node)

---
updated-dependencies:
- dependency-name: "@humanfs/node"
  dependency-version: 0.16.8
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-21 14:13:39 +02:00
dependabot[bot] bfbabe0e58 Update fakeredis requirement from ==2.37.* to ==2.38.* (#6563)
Updates the requirements on [fakeredis](https://github.com/cunla/fakeredis-py) to permit the latest version.
- [Release notes](https://github.com/cunla/fakeredis-py/releases)
- [Commits](https://github.com/cunla/fakeredis-py/compare/v2.37.0...v2.38.0)

---
updated-dependencies:
- dependency-name: fakeredis
  dependency-version: 2.38.0
  dependency-type: direct:development
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-21 14:08:32 +02:00
Raphael Michelandpajowu aa14505d2c Money representation in templates: Allow more precision (#6454)
* Money representation in templates: Allow more precision

When rendering money in templates, we used to have the following logic:

- When the decimal places fit the currency, render with Babel
- When they don't, e.g. we stored 123.67 JPY, even though there are no
  fractional Yens, render without Babel with a custom format, but render
  the fractional Yens because we'd rather *show* wrong data and make the
  bug obvious than hide it.

However, we only did that up to a prevision of two places, we never
showed more. This is still sufficient for core pretix, but we have
plugins that need to operate in fractional cents. Also, we CAN render
everything through babel for consistent formatting.

There is one **risk**: This might cause weird results on SQLite. Since
SQLite has no concept of precise decimal math, results of in-SQL
computations can sometimes experience floating point errors and show
with A LOT of decimal palces. This used to be invisible since the UI
performed the rounding. With this PR – not any more. We'll need to see
how annoying it is, but it should only affect development mode.

This PR also fixes a bug in tax_rate_format that for some reason did not
do what it was supposed to do, even though I tested it back then, weird.
Might even be a Python version thing?

* Update src/pretix/base/templatetags/money.py

Co-authored-by: pajowu <engelhardt@pretix.eu>

* Apply suggestion from @pajowu

Co-authored-by: pajowu <engelhardt@pretix.eu>

* Fix typing stuff

* Fix precision issue

---------

Co-authored-by: pajowu <engelhardt@pretix.eu>
2026-09-18 11:49:12 +02:00
Kara Engelhardt df69656364 PDF: Fix background page being rotated multiple times
transfer_rotation_to_content (or rather add_transformation/replace_content) do not properly duplicate the contentstream they're modifying. this means that if you pass a pdf-level copy of the same bg_page multiple times, the content will be rotated multiple times but the rotation-property ('/Rotate') will only be changed for the first page

pypdfs docs explicitly say that you should not to add_transformation + merge, but instead use merge_transformed_page, which this now does for everything
2026-09-18 11:35:01 +02:00
Kara Engelhardt 82cffd1519 pdf: calculate sizebox based on cropbox and mediabox 2026-09-18 11:33:34 +02:00
Richard Schreiber 7fc527135d PDF: use artbox before trimbox before mediabox from background-PDF as size for canvas 2026-09-18 11:33:34 +02:00
Raphael Michel 8e39b67ee9 Fix missing translatable field label 2026-09-17 11:56:12 +02:00
dependabot[bot] 289cbe5bfc Update django-countries requirement from ==9.0.* to ==9.1.* (#6562)
Updates the requirements on [django-countries](https://github.com/SmileyChris/django-countries) to permit the latest version.
- [Changelog](https://github.com/SmileyChris/django-countries/blob/main/CHANGES.md)
- [Commits](https://github.com/SmileyChris/django-countries/compare/v9.0.0...v9.1.0)

---
updated-dependencies:
- dependency-name: django-countries
  dependency-version: 9.1.0
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-17 10:43:55 +02:00
Raphael Michel 7143b877c8 Translations: Update German
Currently translated at 100.0% (6419 of 6419 strings)

Translation: pretix/pretix
Translate-URL: https://translate.pretix.eu/projects/pretix/pretix/de/

powered by weblate
2026-09-16 15:46:28 +02:00
dependabot[bot] e2a78100af Update pyjwt requirement from ==2.13.* to ==2.14.* (#6557)
Updates the requirements on [pyjwt](https://github.com/jpadilla/pyjwt) to permit the latest version.
- [Release notes](https://github.com/jpadilla/pyjwt/releases)
- [Changelog](https://github.com/jpadilla/pyjwt/blob/master/CHANGELOG.rst)
- [Commits](https://github.com/jpadilla/pyjwt/compare/2.13.0...2.14.0)

---
updated-dependencies:
- dependency-name: pyjwt
  dependency-version: 2.14.0
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-16 15:46:16 +02:00
dependabot[bot] ca77467e48 Update sentry-sdk requirement from ==2.68.* to ==2.69.* (#6556)
Updates the requirements on [sentry-sdk](https://github.com/getsentry/sentry-python) to permit the latest version.
- [Release notes](https://github.com/getsentry/sentry-python/releases)
- [Changelog](https://github.com/getsentry/sentry-python/blob/master/CHANGELOG.md)
- [Commits](https://github.com/getsentry/sentry-python/compare/2.68.0...2.69.1)

---
updated-dependencies:
- dependency-name: sentry-sdk
  dependency-version: 2.69.1
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-09-16 15:46:07 +02:00
Raphael Michel d3cbfcd4da Invoice export: Add transmission-specific data (Z#23239732) (#6522) 2026-09-15 16:44:00 +02:00
287 changed files with 30269 additions and 30494 deletions
+1 -2
View File
@@ -16,8 +16,6 @@ recursive-include src/pretix/plugins/banktransfer/templates *
recursive-include src/pretix/plugins/banktransfer/static *
recursive-include src/pretix/plugins/manualpayment/templates *
recursive-include src/pretix/plugins/manualpayment/static *
recursive-include src/pretix/plugins/paypal/templates *
recursive-include src/pretix/plugins/paypal/static *
recursive-include src/pretix/plugins/paypal2/templates *
recursive-include src/pretix/plugins/paypal2/static *
recursive-include src/pretix/plugins/src/pretixdroid/templates *
@@ -44,6 +42,7 @@ recursive-include src *.py
recursive-include src *.svg
recursive-include src *.txt
recursive-include src Makefile
recursive-include src *.pdf
recursive-exclude doc *
recursive-exclude deployment *
+2 -2
View File
@@ -53,6 +53,8 @@ Checking a ticket in
Defaults to ``false`` in which case the server will determine the language (currently
the event default language, might change in the future with support for the
``Accept-Language`` header).
:<json boolean simulate: Do not actually perform the check-in, only simulate the response. The ``position`` response
object will not reflect the simulated changes.
:>json string status: ``"ok"``, ``"incomplete"``, ``"exchange"``, or ``"error"``
:>json string reason: Reason code, only set on status ``"error"``, see below for possible values.
:>json string reason_explanation: Human-readable explanation, only set on status ``"error"`` and reason ``"rules"``, can be null.
@@ -71,8 +73,6 @@ Checking a ticket in
:>json object questions: List of questions to be answered for check-in, only set on status ``"incomplete"``.
:>json object media_policy: Reusable media policy (see documentation on items), only set on status ``"exchange"``.
:>json object media_type: Reusable media type (see documentation on items), only set on status ``"exchange"``.
:>json boolean simulate: Do not actually perform the check-in, only simulate the response. The ``position`` response
object will not reflect the simulated changes.
**Example request**:
+241
View File
@@ -0,0 +1,241 @@
Event Meta Properties
=====================
Resource description
--------------------
An event meta property is used to to define meta information fields for its events.
This information can be re-used, for example, in ticket layouts.
The event meta property resource contains the following public fields:
.. rst-class:: rest-resource-table
===================================== ========================== =======================================================
Field Type Description
===================================== ========================== =======================================================
id integer Unique ID for this property
name string Name of the property
default string Value of the default option
required boolean If ``true``, an event can only be taken live if the
property is set. In event series, it's always optional
to set a value for individual dates
protected boolean If ``true``, the value for an event can only be changed
by organizer-level administrators
filter_public boolean If ``true``, this property will be shown to filter
events in the public event list and calendar
public_label string Public name of the property
filter_allowed boolean If ``true``, this property will be shown to filter
events or reports in the backend, and it can also be
used for hidden filter parameters in the frontend
choices list of objects List of JSON objects representing all permitted values
for this property, or ``null`` for no limitation.
Each choice object has a required internal name named
``key`` and optional public name named ``label``
consisting of a dictionary of i18n string translations
===================================== ========================== =======================================================
Endpoints
---------
.. http:get:: /api/v1/organizers/(organizer)/event_meta_properties/
Returns a list of all meta properties for the organizer.
**Example request**:
.. sourcecode:: http
GET /api/v1/organizers/bigevents/meta_properties/ HTTP/1.1
Host: pretix.eu
Accept: application/json, text/javascript
**Example response**:
.. sourcecode:: http
HTTP/1.1 200 OK
Vary: Accept
Content-Type: application/json
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"id": 1,
"name": "Color",
"default": "blue",
"required": false,
"protected": false,
"filter_public": false,
"public_label": {},
"filter_allowed": true,
"choices": [
{
"key": "blue",
"label": {
"en": "Blue"
},
}
]
}
]
}
:param organizer: The ``slug`` field of the organizer
:statuscode 200: no error
:statuscode 401: Authentication failure
:statuscode 403: The requested organizer does not exist **or** you have no permission to view this resource.
.. http:get:: /api/v1/organizers/(organizer)/event_meta_properties/(id)/
Returns information on one property, identified by its id.
**Example request**:
.. sourcecode:: http
GET /api/v1/organizers/bigevents/event_meta_properties/1/ HTTP/1.1
Host: pretix.eu
Accept: application/json, text/javascript
**Example response**:
.. sourcecode:: http
{
"id": 1,
"name": "Color",
"default": "blue",
"required": false,
"protected": false,
"filter_public": false,
"public_label": {},
"filter_allowed": true,
"choices": null
}
:param organizer: The ``slug`` field of the organizer
:param id: The ``id`` field of the meta property to retrieve
:statuscode 200: no error
:statuscode 401: Authentication failure
:statuscode 403: The requested organizer does not exist **or** you have no permission to view this resource.
.. http:post:: /api/v1/organizers/(organizer)/event_meta_properties/
Creates a new meta property
**Example request**:
.. sourcecode:: http
POST /api/v1/organizers/bigevents/event_meta_properties/ HTTP/1.1
Host: pretix.eu
Accept: application/json, text/javascript
Content-Type: application/json
{
"name": "ref-code",
"default": "abcde",
"required": true,
"choices": null
}
**Example response**:
.. sourcecode:: http
{
"id": 2,
"name": "reference",
"default": "abcde",
"required": true,
"protected": false,
"filter_public": false,
"public_label": null,
"filter_allowed": true,
"choices": null
}
:param organizer: The ``slug`` field of the organizer
:statuscode 201: no error
:statuscode 400: The meta property could not be created due to invalid submitted data.
:statuscode 401: Authentication failure
:statuscode 403: The requested organizer does not exist **or** you have no permission to create this resource.
.. http:patch:: /api/v1/organizers/(organizer)/event_meta_properties/(id)/
Update a meta property. You can also use ``PUT`` instead of ``PATCH``. With ``PUT``, you have to provide
all fields of the resource, other fields will be reset to default. With ``PATCH``, you only need to provide the
fields that you want to change.
You can change all fields of the resource except the ``id`` field.
**Example request**:
.. sourcecode:: http
PATCH /api/v1/organizers/bigevents/event_meta_properties/2/ HTTP/1.1
Host: pretix.eu
Accept: application/json, text/javascript
Content-Type: application/json
Content-Length: 94
{
"required": false
}
**Example response**:
.. sourcecode:: http
HTTP/1.1 200 OK
Vary: Accept
Content-Type: application/json
{
"id": 3,
"name": "reference",
"default": "abcde",
"required": false,
"protected": false,
"filter_public": false,
"public_label": null,
"filter_allowed": true,
"choices": null
}
:param organizer: The ``slug`` field of the organizer
:param id: The ``id`` field of the meta property to modify
:statuscode 200: no error
:statuscode 400: The property could not be modified due to invalid submitted data
:statuscode 401: Authentication failure
:statuscode 403: The requested organizer does not exist **or** you have no permission to change this resource.
.. http:delete:: /api/v1/organizers/(organizer)/event_meta_properties/(id)/
Delete a meta property.
**Example request**:
.. sourcecode:: http
DELETE /api/v1/organizers/bigevents/event_meta_properties/1/ HTTP/1.1
Host: pretix.eu
Accept: application/json, text/javascript
**Example response**:
.. sourcecode:: http
HTTP/1.1 204 No Content
Vary: Accept
:param organizer: The ``slug`` field of the organizer
:param id: The ``id`` field of the meta property to delete
:statuscode 204: no error
:statuscode 401: Authentication failure
:statuscode 403: The requested organizer does not exist **or** you have no permission to delete this resource.
+8 -8
View File
@@ -110,7 +110,7 @@ Endpoints
"plugins": [
"pretix.plugins.banktransfer",
"pretix.plugins.stripe",
"pretix.plugins.paypal",
"pretix.plugins.paypal2",
"pretix.plugins.ticketoutputpdf"
],
"all_sales_channels": false,
@@ -199,7 +199,7 @@ Endpoints
"plugins": [
"pretix.plugins.banktransfer",
"pretix.plugins.stripe",
"pretix.plugins.paypal",
"pretix.plugins.paypal2",
"pretix.plugins.ticketoutputpdf"
],
"valid_keys": {
@@ -262,7 +262,7 @@ Endpoints
"item_meta_properties": {},
"plugins": [
"pretix.plugins.stripe",
"pretix.plugins.paypal"
"pretix.plugins.paypal2"
],
"all_sales_channels": true,
"limit_sales_channels": []
@@ -299,7 +299,7 @@ Endpoints
"item_meta_properties": {},
"plugins": [
"pretix.plugins.stripe",
"pretix.plugins.paypal"
"pretix.plugins.paypal2"
],
"all_sales_channels": true,
"limit_sales_channels": [],
@@ -364,7 +364,7 @@ Endpoints
"item_meta_properties": {},
"plugins": [
"pretix.plugins.stripe",
"pretix.plugins.paypal"
"pretix.plugins.paypal2"
],
"all_sales_channels": true,
"limit_sales_channels": []
@@ -401,7 +401,7 @@ Endpoints
"item_meta_properties": {},
"plugins": [
"pretix.plugins.stripe",
"pretix.plugins.paypal"
"pretix.plugins.paypal2"
],
"all_sales_channels": true,
"limit_sales_channels": [],
@@ -438,7 +438,7 @@ Endpoints
"plugins": [
"pretix.plugins.banktransfer",
"pretix.plugins.stripe",
"pretix.plugins.paypal",
"pretix.plugins.paypal2",
"pretix.plugins.pretixdroid"
]
}
@@ -475,7 +475,7 @@ Endpoints
"plugins": [
"pretix.plugins.banktransfer",
"pretix.plugins.stripe",
"pretix.plugins.paypal",
"pretix.plugins.paypal2",
"pretix.plugins.pretixdroid"
],
"all_sales_channels": true,
+1
View File
@@ -12,6 +12,7 @@ at :ref:`plugin-docs`.
organizers
events
subevents
event_meta_properties
taxrules
categories
items
+1
View File
@@ -116,6 +116,7 @@ Endpoints
:query integer page: The page number in case of a multi-page result set, default is 1
:query string code: Only show the voucher with the given voucher code.
:query string search: Only show the voucher with the given query found in the code, tag, or comment.
:query integer max_usages: Only show vouchers with the given maximal number of usages.
:query integer redeemed: Only show vouchers with the given number of redemptions. Note that this doesn't tell you if
the voucher can still be redeemed, as this also depends on ``max_usages``. See the
-1
View File
@@ -49,7 +49,6 @@ const ignores = globalIgnores([
'src/pretix/static/pretixcontrol/js/ui/editor.js',
'src/pretix/static/pretixcontrol/js/ui/geo.js',
'src/pretix/static/pretixcontrol/js/ui/main.js',
'src/pretix/static/pretixcontrol/js/ui/plugins.js',
'src/pretix/static/pretixcontrol/js/ui/subevent.js',
'src/pretix/static/pretixcontrol/js/ui/variations.js',
'src/pretix/static/pretixcontrol/js/ui/webauthn.js',
+25 -21
View File
@@ -9,8 +9,7 @@
"version": "1.0.0",
"license": "SEE LICENSE IN LICENSE",
"dependencies": {
"vue": "^3.5.30",
"vue-slicksort": "^2.0.5"
"vue": "^3.5.30"
},
"devDependencies": {
"@eslint/js": "^10.0.1",
@@ -295,29 +294,43 @@
}
},
"node_modules/@humanfs/core": {
"version": "0.19.1",
"resolved": "https://registry.npmjs.org/@humanfs/core/-/core-0.19.1.tgz",
"integrity": "sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==",
"version": "0.19.2",
"resolved": "https://registry.npmjs.org/@humanfs/core/-/core-0.19.2.tgz",
"integrity": "sha512-UhXNm+CFMWcbChXywFwkmhqjs3PRCmcSa/hfBgLIb7oQ5HNb1wS0icWsGtSAUNgefHeI+eBrA8I1fxmbHsGdvA==",
"dev": true,
"license": "Apache-2.0",
"dependencies": {
"@humanfs/types": "^0.15.0"
},
"engines": {
"node": ">=18.18.0"
}
},
"node_modules/@humanfs/node": {
"version": "0.16.7",
"resolved": "https://registry.npmjs.org/@humanfs/node/-/node-0.16.7.tgz",
"integrity": "sha512-/zUx+yOsIrG4Y43Eh2peDeKCxlRt/gET6aHfaKpuq267qXdYDFViVHfMaLyygZOnl0kGWxFIgsBy8QFuTLUXEQ==",
"version": "0.16.8",
"resolved": "https://registry.npmjs.org/@humanfs/node/-/node-0.16.8.tgz",
"integrity": "sha512-gE1eQNZ3R++kTzFUpdGlpmy8kDZD/MLyHqDwqjkVQI0JMdI1D51sy1H958PNXYkM2rAac7e5/CnIKZrHtPh3BQ==",
"dev": true,
"license": "Apache-2.0",
"dependencies": {
"@humanfs/core": "^0.19.1",
"@humanfs/core": "^0.19.2",
"@humanfs/types": "^0.15.0",
"@humanwhocodes/retry": "^0.4.0"
},
"engines": {
"node": ">=18.18.0"
}
},
"node_modules/@humanfs/types": {
"version": "0.15.0",
"resolved": "https://registry.npmjs.org/@humanfs/types/-/types-0.15.0.tgz",
"integrity": "sha512-ZZ1w0aoQkwuUuC7Yf+7sdeaNfqQiiLcSRbfI08oAxqLtpXQr9AIVX7Ay7HLDuiLYAaFPu8oBYNq/QIi9URHJ3Q==",
"dev": true,
"license": "Apache-2.0",
"engines": {
"node": ">=18.18.0"
}
},
"node_modules/@humanwhocodes/module-importer": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz",
@@ -3381,9 +3394,9 @@
}
},
"node_modules/postcss-selector-parser": {
"version": "7.1.1",
"resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.1.1.tgz",
"integrity": "sha512-orRsuYpJVw8LdAwqqLykBj9ecS5/cRHlI5+nvTo8LcCKmzDmqVORXtOIYEEQuL9D4BxtA1lm5isAqzQZCoQ6Eg==",
"version": "7.1.5",
"resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.1.5.tgz",
"integrity": "sha512-KvvtD7SrlBP7dlgkBghEE3r84CABm5SmV2aNcG4oCA+qDnJ/tvKonFVvwWAyyWUEwxuNawdfEAZKP9zM3oZ2Uw==",
"dev": true,
"license": "MIT",
"dependencies": {
@@ -4636,15 +4649,6 @@
"vue-eslint-parser": "^10.0.0"
}
},
"node_modules/vue-slicksort": {
"version": "2.0.5",
"resolved": "https://registry.npmjs.org/vue-slicksort/-/vue-slicksort-2.0.5.tgz",
"integrity": "sha512-fXz1YrNjhUbJK7o0tMk27mIr4pMAZYLSYvtmLazCtfpvz+zafPCn34ILDL8B7hT7WLVZKreYs6JVe5VWymqmzA==",
"license": "MIT",
"peerDependencies": {
"vue": ">=3.0.0"
}
},
"node_modules/which": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz",
+1 -2
View File
@@ -27,8 +27,7 @@
"test": "echo \"Error: no test specified\" && exit 1"
},
"dependencies": {
"vue": "^3.5.30",
"vue-slicksort": "^2.0.5"
"vue": "^3.5.30"
},
"devDependencies": {
"@eslint/js": "^10.0.1",
+10 -9
View File
@@ -33,14 +33,14 @@ dependencies = [
"bleach==6.4.*",
"celery==5.6.*",
"chardet==5.2.*",
"cryptography>=50.0.0",
"cryptography>=50.0.1",
"css-inline==0.21.*",
"defusedcsv>=3.0.0",
"dnspython==2.*",
"Django[argon2]==5.2.*,>=5.2.17",
"django-bootstrap3==26.2",
"django-compressor==4.6.0",
"django-countries==9.0.*",
"django-countries==9.1.*",
"django-filter==26.1",
"django-formset-js-improved==0.5.0.5",
"django-formtools==2.7",
@@ -67,7 +67,7 @@ dependencies = [
"kombu==5.6.*",
"libsass==0.23.*",
"lxml",
"markdown==3.10.3", # 3.3.5 requires importlib-metadata>=4.4, but django-bootstrap3 requires importlib-metadata<3.
"markdown==3.11", # 3.3.5 requires importlib-metadata>=4.4, but django-bootstrap3 requires importlib-metadata<3.
# We can upgrade markdown again once django-bootstrap3 upgrades or once we drop Python 3.6 and 3.7
"mt-940==4.30.*",
"oauthlib==3.3.*",
@@ -75,7 +75,7 @@ dependencies = [
"packaging",
"paypalrestsdk==1.13.*",
"paypal-checkout-serversdk==1.0.*",
"PyJWT==2.13.*",
"PyJWT==2.15.*",
"phonenumberslite==9.0.*",
"Pillow==12.3.*",
"pretix-plugin-build",
@@ -84,7 +84,7 @@ dependencies = [
"pycountry",
"pycparser==3.0",
"pycryptodome==3.23.*",
"pypdf==6.11.*",
"pypdf==6.19.*",
"python-bidi==0.6.*", # Support for Arabic in reportlab
"python-dateutil==2.9.*",
"pytz",
@@ -94,7 +94,7 @@ dependencies = [
"redis==7.4.*",
"reportlab==5.0.*",
"requests==2.34.*",
"sentry-sdk==2.68.*",
"sentry-sdk==2.70.*",
"sepaxml==2.7.*",
"stripe==7.9.*",
"text-unidecode==1.*",
@@ -112,10 +112,10 @@ dev = [
"aiohttp==3.14.*",
"coverage",
"coveralls",
"fakeredis==2.37.*",
"flake8==7.3.*",
"fakeredis==2.38.*",
"flake8==7.4.*",
"freezegun",
"isort==8.0.*",
"isort==9.0.*",
"pep8-naming==0.15.*",
"potypo",
"pytest-asyncio>=1.4.0",
@@ -129,6 +129,7 @@ dev = [
"pytest==9.1.*",
"playwright",
"responses",
"pypdfium2"
]
[project.entry-points."distutils.commands"]
-1
View File
@@ -26,7 +26,6 @@ ignore =
src/tests/plugins/*
src/tests/plugins/badges/*
src/tests/plugins/banktransfer/*
src/tests/plugins/paypal/*
src/tests/plugins/paypal2/*
src/tests/plugins/pretixdroid/*
src/tests/plugins/stripe/*
+2
View File
@@ -30,3 +30,5 @@ npminstall:
npmbuild:
npm run build
licenseheaders:
licenseheaders -t ../.licenseheader -E .py -x "*/migrations/*.py"
+1 -1
View File
@@ -19,4 +19,4 @@
# You should have received a copy of the GNU Affero General Public License along with this program. If not, see
# <https://www.gnu.org/licenses/>.
#
__version__ = "2026.8.0.dev0"
__version__ = "2026.8.0"
@@ -19,13 +19,12 @@
# You should have received a copy of the GNU Affero General Public License along with this program. If not, see
# <https://www.gnu.org/licenses/>.
#
from django.dispatch import receiver
from pretix.base.signals import register_payment_providers
def get_session_key_for_api_auth(user, auth):
if user.is_authenticated:
return f'api-upload-User-{user.pk}'
else:
return f'api-upload-{str(type(auth))}-{auth.pk}'
@receiver(register_payment_providers, dispatch_uid="payment_paypal")
def register_payment_provider(sender, **kwargs):
from .payment import Paypal
return Paypal
def get_session_key_for_api_request(request):
return get_session_key_for_api_auth(request.user, request.auth)
+4
View File
@@ -101,6 +101,10 @@ class OAuthAccessToken(AbstractAccessToken):
self.expires = now() - timedelta(hours=1)
self.save(update_fields=['expires'])
def is_valid(self, scopes=None):
# Can maybe be removed after upgrading django-oauth-toolkit to 3.4.1
return super().is_valid(scopes) and self.application.is_usable(None)
class OAuthRefreshToken(AbstractRefreshToken):
application = models.ForeignKey(
+1 -1
View File
@@ -979,7 +979,7 @@ class DeviceEventSettingsSerializer(EventSettingsSerializer):
'reusable_media_type_nfc_mf0aes',
'reusable_media_type_nfc_mf0aes_random_uid',
'reusable_media_usage_enforced',
'system_question_order', # TODO(questionnaires) - remove or replace
'system_question_order',
'tax_rule_payment',
'tax_rule_cancellation',
]
+9 -1
View File
@@ -37,6 +37,8 @@ from collections import OrderedDict
from django.core.exceptions import ValidationError
from rest_framework import serializers
from pretix.api.auth.utils import get_session_key_for_api_request
def remove_duplicates_from_list(data):
return list(OrderedDict.fromkeys(data))
@@ -83,10 +85,16 @@ class UploadedFileField(serializers.Field):
request = self.context.get('request', None)
try:
cf = CachedFile.objects.get(
session_key=f'api-upload-{str(type(request.user or request.auth))}-{(request.user or request.auth).pk}',
file__isnull=False,
pk=data[len("file:"):],
)
if cf.session_key == "api-upload-<class 'django.contrib.auth.models.AnonymousUser'>-None":
# OK, backwards-compatibility of a security bug fixed 2026-09, delete this at some point, but should
# also be harmless because all files with this key are expired one day after deployment of this fix
# and no new files with this key are created
pass
elif cf.session_key != get_session_key_for_api_request(request):
self.fail('not_found')
except (ValidationError, IndexError): # invalid uuid
self.fail('not_found')
except CachedFile.DoesNotExist:
+1 -157
View File
@@ -53,7 +53,6 @@ from pretix.base.models import (
ItemVariation, ItemVariationMetaValue, Question, QuestionOption, Quota,
SalesChannel,
)
from pretix.base.models.items import Questionnaire, QuestionnaireChild
class InlineItemVariationSerializer(SalesChannelMigrationMixin, I18nAwareModelSerializer):
@@ -543,7 +542,6 @@ class LegacyDependencyValueField(serializers.CharField):
class QuestionSerializer(I18nAwareModelSerializer):
options = InlineQuestionOptionSerializer(many=True, required=False)
identifier = serializers.CharField(allow_null=True)
internal_name = serializers.CharField(allow_null=True, source='question', read_only=True)
dependency_value = LegacyDependencyValueField(source='dependency_values', required=False, allow_null=True)
class Meta:
@@ -552,7 +550,7 @@ class QuestionSerializer(I18nAwareModelSerializer):
'ask_during_checkin', 'show_during_checkin', 'identifier', 'dependency_question', 'dependency_values',
'hidden', 'dependency_value', 'print_on_invoice', 'help_text', 'valid_number_min',
'valid_number_max', 'valid_date_min', 'valid_date_max', 'valid_datetime_min', 'valid_datetime_max',
'valid_string_length_max', 'valid_string_length_min', 'valid_file_portrait', 'internal_name',)
'valid_string_length_max', 'valid_string_length_min', 'valid_file_portrait')
def validate_identifier(self, value):
Question._clean_identifier(self.context['event'], value, self.instance)
@@ -628,160 +626,6 @@ class QuestionSerializer(I18nAwareModelSerializer):
return question
class QuestionRefField(serializers.PrimaryKeyRelatedField):
def to_representation(self, qc):
if not qc:
return None
elif qc.system_datafield:
return qc.system_datafield
elif qc.user_datafield_id:
return qc.user_datafield_id
else:
return None
def to_internal_value(self, data):
if type(data) == int:
return {'user_datafield': super().to_internal_value(data), 'system_datafield': None}
elif type(data) == str or data is None:
return {'user_datafield': None, 'system_datafield': data}
else:
self.fail('incorrect_type', data_type=type(data).__name__)
def use_pk_only_optimization(self):
return self.source == '*'
class InlineQuestionnaireChildSerializer(I18nAwareModelSerializer):
question = QuestionRefField(source='*', queryset=Question.objects.none())
dependency_question = QuestionRefField(allow_null=True, required=False, queryset=Question.objects.none())
class Meta:
model = QuestionnaireChild
fields = ('question', 'required', 'label', 'help_text', 'dependency_question', 'dependency_values')
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.fields["question"].queryset = self.context["event"].questions.all()
self.fields["dependency_question"].queryset = self.context["event"].questions.all()
def validate(self, data):
data = super().validate(data)
event = self.context['event']
full_data = self.to_internal_value(self.to_representation(self.instance)) if self.instance else {}
full_data.update(data)
if full_data.get('ask_during_checkin') and full_data.get('dependency_question'):
raise ValidationError('Dependencies are not supported during check-in.')
dep = full_data.get('dependency_question')
if dep:
if dep.ask_during_checkin:
raise ValidationError(_('Question cannot depend on a question asked during check-in.'))
seen_ids = {self.instance.pk} if self.instance else set()
while dep:
if dep.pk in seen_ids:
raise ValidationError(_('Circular dependency between questions detected.'))
seen_ids.add(dep.pk)
dep = dep.dependency_question
return data
def validate_dependency_question(self, value):
if value:
if value.type not in (Question.TYPE_CHOICE, Question.TYPE_BOOLEAN, Question.TYPE_CHOICE_MULTIPLE):
raise ValidationError('Question dependencies can only be set to boolean or choice questions.')
if value == self.instance:
raise ValidationError('A question cannot depend on itself.')
return value
class QuestionnaireSerializer(I18nAwareModelSerializer):
limit_sales_channels = serializers.SlugRelatedField(
slug_field="identifier",
queryset=SalesChannel.objects.none(),
required=False,
allow_empty=True,
many=True,
)
class Meta:
model = Questionnaire
fields = ('id', 'type', 'internal_name', 'items', 'position', 'all_sales_channels', 'limit_sales_channels', 'children')
def __init__(self, *args, **kwargs):
self.fields['children'] = InlineQuestionnaireChildSerializer(many=True, required=True, context=kwargs['context'], partial=False)
super().__init__(*args, **kwargs)
def validate(self, data):
data = super().validate(data)
event = self.context['event']
#full_data = self.to_internal_value(self.to_representation(self.instance)) if self.instance else {}
#full_data.update(data)
#if full_data.get('ask_during_checkin') and full_data.get('dependency_question'):
# raise ValidationError('Dependencies are not supported during check-in.')
#if full_data.get('ask_during_checkin') and full_data.get('type') in Question.ASK_DURING_CHECKIN_UNSUPPORTED:
# raise ValidationError(_('This type of question cannot be asked during check-in.'))
#if full_data.get('show_during_checkin') and full_data.get('type') in Question.SHOW_DURING_CHECKIN_UNSUPPORTED:
# raise ValidationError(_('This type of question cannot be shown during check-in.'))
#Question.clean_items(event, full_data.get('items') or [])
return data
def validate_children(self, value):
prev_questions = {}
for child in value:
if child.get('dependency_question'):
if (child['dependency_question']['user_datafield'] or child['dependency_question']['system_datafield']) not in prev_questions:
raise ValidationError('A question can only depend on a previous question from the same questionnaire.')
if child['user_datafield']:
prev_questions[child['user_datafield']] = child
if child['system_datafield']:
prev_questions[child['system_datafield']] = child
return value
@transaction.atomic
def create(self, validated_data):
children_data = validated_data.pop('children') if 'children' in validated_data else []
questionnaire = super().create(validated_data)
self.set_children(questionnaire, children_data)
return questionnaire
@transaction.atomic
def update(self, instance, validated_data):
children_data = validated_data.pop('children', None)
questionnaire = super().update(instance, validated_data)
if children_data is not None:
self.set_children(questionnaire, children_data)
return questionnaire
def set_children(self, questionnaire, new_data):
result = []
child_serializer = self.fields['children'].child
existing = questionnaire.children.all()
for i, d in enumerate(new_data):
d['questionnaire'] = questionnaire
d['position'] = i + 1
d.setdefault('required', False)
d.setdefault('help_text', None)
d.setdefault('dependency_question', None)
d.setdefault('dependency_values', None)
updatable = min(len(existing), len(new_data))
for i in range(0, updatable):
result.append(child_serializer.update(existing[i], new_data[i]))
for i in range(updatable, len(new_data)):
result.append(child_serializer.create(new_data[i]))
for i in range(updatable, len(existing)):
existing[i].delete()
return result
class QuotaSerializer(I18nAwareModelSerializer):
available = serializers.BooleanField(read_only=True)
available_number = serializers.IntegerField(read_only=True)
+10 -4
View File
@@ -41,6 +41,7 @@ from rest_framework.exceptions import ValidationError
from rest_framework.relations import SlugRelatedField
from rest_framework.reverse import reverse
from pretix.api.auth.utils import get_session_key_for_api_request
from pretix.api.serializers import CompatDecimalField, CompatibleJSONField
from pretix.api.serializers.event import SubEventSerializer
from pretix.api.serializers.forms import form_field_to_serializer_field
@@ -258,16 +259,21 @@ class AnswerSerializer(I18nAwareModelSerializer):
if data['answer'] == 'file:keep':
return data
try:
ao = self.context["request"].user or self.context["request"].auth
cf = CachedFile.objects.get(
session_key=f'api-upload-{str(type(ao))}-{ao.pk}',
file__isnull=False,
pk=data['answer'][len("file:"):],
)
if cf.session_key == "api-upload-<class 'django.contrib.auth.models.AnonymousUser'>-None":
# OK, backwards-compatibility of a security bug fixed 2026-09, delete this at some point, but should
# also be harmless because all files with this key are expired one day after deployment of this fix
# and no new files with this key are created
pass
elif cf.session_key != get_session_key_for_api_request(self.context["request"]):
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data['answer']))
except (ValidationError, IndexError): # invalid uuid
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data))
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data['answer']))
except CachedFile.DoesNotExist:
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data))
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data['answer']))
allowed_types = (
'image/png', 'image/jpeg', 'image/gif', 'application/pdf'
+90 -3
View File
@@ -28,6 +28,7 @@ from django.db import transaction
from django.db.models import Q
from django.utils.crypto import get_random_string
from django.utils.translation import gettext, gettext_lazy as _
from i18nfield.rest_framework import I18nField
from rest_framework import serializers
from rest_framework.exceptions import ValidationError
@@ -40,9 +41,10 @@ from pretix.api.serializers.settings import SettingsSerializer
from pretix.base.auth import get_auth_backends
from pretix.base.i18n import get_language_without_region
from pretix.base.models import (
Customer, Device, GiftCard, GiftCardAcceptance, GiftCardTransaction,
Membership, MembershipType, OrderPosition, Organizer, ReusableMedium,
SalesChannel, SeatingPlan, Team, TeamAPIToken, TeamInvite, User,
Customer, Device, EventMetaProperty, GiftCard, GiftCardAcceptance,
GiftCardTransaction, Membership, MembershipType, OrderPosition, Organizer,
ReusableMedium, SalesChannel, SeatingPlan, Team, TeamAPIToken, TeamInvite,
User,
)
from pretix.base.models.seating import SeatingPlanLayoutValidator
from pretix.base.permissions import (
@@ -640,3 +642,88 @@ class OrganizerSettingsSerializer(SettingsSerializer):
)
# TODO: make sure pub is always correct
return 'pub/' + fname
class MetaPropertyListField(serializers.ListField):
def __init__(self, *args, **kwargs):
kwargs["validators"] = kwargs.pop("validators", [])
def validate_keys_unique(choices):
if not choices:
return
keys = [c.get("key") for c in choices]
if len(set(keys)) < len(keys):
raise ValidationError("The key for each meta property value option must be unique.")
kwargs["validators"].append(
validate_keys_unique
)
super().__init__(*args, **kwargs)
class MetaPropertyDictField(serializers.DictField):
def __init__(self, **kwargs):
self.label_child = kwargs.pop("label_child", I18nField())
super().__init__(**kwargs)
def to_representation(self, value):
# django added unneccessary keys DELETE, ORDER through formsets, filter them here for backwards compat
d = {
"key": value["key"]
}
if "label" in value:
d["label"] = self.label_child.to_representation(value["label"])
return super().to_representation(d)
def to_internal_value(self, data):
if not isinstance(data, dict):
raise ValidationError("Meta property value options must be a dict.")
if not isinstance(data.get("key"), str):
raise ValidationError("Meta property value options must have a key of type string.")
if any(k not in {"key", "label"} for k in data.keys()):
raise ValidationError("Meta property value options may only have a key and optionally a label.")
if "label" in data:
try:
data["label"] = self.label_child.to_internal_value(data["label"])
except ValidationError as e:
raise ValidationError({"label": e.detail})
return super().to_internal_value(data)
class EventMetaPropertiesSerializer(I18nAwareModelSerializer):
choices = MetaPropertyListField(
child=MetaPropertyDictField(
label_child=I18nField()
),
allow_null=True,
)
class Meta:
model = EventMetaProperty
fields = (
'id', 'name', 'default', 'required', 'protected', 'filter_public', 'public_label', 'filter_allowed',
'choices'
)
def validate(self, data):
data = super().validate(data)
full_data = self.to_internal_value(self.to_representation(self.instance)) if self.instance else {}
full_data.update(data)
choices = full_data.get("choices")
default = full_data.get("default")
if choices and default:
choice_keys = [c.get("key") for c in choices]
if default not in choice_keys:
raise ValidationError("You cannot set a default value that is not a valid value.")
if not choices and "choices" in data:
# normalize empty dict to None
data["choices"] = None
return data
+2 -2
View File
@@ -68,6 +68,7 @@ orga_router.register(r'scheduled_exports', exporters.ScheduledOrganizerExportVie
orga_router.register(r'exporters', exporters.OrganizerExportersViewSet, basename='exporters')
orga_router.register(r'transactions', order.OrganizerTransactionViewSet)
orga_router.register(r'orderpositions', order.OrganizerOrderPositionViewSet, basename='orderpositions')
orga_router.register(r'event_meta_properties', organizer.EventMetaPropertiesViewSet)
team_router = routers.DefaultRouter()
team_router.register(r'members', organizer.TeamMemberViewSet)
@@ -79,8 +80,7 @@ event_router.register(r'subevents', event.SubEventViewSet)
event_router.register(r'clone', event.CloneEventViewSet)
event_router.register(r'items', item.ItemViewSet)
event_router.register(r'categories', item.ItemCategoryViewSet)
event_router.register(r'datafields', item.QuestionViewSet)
event_router.register(r'questionnaires', item.QuestionnaireViewSet)
event_router.register(r'questions', item.QuestionViewSet)
event_router.register(r'discounts', discount.DiscountViewSet)
event_router.register(r'quotas', item.QuotaViewSet)
event_router.register(r'vouchers', voucher.VoucherViewSet)
+8 -1
View File
@@ -50,6 +50,7 @@ from rest_framework.generics import ListAPIView
from rest_framework.permissions import SAFE_METHODS
from rest_framework.response import Response
from pretix.api.auth.utils import get_session_key_for_api_auth
from pretix.api.serializers.checkin import (
CheckinListSerializer, CheckinRPCAnnulInputSerializer,
CheckinRPCRedeemInputSerializer, MiniCheckinListSerializer,
@@ -331,10 +332,16 @@ with scopes_disabled():
def _handle_file_upload(data, user, auth):
try:
cf = CachedFile.objects.get(
session_key=f'api-upload-{str(type(user or auth))}-{(user or auth).pk}',
file__isnull=False,
pk=data[len("file:"):],
)
if cf.session_key == "api-upload-<class 'django.contrib.auth.models.AnonymousUser'>-None":
# OK, backwards-compatibility of a security bug fixed 2026-09, delete this at some point, but should
# also be harmless because all files with this key are expired one day after deployment of this fix
# and no new files with this key are created
pass
elif cf.session_key != get_session_key_for_api_auth(user, auth):
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data))
except (ValidationError, BaseValidationError, IndexError): # invalid uuid
raise ValidationError('The submitted file ID "{fid}" was not found.'.format(fid=data))
except CachedFile.DoesNotExist:
+1 -48
View File
@@ -48,15 +48,13 @@ from pretix.api.pagination import TotalOrderingFilter
from pretix.api.serializers.item import (
ItemAddOnSerializer, ItemBundleSerializer, ItemCategorySerializer,
ItemProgramTimeSerializer, ItemSerializer, ItemVariationSerializer,
QuestionnaireSerializer, QuestionOptionSerializer, QuestionSerializer,
QuotaSerializer,
QuestionOptionSerializer, QuestionSerializer, QuotaSerializer,
)
from pretix.api.views import ConditionalListView
from pretix.base.models import (
CartPosition, Item, ItemAddOn, ItemBundle, ItemCategory, ItemProgramTime,
ItemVariation, Question, QuestionOption, Quota,
)
from pretix.base.models.items import Questionnaire
from pretix.base.services.quotas import QuotaAvailability
from pretix.helpers.dicts import merge_dicts
from pretix.helpers.i18n import i18ncomp
@@ -568,51 +566,6 @@ class QuestionOptionViewSet(viewsets.ModelViewSet):
super().perform_destroy(instance)
class QuestionnaireViewSet(ConditionalListView, viewsets.ModelViewSet):
serializer_class = QuestionnaireSerializer
queryset = Questionnaire.objects.none()
#filter_backends = (DjangoFilterBackend, TotalOrderingFilter)
#filterset_class = QuestionFilter
ordering_fields = ('id', 'position')
ordering = ('position', 'id')
permission = None
write_permission = 'event.items:write'
def get_queryset(self):
return self.request.event.questionnaires.prefetch_related('children').all()
def perform_create(self, serializer):
serializer.save(event=self.request.event)
serializer.instance.log_action(
'pretix.event.questionnaire.added',
user=self.request.user,
auth=self.request.auth,
data=self.request.data
)
def get_serializer_context(self):
ctx = super().get_serializer_context()
ctx['event'] = self.request.event
return ctx
def perform_update(self, serializer):
serializer.save(event=self.request.event)
serializer.instance.log_action(
'pretix.event.questionnaire.changed',
user=self.request.user,
auth=self.request.auth,
data=self.request.data
)
def perform_destroy(self, instance):
instance.log_action(
'pretix.event.questionnaire.deleted',
user=self.request.user,
auth=self.request.auth,
)
super().perform_destroy(instance)
class NumberInFilter(django_filters.BaseInFilter, django_filters.NumberFilter):
pass
+51 -4
View File
@@ -44,15 +44,16 @@ from pretix.api.models import OAuthAccessToken
from pretix.api.pagination import TotalOrderingFilter
from pretix.api.serializers.organizer import (
CustomerCreateSerializer, CustomerSerializer, DeviceSerializer,
GiftCardSerializer, GiftCardTransactionSerializer, MembershipSerializer,
EventMetaPropertiesSerializer, GiftCardSerializer,
GiftCardTransactionSerializer, MembershipSerializer,
MembershipTypeSerializer, OrganizerSerializer, OrganizerSettingsSerializer,
SalesChannelSerializer, SeatingPlanSerializer, TeamAPITokenSerializer,
TeamInviteSerializer, TeamMemberSerializer, TeamSerializer,
)
from pretix.base.models import (
Customer, Device, Event, GiftCard, GiftCardTransaction, LogEntry,
Membership, MembershipType, Organizer, SalesChannel, SeatingPlan, Team,
TeamAPIToken, TeamInvite, User,
Customer, Device, Event, EventMetaProperty, GiftCard, GiftCardTransaction,
LogEntry, Membership, MembershipType, Organizer, SalesChannel, SeatingPlan,
Team, TeamAPIToken, TeamInvite, User,
)
from pretix.base.plugins import (
PLUGIN_LEVEL_EVENT, PLUGIN_LEVEL_EVENT_ORGANIZER_HYBRID,
@@ -846,3 +847,49 @@ class SalesChannelViewSet(viewsets.ModelViewSet):
data={'id': instance.pk}
)
instance.delete()
class EventMetaPropertiesViewSet(viewsets.ModelViewSet):
serializer_class = EventMetaPropertiesSerializer
queryset = EventMetaProperty.objects.none()
write_permission = 'organizer.settings.general:write'
def get_queryset(self):
return self.request.organizer.meta_properties.all()
def get_serializer_context(self):
ctx = super().get_serializer_context()
ctx['organizer'] = self.request.organizer
return ctx
@transaction.atomic()
def perform_destroy(self, instance):
instance.log_action(
'pretix.property.deleted',
user=self.request.user,
auth=self.request.auth,
data={'id': instance.pk}
)
instance.delete()
@transaction.atomic()
def perform_create(self, serializer):
inst = serializer.save(organizer_id=self.request.organizer.pk)
serializer.instance.log_action(
'pretix.property.created',
user=self.request.user,
auth=self.request.auth,
data=self.request.data,
)
return inst
@transaction.atomic()
def perform_update(self, serializer):
inst = serializer.save(organizer_id=self.request.organizer.pk)
serializer.instance.log_action(
'pretix.property.changed',
user=self.request.user,
auth=self.request.auth,
data=self.request.data,
)
return inst
+2 -1
View File
@@ -33,6 +33,7 @@ from rest_framework.views import APIView
from pretix.api.auth.device import DeviceTokenAuthentication
from pretix.api.auth.permission import AnyAuthenticatedClientPermission
from pretix.api.auth.token import TeamTokenAuthentication
from pretix.api.auth.utils import get_session_key_for_api_request
from pretix.base.models import CachedFile
from pretix.helpers.images import (
IMAGE_TYPES, validate_uploaded_file_for_valid_image,
@@ -78,7 +79,7 @@ class UploadView(APIView):
web_download=False,
filename=file_obj.name,
type=content_type,
session_key=f'api-upload-{str(type(request.user or request.auth))}-{(request.user or request.auth).pk}'
session_key=get_session_key_for_api_request(request)
)
cf.file.save(file_obj.name, file_obj)
cf.save()
+4
View File
@@ -40,6 +40,7 @@ with scopes_disabled():
class VoucherFilter(FilterSet):
active = BooleanFilter(method='filter_active')
code = CharFilter(lookup_expr='iexact')
search = CharFilter(method='search_qs')
class Meta:
model = Voucher
@@ -54,6 +55,9 @@ with scopes_disabled():
return queryset.filter(Q(redeemed__gte=F('max_usages')) |
(Q(valid_until__isnull=False) & Q(valid_until__lte=now())))
def search_qs(self, qs, name, value):
return qs.filter(Q(code__icontains=value) | Q(tag__icontains=value) | Q(comment__icontains=value))
class VoucherViewSet(viewsets.ModelViewSet):
serializer_class = VoucherSerializer
+7 -3
View File
@@ -27,7 +27,7 @@ from datetime import timedelta
from functools import cached_property
from typing import List, Optional, Protocol
import sentry_sdk
from django.conf import settings
from django.db import DatabaseError, transaction
from django.utils.timezone import now
from django.utils.translation import gettext_lazy as _
@@ -236,7 +236,9 @@ class OutboundSyncProvider:
# model changes saved by set_sync_error / clear_in_flight calls below
if sq.failed_attempts >= self.max_attempts:
logger.exception('Failed to sync order (max attempts exceeded)')
sentry_sdk.capture_exception(e)
if settings.SENTRY_ENABLED:
import sentry_sdk
sentry_sdk.capture_exception(e)
sq.set_sync_error("exceeded", e.messages, e.full_message)
else:
logger.info(
@@ -247,7 +249,9 @@ class OutboundSyncProvider:
sq.clear_in_flight()
except Exception as e:
logger.exception('Failed to sync order (unhandled exception)')
sentry_sdk.capture_exception(e)
if settings.SENTRY_ENABLED:
import sentry_sdk
sentry_sdk.capture_exception(e)
sq.set_sync_error("internal", [], str(e))
@cached_property
+27 -4
View File
@@ -54,6 +54,7 @@ from ...control.forms.filter import get_all_payment_providers
from ...helpers import GroupConcat
from ...helpers.iter import chunked_iterable
from ..exporter import BaseExporter, MultiSheetListExporter
from ..invoicing.transmission import get_transmission_types
from ..services.export import ExportError
from ..services.invoices import invoice_pdf_task
from ..signals import (
@@ -197,7 +198,7 @@ class InvoiceDataExporter(InvoiceExporterMixin, MultiSheetListExporter):
def iterate_sheet(self, form_data, sheet):
_ = gettext
if sheet == 'invoices':
yield [
headers = [
_('Invoice number'),
_('Date'),
_('Order code'),
@@ -230,8 +231,18 @@ class InvoiceDataExporter(InvoiceExporterMixin, MultiSheetListExporter):
_('Total value (without taxes)'),
_('Payment matching IDs'),
_('Payment providers'),
_('Transmission type'),
_('Transmission status'),
_('Transmission date'),
]
transmission_types = get_transmission_types()
for tt in transmission_types:
for c in tt.describe_info_columns():
headers.append(str(tt.verbose_name) + ': ' + str(c))
yield headers
p_providers = OrderPayment.objects.filter(
order=OuterRef('order'),
state__in=(OrderPayment.PAYMENT_STATE_CONFIRMED, OrderPayment.PAYMENT_STATE_REFUNDED,
@@ -242,7 +253,7 @@ class InvoiceDataExporter(InvoiceExporterMixin, MultiSheetListExporter):
'm'
).order_by()
base_qs = self.invoices_queryset(form_data)\
base_qs = self.invoices_queryset(form_data)
qs = base_qs.select_related(
'order', 'refers'
@@ -280,7 +291,7 @@ class InvoiceDataExporter(InvoiceExporterMixin, MultiSheetListExporter):
if mid:
pmis.append(mid)
pmi = '\n'.join(pmis)
yield [
line = [
i.full_invoice_no,
date_format(i.date, "SHORT_DATE_FORMAT"),
i.order.code,
@@ -315,8 +326,20 @@ class InvoiceDataExporter(InvoiceExporterMixin, MultiSheetListExporter):
', '.join([
str(self.providers.get(p, p)) for p in sorted(set((i.payment_providers or '').split(',')))
if p and p != 'free'
])
]),
i.transmission_type_instance.verbose_name,
i.get_transmission_status_display(),
date_format(i.transmission_date, "SHORT_DATETIME_FORMAT") if i.transmission_date else "",
]
for tt in transmission_types:
if tt.identifier == i.transmission_type:
described = dict(tt.describe_info(i.invoice_to_transmission_info, i.invoice_to_country, i.invoice_to_is_business))
for c in tt.describe_info_columns():
line.append(described.get(c, ""))
else:
for c in tt.describe_info_columns():
line.append("")
yield line
elif sheet == 'lines':
yield [
_('Invoice number'),
+155 -117
View File
@@ -36,6 +36,7 @@ import copy
import json
import logging
import re
from collections import namedtuple
from datetime import timedelta
from decimal import Decimal
from io import BytesIO
@@ -599,12 +600,16 @@ class PortraitImageField(SizeValidationMixin, ExtValidationMixin, forms.FileFiel
image = ImageOps.exif_transpose(image)
if f._cropdata:
image = image.crop((
f._cropdata.get('x', 0),
f._cropdata.get('y', 0),
f._cropdata.get('x', 0) + f._cropdata.get('width', image.width),
f._cropdata.get('y', 0) + f._cropdata.get('height', image.height),
))
left = int(f._cropdata.get('x', 0))
top = int(f._cropdata.get('y', 0))
right = left + int(f._cropdata.get('width', image.width))
bottom = top + int(f._cropdata.get('height', image.height))
if left >= image.width or top >= image.height or right > image.width or bottom > image.height:
raise ValidationError(
self.error_messages['max_dimension'],
code='max_dimension',
)
image = image.crop((left, top, right, bottom))
with BytesIO() as output:
# This might use a lot of memory, but temporary files are not a good option since
# we don't control the cleanup
@@ -642,22 +647,49 @@ class PortraitImageField(SizeValidationMixin, ExtValidationMixin, forms.FileFiel
super().__init__(*args, **kwargs)
FakeQuestion = namedtuple(
'FakeQuestion', 'id question position required help_text container_type', defaults=('', Question.ContainerType.ORDERPOSITION)
)
def get_fake_attendee_questions(settings):
fq = []
sqo = settings.system_question_order
if settings.attendee_names_asked:
fq.append(FakeQuestion('attendee_name_parts', _('Attendee name'), sqo.get('attendee_name_parts', 0), settings.attendee_names_required))
if settings.attendee_emails_asked:
fq.append(FakeQuestion('attendee_email', _('Attendee email'), sqo.get('attendee_email', 0), settings.attendee_emails_required))
if settings.attendee_company_asked:
fq.append(FakeQuestion('company', _('Company'), sqo.get('company', 0), settings.attendee_company_required))
if settings.attendee_addresses_asked:
fq.append(FakeQuestion('street', _('Street'), sqo.get('street', 0), settings.attendee_addresses_required))
fq.append(FakeQuestion('zipcode', _('ZIP code'), sqo.get('zipcode', 0), settings.attendee_addresses_required))
fq.append(FakeQuestion('city', _('City'), sqo.get('city', 0), settings.attendee_addresses_required))
fq.append(FakeQuestion('state', _('State'), sqo.get('country', 0), settings.attendee_addresses_required))
fq.append(FakeQuestion('country', _('Country'), sqo.get('country', 0), settings.attendee_addresses_required))
return fq
class BaseQuestionsForm(forms.Form):
"""
This is the base form class responsible for asking order- or ticket-related questions.
"""
address_validation = False
def build_user_question_field(self, request, event, answerlist, qc, datafield):
def build_user_question_field(self, request, event, answerlist, q):
# Do we already have an answer? Provide it as the initial value
answers = [a for a in answerlist if a.question_id == datafield.id]
answers = [a for a in answerlist if a.question_id == q.id]
if answers:
initial = answers[0]
else:
initial = None
tz = ZoneInfo(event.settings.timezone)
required = qc.required and not self.all_optional
if datafield.type == Question.TYPE_BOOLEAN:
required = q.required and not self.all_optional
if q.type == Question.TYPE_BOOLEAN:
if required:
# For some reason, django-bootstrap3 does not set the required attribute
# itself.
@@ -671,105 +703,107 @@ class BaseQuestionsForm(forms.Form):
initialbool = False
field = forms.BooleanField(
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
initial=initialbool, widget=widget,
)
elif datafield.type == Question.TYPE_NUMBER:
elif q.type == Question.TYPE_NUMBER:
field = forms.DecimalField(
label=escape(qc.label), required=required,
min_value=datafield.valid_number_min or Decimal('0.00'),
max_value=datafield.valid_number_max,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
min_value=q.valid_number_min or Decimal('0.00'),
max_value=q.valid_number_max,
help_text=rich_text(q.help_text),
initial=initial.answer if initial else None,
)
elif datafield.type == Question.TYPE_STRING:
elif q.type == Question.TYPE_STRING:
field = forms.CharField(
label=escape(qc.label), required=required,
min_length=datafield.valid_string_length_min,
max_length=datafield.valid_string_length_max,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
min_length=q.valid_string_length_min,
max_length=q.valid_string_length_max,
help_text=rich_text(q.help_text),
initial=initial.answer if initial else None,
)
elif datafield.type == Question.TYPE_TEXT:
elif q.type == Question.TYPE_TEXT:
field = forms.CharField(
label=escape(qc.label), required=required,
min_length=datafield.valid_string_length_min,
max_length=datafield.valid_string_length_max,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
min_length=q.valid_string_length_min,
max_length=q.valid_string_length_max,
help_text=rich_text(q.help_text),
widget=forms.Textarea,
initial=initial.answer if initial else None,
)
elif datafield.type == Question.TYPE_COUNTRYCODE:
elif q.type == Question.TYPE_COUNTRYCODE:
field = CountryField(
countries=CachedCountries,
blank=True, null=True, blank_label=' ',
).formfield(
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
widget=forms.Select,
empty_label=' ',
initial=initial.answer if initial else (guess_country_from_request(request, event) if required else None),
initial=initial.answer if initial else (
guess_country_from_request(request, event) if required else None),
)
elif datafield.type == Question.TYPE_CHOICE:
elif q.type == Question.TYPE_CHOICE:
field = forms.ModelChoiceField(
queryset=datafield.options,
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
queryset=q.options,
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
widget=forms.Select,
to_field_name='identifier',
empty_label='',
initial=initial.options.first() if initial else None,
)
elif datafield.type == Question.TYPE_CHOICE_MULTIPLE:
elif q.type == Question.TYPE_CHOICE_MULTIPLE:
field = forms.ModelMultipleChoiceField(
queryset=datafield.options,
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
queryset=q.options,
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
to_field_name='identifier',
widget=QuestionCheckboxSelectMultiple,
initial=initial.options.all() if initial else None,
)
elif datafield.type == Question.TYPE_FILE:
if datafield.valid_file_portrait:
elif q.type == Question.TYPE_FILE:
if q.valid_file_portrait:
field = PortraitImageField(
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
initial=initial.file if initial else None,
widget=PortraitImageWidget(answer=initial, request=request, attrs={'data-portrait-photo': 'true'}),
widget=PortraitImageWidget(answer=initial, request=request,
attrs={'data-portrait-photo': 'true'}),
)
else:
field = ExtFileField(
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
initial=initial.file if initial else None,
widget=UploadedFileWidget(answer=initial, request=request),
ext_whitelist=settings.FILE_UPLOAD_EXTENSIONS_OTHER,
max_size=settings.FILE_UPLOAD_MAX_SIZE_OTHER,
)
elif datafield.type == Question.TYPE_DATE:
elif q.type == Question.TYPE_DATE:
attrs = {}
if datafield.valid_date_min:
attrs['data-min'] = datafield.valid_date_min.isoformat()
if datafield.valid_date_max:
attrs['data-max'] = datafield.valid_date_max.isoformat()
help_text = qc.help_text
if q.valid_date_min:
attrs['data-min'] = q.valid_date_min.isoformat()
if q.valid_date_max:
attrs['data-max'] = q.valid_date_max.isoformat()
help_text = q.help_text
if not help_text:
if datafield.valid_date_min and datafield.valid_date_max:
if q.valid_date_min and q.valid_date_max:
help_text = format_lazy(
_('Please enter a date between {min} and {max}.'),
min=date_format(datafield.valid_date_min, "SHORT_DATE_FORMAT"),
max=date_format(datafield.valid_date_max, "SHORT_DATE_FORMAT"),
min=date_format(q.valid_date_min, "SHORT_DATE_FORMAT"),
max=date_format(q.valid_date_max, "SHORT_DATE_FORMAT"),
)
elif datafield.valid_date_min:
elif q.valid_date_min:
help_text = format_lazy(
_('Please enter a date no earlier than {min}.'),
min=date_format(datafield.valid_date_min, "SHORT_DATE_FORMAT"),
min=date_format(q.valid_date_min, "SHORT_DATE_FORMAT"),
)
elif datafield.valid_date_max:
elif q.valid_date_max:
help_text = format_lazy(
_('Please enter a date no later than {max}.'),
max=date_format(datafield.valid_date_max, "SHORT_DATE_FORMAT"),
max=date_format(q.valid_date_max, "SHORT_DATE_FORMAT"),
)
if initial and initial.answer:
try:
@@ -779,16 +813,16 @@ class BaseQuestionsForm(forms.Form):
else:
_initial = None
field = forms.DateField(
label=escape(qc.label), required=required,
label=escape(q.question), required=required,
help_text=rich_text(help_text),
initial=_initial,
widget=DatePickerWidget(attrs),
)
if datafield.valid_date_min:
field.validators.append(MinDateValidator(datafield.valid_date_min))
if datafield.valid_date_max:
field.validators.append(MaxDateValidator(datafield.valid_date_max))
elif datafield.type == Question.TYPE_TIME:
if q.valid_date_min:
field.validators.append(MinDateValidator(q.valid_date_min))
if q.valid_date_max:
field.validators.append(MaxDateValidator(q.valid_date_max))
elif q.type == Question.TYPE_TIME:
if initial and initial.answer:
try:
_initial = dateutil.parser.parse(initial.answer).time()
@@ -797,29 +831,29 @@ class BaseQuestionsForm(forms.Form):
else:
_initial = None
field = forms.TimeField(
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
initial=_initial,
widget=TimePickerWidget(without_seconds=True),
)
elif datafield.type == Question.TYPE_DATETIME:
help_text = qc.help_text
elif q.type == Question.TYPE_DATETIME:
help_text = q.help_text
if not help_text:
if datafield.valid_datetime_min and datafield.valid_datetime_max:
if q.valid_datetime_min and q.valid_datetime_max:
help_text = format_lazy(
_('Please enter a date and time between {min} and {max}.'),
min=date_format(datafield.valid_datetime_min, "SHORT_DATETIME_FORMAT"),
max=date_format(datafield.valid_datetime_max, "SHORT_DATETIME_FORMAT"),
min=date_format(q.valid_datetime_min, "SHORT_DATETIME_FORMAT"),
max=date_format(q.valid_datetime_max, "SHORT_DATETIME_FORMAT"),
)
elif datafield.valid_datetime_min:
elif q.valid_datetime_min:
help_text = format_lazy(
_('Please enter a date and time no earlier than {min}.'),
min=date_format(datafield.valid_datetime_min, "SHORT_DATETIME_FORMAT"),
min=date_format(q.valid_datetime_min, "SHORT_DATETIME_FORMAT"),
)
elif datafield.valid_datetime_max:
elif q.valid_datetime_max:
help_text = format_lazy(
_('Please enter a date and time no later than {max}.'),
max=date_format(datafield.valid_datetime_max, "SHORT_DATETIME_FORMAT"),
max=date_format(q.valid_datetime_max, "SHORT_DATETIME_FORMAT"),
)
if initial and initial.answer:
@@ -831,20 +865,20 @@ class BaseQuestionsForm(forms.Form):
_initial = None
field = SplitDateTimeField(
label=escape(qc.label), required=required,
label=escape(q.question), required=required,
help_text=rich_text(help_text),
initial=_initial,
widget=SplitDateTimePickerWidget(
time_format=get_format_without_seconds('TIME_INPUT_FORMATS'),
min_date=datafield.valid_datetime_min,
max_date=datafield.valid_datetime_max
min_date=q.valid_datetime_min,
max_date=q.valid_datetime_max
),
)
if datafield.valid_datetime_min:
field.validators.append(MinDateTimeValidator(datafield.valid_datetime_min))
if datafield.valid_datetime_max:
field.validators.append(MaxDateTimeValidator(datafield.valid_datetime_max))
elif datafield.type == Question.TYPE_PHONENUMBER:
if q.valid_datetime_min:
field.validators.append(MinDateTimeValidator(q.valid_datetime_min))
if q.valid_datetime_max:
field.validators.append(MaxDateTimeValidator(q.valid_datetime_max))
elif q.type == Question.TYPE_PHONENUMBER:
if initial:
try:
initial = PhoneNumber().from_string(initial.answer)
@@ -857,27 +891,26 @@ class BaseQuestionsForm(forms.Form):
initial = "+{}.".format(phone_prefix)
field = PhoneNumberField(
label=escape(qc.label), required=required,
help_text=rich_text(qc.help_text),
label=escape(q.question), required=required,
help_text=rich_text(q.help_text),
# We now exploit an implementation detail in PhoneNumberPrefixWidget to allow us to pass just
# a country code but no number as an initial value. It's a bit hacky, but should be stable for
# the future.
initial=initial,
widget=WrappedPhoneNumberPrefixWidget()
)
field.datafield = datafield
field.question = q
if answers:
# Cache the answer object for later use
field.answer = answers[0]
if qc.dependency_question_id:
field.widget.attrs['data-question-dependency'] = qc.dependency_question_id
field.widget.attrs['data-question-dependency-values'] = escapejson_attr(json.dumps(qc.dependency_values))
if datafield.type != 'M':
field.widget.attrs['required'] = qc.required and not self.all_optional
field._required = qc.required and not self.all_optional
if q.dependency_question_id:
field.widget.attrs['data-question-dependency'] = q.dependency_question_id
field.widget.attrs['data-question-dependency-values'] = escapejson_attr(json.dumps(q.dependency_values))
if q.type != 'M':
field.widget.attrs['required'] = q.required and not self.all_optional
field._required = q.required and not self.all_optional
field.required = False
return field
def check_user_questions(self, d):
@@ -941,7 +974,6 @@ class OrderLevelQuestionsForm(BaseQuestionsForm):
super().__init__(*args, **kwargs)
# TODO(questionnaires) - switch olq's to questionnaires !
questions = Question.objects.filter(
event=event, container_type=Question.ContainerType.ORDER,
ask_during_checkin=False, hidden=False,
@@ -976,7 +1008,6 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
orderpos = self.orderpos = kwargs.pop('orderpos', None)
pos = cartpos or orderpos
item = pos.item
questionnaires = pos.item.relevant_questionnaires
event = kwargs.pop('event')
self.all_optional = kwargs.pop('all_optional', False)
self.attendee_addresses_required = event.settings.attendee_addresses_required and not self.all_optional
@@ -986,13 +1017,18 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
if cartpos and item.validity_mode == Item.VALIDITY_MODE_DYNAMIC and item.validity_dynamic_start_choice:
self.fields['requested_valid_from'] = self.build_requested_valid_from_field(event, pos, item)
for questionnaire in questionnaires:
for child in getattr(questionnaire, 'childlist', questionnaire.children.all()):
if child.user_datafield:
df = child.user_datafield
self.fields['question_%s' % df.id] = self.build_user_question_field(request, event, pos.answerlist, child, df)
elif child.system_datafield:
self.fields[child.system_datafield] = self.build_system_question_field(request, event, pos, child)
questions = []
if item.ask_attendee_data:
questions += get_fake_attendee_questions(event.settings)
questions += pos.item.questions_to_ask
questions.sort(key=lambda q: q.position)
for q in questions:
if isinstance(q, FakeQuestion):
self.fields[q.id] = self.build_system_question_field(request, event, pos, q)
else:
self.fields['question_%s' % q.id] = self.build_user_question_field(request, event, pos.answerlist, q)
responses = question_form_fields.send(sender=event, position=pos)
data = pos.meta_info_data
@@ -1057,21 +1093,21 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
)
def build_system_question_field(self, request, event, pos, qc):
field_name = qc.system_datafield
field_name = qc.id
if field_name == 'attendee_name_parts':
return NamePartsFormField(
max_length=255,
required=qc.required and not self.all_optional,
scheme=event.settings.name_scheme,
titles=event.settings.name_scheme_titles,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
initial=pos.attendee_name_parts,
)
if field_name == 'attendee_email':
return forms.EmailField(
required=qc.required and not self.all_optional,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
initial=pos.attendee_email,
widget=forms.EmailInput(
@@ -1083,7 +1119,7 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
if field_name == 'company':
return forms.CharField(
required=qc.required and not self.all_optional,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
max_length=255,
initial=pos.company,
@@ -1092,7 +1128,7 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
if field_name == 'street':
return forms.CharField(
required=qc.required and not self.all_optional,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
widget=forms.Textarea(attrs={
'rows': 2,
@@ -1105,7 +1141,7 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
return forms.CharField(
required=False,
max_length=30,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
initial=pos.zipcode,
widget=forms.TextInput(attrs={
@@ -1115,7 +1151,7 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
if field_name == 'city':
return forms.CharField(
required=False,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
max_length=255,
initial=pos.city,
@@ -1129,7 +1165,7 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
countries=CachedCountries
).formfield(
required=qc.required and not self.all_optional,
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
initial=country,
widget=forms.Select(attrs={
@@ -1157,7 +1193,7 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
del self.data[fprefix + 'state']
field = forms.ChoiceField(
label=escape(qc.label),
label=escape(qc.question),
help_text=rich_text(qc.help_text),
required=False,
choices=c,
@@ -1170,8 +1206,9 @@ class TicketLevelQuestionsForm(BaseQuestionsForm):
return field
def clean(self):
from pretix.base.addressvalidation import \
validate_address # local import to prevent impact on startup time
from pretix.base.addressvalidation import ( # local import to prevent impact on startup time
validate_address,
)
d = super().clean()
@@ -1412,8 +1449,9 @@ class BaseInvoiceAddressForm(forms.ModelForm):
self.fields['transmission_type'].widget.attrs['data-trigger-address-info'] = 'on'
def clean(self):
from pretix.base.addressvalidation import \
validate_address # local import to prevent impact on startup time
from pretix.base.addressvalidation import ( # local import to prevent impact on startup time
validate_address,
)
data = self.cleaned_data
@@ -1467,7 +1505,7 @@ class BaseInvoiceAddressForm(forms.ModelForm):
"vat_id": _("This field is required.")
})
if self.validate_vat_id and self.instance.vat_id_validated and 'vat_id' not in self.changed_data:
if self.validate_vat_id and self.instance.vat_id_validated and not any(v in self.changed_data for v in ('is_business', 'vat_id', 'country')):
pass # Skip re-validation if it is validated
elif self.validate_vat_id and vat_id_applicable:
try:
+2 -2
View File
@@ -82,8 +82,8 @@ class UserSettingsForm(forms.ModelForm):
class User2FADeviceAddForm(forms.Form):
name = forms.CharField(label=_('Device name'), max_length=64)
devicetype = forms.ChoiceField(label=_('Device type'), widget=forms.RadioSelect, choices=(
('totp', _('Smartphone with the Authenticator application')),
('webauthn', _('WebAuthn-compatible hardware token (e.g. Yubikey)')),
('otp_totp.totpdevice', _('Smartphone with the Authenticator application')),
('pretixbase.webauthndevice', _('WebAuthn-compatible hardware token (e.g. Yubikey)')),
))
@@ -107,6 +107,9 @@ class TransmissionType:
def transmission_info_to_form_data(self, transmission_info: dict) -> dict:
return transmission_info
def describe_info_columns(self):
return [f.label for f in self.invoice_address_form_fields.values()]
def describe_info(self, transmission_info: dict, country: Country, is_business: bool):
form_data = self.transmission_info_to_form_data(transmission_info)
data = []
@@ -1,196 +0,0 @@
# Generated by Django 4.2.29 on 2026-03-19 14:24
import json
from collections import namedtuple
from itertools import chain, groupby
from django.db import migrations, models
import django.db.models.deletion
import i18nfield.fields
from i18nfield.strings import LazyI18nString
import pretix.base.models.base
import pretix.base.models.fields
FakeQuestion = namedtuple(
'FakeQuestion', 'id question position required'
)
def get_fake_questions(settings):
def b(s):
return s == 'True'
fq = []
sqo = json.loads(settings.get('system_question_order', '{}'))
_ = LazyI18nString.from_gettext
if b(settings.get('attendee_names_asked', 'True')):
fq.append(FakeQuestion('attendee_name_parts', _('Attendee name'), sqo.get('attendee_name_parts', 0), b(settings.get('attendee_names_required'))))
if b(settings.get('attendee_emails_asked')):
fq.append(FakeQuestion('attendee_email', _('Attendee email'), sqo.get('attendee_email', 0), b(settings.get('attendee_emails_required'))))
if b(settings.get('attendee_company_asked')):
fq.append(FakeQuestion('company', _('Company'), sqo.get('company', 0), b(settings.get('attendee_company_required'))))
if b(settings.get('attendee_addresses_asked')):
fq.append(FakeQuestion('street', _('Street'), sqo.get('street', 0), b(settings.get('attendee_addresses_required'))))
fq.append(FakeQuestion('zipcode', _('ZIP code'), sqo.get('zipcode', 0), b(settings.get('attendee_addresses_required'))))
fq.append(FakeQuestion('city', _('City'), sqo.get('city', 0), b(settings.get('attendee_addresses_required'))))
fq.append(FakeQuestion('country', _('Country'), sqo.get('country', 0), b(settings.get('attendee_addresses_required'))))
return fq
def migrate_questions_forward(apps, schema_editor):
Event = apps.get_model("pretixbase", "Event")
Item = apps.get_model("pretixbase", "Item")
Question = apps.get_model("pretixbase", "Question")
Questionnaire = apps.get_model("pretixbase", "Questionnaire")
QuestionnaireChild = apps.get_model("pretixbase", "QuestionnaireChild")
EventSettingsStore = apps.get_model('pretixbase', 'Event_SettingsStore')
def create_grouped_item_questionnaires(event, children, label_prefix, questionnaire_type):
# group by item, creating a unique questionnaire per item
item_questionnaires = (([t[3] for t in children], item_id) for item_id, children in
groupby(children, key=lambda t: t[0]))
# group again, merging all questionnaires with identical children
merged_questionnaires = groupby(sorted(item_questionnaires, key=lambda t: [q.id for q in t[0]]),
key=lambda t: t[0])
for children, iterator in merged_questionnaires:
items = [item for _c, item in iterator]
# create questionnaires and children
questionnaire = Questionnaire.objects.create(
event=event, type=questionnaire_type, position=0, all_sales_channels=True,
internal_name=label_prefix + ', '.join(str(iname or name) for (id, iname, name) in items)
)
questionnaire.items.set([id for (id, iname, name) in items])
deps = {}
for position, child in enumerate(children):
if isinstance(child, FakeQuestion):
QuestionnaireChild.objects.create(
questionnaire=questionnaire,
position=position + 1,
system_datafield=child.id,
required=child.required,
label=child.question,
)
else:
deps[child.id] = QuestionnaireChild.objects.create(
questionnaire=questionnaire,
position=position + 1,
user_datafield=child,
required=child.required,
label=child.question,
help_text=child.help_text,
dependency_question=deps[child.dependency_question.id] if child.dependency_question else None,
dependency_values=child.dependency_values,
)
for event in Event.objects.iterator():
# get relevant settings
settings = {
setting.key: setting.value for setting in EventSettingsStore.objects.filter(object_id=event.id, key__in=(
'system_question_order', 'attendee_names_asked', 'attendee_names_required', 'attendee_emails_asked', 'attendee_emails_required',
'attendee_company_asked', 'attendee_company_required', 'attendee_addresses_asked', 'attendee_addresses_required',
))
}
# get all ticket-level questions (user-defined and system provided), along with the products for which they're asked
questions = event.questions.filter(container_type='P')
children = sorted(chain((
(item, q.position, 0, q)
for q in get_fake_questions(settings)
for item in event.items.filter(personalized=True).values_list('id', 'internal_name', 'name')
), (
(item, q.position, q.id, q)
for q in questions.filter(hidden=False)
for item in q.items.values_list('id', 'internal_name', 'name')
)), key=lambda t: (t[0], t[1]))
create_grouped_item_questionnaires(event, children, '', 'PS')
children = sorted(chain((
(item, q.position, q.id, q)
for q in questions.filter(hidden=True)
for item in q.items.values_list('id', 'internal_name', 'name')
)), key=lambda t: (t[0], t[1]))
create_grouped_item_questionnaires(event, children, 'Hidden questions for ', 'PH')
# get all order-level questions
questions = list(event.questions.filter(container_type='O', hidden=False).order_by('position'))
if questions:
# create questionnaires and children
questionnaire = Questionnaire.objects.create(
event=event, type='OS', position=0, all_sales_channels=True,
internal_name='Per-order questions',
)
deps = {}
for position, child in enumerate(questions):
deps[child.id] = QuestionnaireChild.objects.create(
questionnaire=questionnaire,
position=position + 1,
user_datafield=child,
required=child.required,
label=child.question,
help_text=child.help_text,
dependency_question=deps[child.dependency_question.id] if child.dependency_question else None,
dependency_values=child.dependency_values,
)
def migrate_questions_backward(apps, schema_editor):
pass # as long as we don't delete the old columns, this is a no op. after that, it gets complicated...
class Migration(migrations.Migration):
dependencies = [
('pretixbase', '0309_alter_questionanswer_unique_together_and_more'),
]
operations = [
migrations.CreateModel(
name='Questionnaire',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False)),
('internal_name', models.CharField(max_length=255)),
('type', models.CharField(max_length=5)),
('position', models.PositiveIntegerField(default=0)),
('all_sales_channels', models.BooleanField(default=True)),
('event', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='questionnaires', to='pretixbase.event')),
('items', models.ManyToManyField(related_name='questionnaires', to='pretixbase.item')),
('limit_sales_channels', models.ManyToManyField(to='pretixbase.saleschannel')),
],
options={
'abstract': False,
},
bases=(models.Model, pretix.base.models.base.LoggingMixin),
),
migrations.CreateModel(
name='QuestionnaireChild',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False)),
('position', models.PositiveIntegerField(default=0)),
('system_datafield', models.CharField(max_length=25, null=True)),
('required', models.BooleanField(default=False)),
('label', i18nfield.fields.I18nTextField()),
('help_text', i18nfield.fields.I18nTextField(null=True)),
('dependency_values', pretix.base.models.fields.MultiStringField(default=[])),
('dependency_question', models.ForeignKey(null=True, on_delete=django.db.models.deletion.SET_NULL, related_name='dependent_questions', to='pretixbase.questionnairechild')),
('questionnaire', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='children', to='pretixbase.questionnaire')),
('user_datafield', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, related_name='references', to='pretixbase.question')),
],
options={
'abstract': False,
},
bases=(models.Model, pretix.base.models.base.LoggingMixin),
),
migrations.RunPython(
migrate_questions_forward,
migrate_questions_backward,
),
# TODO(questionnaires) remove old columns from Question model
]
@@ -0,0 +1,49 @@
# Generated by Django 5.2.17 on 2026-09-21 11:30
import django.db.models.deletion
from django.db import migrations, models
def fix_unshredded_invoices(apps, _):
Invoice = apps.get_model("pretixbase", "Invoice")
InvoiceLine = apps.get_model("pretixbase", "InvoiceLine")
ignore_fields = (
# bool/int fields are not listed and skipped automatically
'prefix', 'invoice_no', 'full_invoice_no', 'invoice_from', 'invoice_from_name', 'invoice_from_zipcode',
'invoice_from_city', 'invoice_from_state', 'invoice_from_country', 'invoice_from_tax_id',
'invoice_from_vat_id', 'locale', 'payment_provider_stamp', 'footer_text', 'foreign_currency_display',
'foreign_currency_source', 'transmission_type', 'transmission_provider', 'transmission_status',
)
for i in Invoice.objects.filter(shredded=True):
for f in Invoice._meta.fields:
if f.name in ignore_fields:
continue
val = getattr(i, f.name, None)
if val and isinstance(val, str):
setattr(i, f.name, "█")
elif val and isinstance(val, list): # jsonfield
setattr(i, f.name, [])
elif val and isinstance(val, dict): # jsonfield
setattr(i, f.name, {"_shredded": True})
i.save()
InvoiceLine.objects.filter(
attendee_name__isnull=False,
invoice__shredded=True
).update(attendee_name="█")
class Migration(migrations.Migration):
dependencies = [
("pretixbase", "0310_question_valid_string_length_min"),
]
operations = [
migrations.RunPython(
fix_unshredded_invoices,
migrations.RunPython.noop,
),
]
+2 -2
View File
@@ -37,8 +37,8 @@ from .invoices import Invoice, InvoiceLine, invoice_filename
from .items import (
Item, ItemAddOn, ItemBundle, ItemCategory, ItemMetaProperty, ItemMetaValue,
ItemProgramTime, ItemVariation, ItemVariationMetaValue, Question,
Questionnaire, QuestionnaireChild, QuestionOption, Quota, SubEventItem,
SubEventItemVariation, itempicture_upload_to,
QuestionOption, Quota, SubEventItem, SubEventItemVariation,
itempicture_upload_to,
)
from .log import LogEntry
from .mail import OutgoingMail
+1
View File
@@ -166,6 +166,7 @@ class Device(LoggedModel):
)
security_profile = models.CharField(
max_length=190,
verbose_name=_('Security profile'),
default='full',
null=True,
blank=False
+18 -123
View File
@@ -1050,10 +1050,8 @@ class Item(LoggedModel):
replace_year = valid_until.year
replace_month = valid_until.month + self.validity_dynamic_duration_months
while replace_month > 12:
replace_month -= 12
replace_year += 1
replace_year += (replace_month - 1) // 12
replace_month = ((replace_month - 1) % 12) + 1
max_day = calendar.monthrange(replace_year, replace_month)[1]
replace_date = date(
year=replace_year,
@@ -1569,12 +1567,10 @@ class ItemBundle(models.Model):
class Question(LoggedModel):
"""
A question is a data field that can be used to extend an order or a ticket by custom
information, e.g. "Attendee age". To be actually useful, questions need to be added to
one or multiple Questionnaires. The answers may be found in QuestionAnswers, attached
to Orders, OrderPositions or CartPositions.
A question can allow one of several input types, currently:
A question is an input field that can be used to extend a ticket by custom information,
e.g. "Attendee age". The answers are found next to the position. The answers may be found
in QuestionAnswers, attached to OrderPositions/CartPositions. A question can allow one of
several input types, currently:
* a number (``TYPE_NUMBER``)
* a one-line string (``TYPE_STRING``)
@@ -1594,7 +1590,7 @@ class Question(LoggedModel):
:param required: Whether answering this question is required for submitting an order including
items associated with this question.
:type required: bool
:param items: TO BE REMOVED
:param items: A set of ``Items`` objects that this question should be applied to
:param ask_during_checkin: Whether to ask this question during check-in instead of during check-out.
:type ask_during_checkin: bool
:param show_during_checkin: Whether to show the answer to this question during check-in.
@@ -1653,7 +1649,6 @@ class Question(LoggedModel):
default=ContainerType.ORDERPOSITION,
)
question = I18nTextField(
# TODO(questionnaires) : to be renamed to 'internal_name'
verbose_name=_("Question")
)
identifier = models.CharField(
@@ -1669,7 +1664,6 @@ class Question(LoggedModel):
],
)
help_text = I18nTextField(
# TODO(questionnaires) : to be removed
verbose_name=_("Help text"),
help_text=_("If the question needs to be explained or clarified, do it here!"),
null=True, blank=True,
@@ -1679,22 +1673,22 @@ class Question(LoggedModel):
choices=TYPE_CHOICES,
verbose_name=_("Question type")
)
required = models.BooleanField( # TODO(questionnaires) : to be removed, -> QuestionnaireChild
required = models.BooleanField(
default=False,
verbose_name=_("Required question")
)
items = models.ManyToManyField( # TODO(questionnaires) : to be removed, -> Questionnaire
items = models.ManyToManyField(
Item,
related_name='questions',
verbose_name=_("Products"),
blank=True,
help_text=_('This question will be asked to buyers of the selected products')
)
position = models.PositiveIntegerField( # TODO(questionnaires) : to be removed, -> Questionnaire + QuestionnaireChild
position = models.PositiveIntegerField(
default=0,
verbose_name=_("Position")
)
ask_during_checkin = models.BooleanField( # TODO(questionnaires) : to be removed
ask_during_checkin = models.BooleanField(
verbose_name=_('Ask during check-in instead of in the ticket buying process'),
help_text=_('Not supported by all check-in apps for all question types.'),
default=False
@@ -1704,7 +1698,7 @@ class Question(LoggedModel):
help_text=_('Not supported by all check-in apps for all question types.'),
default=False
)
hidden = models.BooleanField( # to be removed
hidden = models.BooleanField(
verbose_name=_('Hidden question'),
help_text=_('This question will only show up in the backend.'),
default=False
@@ -1713,10 +1707,10 @@ class Question(LoggedModel):
verbose_name=_('Print answer on invoices'),
default=False
)
dependency_question = models.ForeignKey( # TODO(questionnaires) : to be removed, -> QuestionnaireChild
dependency_question = models.ForeignKey(
'Question', null=True, blank=True, on_delete=models.SET_NULL, related_name='dependent_questions'
)
dependency_values = MultiStringField(default=[]) # TODO(questionnaires) : to be removed, -> QuestionnaireChild
dependency_values = MultiStringField(default=[])
valid_number_min = models.DecimalField(decimal_places=6, max_digits=30, null=True, blank=True,
verbose_name=_('Minimum value'),
help_text=_('Currently not supported in our apps and during check-in'))
@@ -1755,9 +1749,9 @@ class Question(LoggedModel):
objects = ScopedManager(organizer='event__organizer')
class Meta:
verbose_name = _("Data field")
verbose_name_plural = _("Data fields")
ordering = ('question', 'id')
verbose_name = _("Question")
verbose_name_plural = _("Questions")
ordering = ('position', 'id')
unique_together = (('event', 'identifier'),)
def __str__(self):
@@ -1908,7 +1902,7 @@ class Question(LoggedModel):
return answer
@staticmethod
def clean_items(event, items): # TODO(questionnaires) : remove method / move to qc
def clean_items(event, items):
for item in items:
if event != item.event:
raise ValidationError(_('One or more items do not belong to this event.'))
@@ -1989,105 +1983,6 @@ class QuestionOption(models.Model):
ordering = ('position', 'id')
class Questionnaire(LoggedModel):
TYPE_ORDER_SALE = "OS"
TYPE_ORDER_POSITION_SALE = "PS"
TYPE_ORDER_POSITION_ATTENDEE_ONLY = "PA"
TYPE_ORDER_POSITION_CHECKIN = "PC"
TYPE_ORDER_POSITION_HIDDEN = "PH"
TYPE_CHOICES = (
(TYPE_ORDER_SALE, _("Order-wide, before purchase")),
(TYPE_ORDER_POSITION_SALE, _("Per product, before purchase")),
(TYPE_ORDER_POSITION_ATTENDEE_ONLY, _("Per product, via attendee link")),
(TYPE_ORDER_POSITION_CHECKIN, _("Per product, at check-in")),
(TYPE_ORDER_POSITION_HIDDEN, _("Per product, hidden")),
)
event = models.ForeignKey(
Event,
related_name="questionnaires",
on_delete=models.CASCADE
)
internal_name = models.CharField(
verbose_name=_("Internal name"),
max_length=255,
)
type = models.CharField(
max_length=5,
choices=TYPE_CHOICES,
verbose_name=_("Questionnaire type")
)
items = models.ManyToManyField(
Item,
related_name='questionnaires',
verbose_name=_("Products"),
blank=True,
help_text=_('This questionnaire will be asked to buyers of the selected products')
)
position = models.PositiveIntegerField(
default=0,
verbose_name=_("Position")
)
all_sales_channels = models.BooleanField(
verbose_name=_("Sell on all sales channels the product is sold on"),
default=True,
)
limit_sales_channels = models.ManyToManyField(
"SalesChannel",
verbose_name=_("Restrict to specific sales channels"),
help_text=_('The sales channel selection for the product as a whole takes precedence, so if a sales channel is '
'selected here but not on product level, the variation will not be available.'),
blank=True,
)
class QuestionnaireChild(LoggedModel):
SYSTEM_QUESTION_CHOICES = (
('attendee_name_parts', _('Attendee name')),
('attendee_email', _('Attendee email')),
('company', _('Company')),
('street', _('Street')),
('zipcode', _('ZIP code')),
('city', _('City')),
('country', _('Country')),
)
questionnaire = models.ForeignKey(
Questionnaire,
related_name="children",
on_delete=models.CASCADE
)
position = models.PositiveIntegerField(
default=0,
verbose_name=_("Position")
)
user_datafield = models.ForeignKey(
Question,
related_name="references",
on_delete=models.CASCADE,
null=True, blank=True,
)
system_datafield = models.CharField(
max_length=25,
choices=SYSTEM_QUESTION_CHOICES,
null=True, blank=True,
)
required = models.BooleanField(
default=False,
verbose_name=_("Required question")
)
label = I18nTextField(
verbose_name=_("Question")
)
help_text = I18nTextField(
verbose_name=_("Help text"),
help_text=_("If the question needs to be explained or clarified, do it here!"),
null=True, blank=True,
)
dependency_question = models.ForeignKey(
'QuestionnaireChild', null=True, blank=True, on_delete=models.SET_NULL, related_name='dependent_questions'
)
dependency_values = MultiStringField(default=[])
class Quota(LoggedModel):
"""
A quota is a "pool of tickets". It is there to limit the number of items
+32 -65
View File
@@ -1449,12 +1449,6 @@ class QuestionAnswer(models.Model):
else:
return self.answer
def to_dependency_values(self):
if self.question.type in (Question.TYPE_CHOICE, Question.TYPE_CHOICE_MULTIPLE):
return [o.identifier for o in self.options.all()]
elif self.question.type in (Question.TYPE_BOOLEAN, Question.TYPE_COUNTRYCODE):
return self.answer
def save(self, *args, **kwargs):
if self.orderposition and self.cartposition:
raise ValueError('QuestionAnswer cannot be linked to an order and a cart position at the same time.')
@@ -1599,80 +1593,53 @@ class AbstractPosition(RoundingCorrectionMixin, models.Model):
def cache_answers(self, all=True):
"""
Creates a new property on the object:
questions: a list of Question objects, extended by an 'answer' property
Creates two properties on the object.
(1) answ: a dictionary of question.id → answer string
(2) questions: a list of Question objects, extended by an 'answer' property
"""
self.answ = {}
for a in getattr(self, 'answerlist', self.answers.all()): # use prefetch_related cache from get_cart
self.answ[a.question_id] = a
# We need to clone our question objects, otherwise we will override the cached
# answers of other items in the same cart if the question objects have been
# selected via prefetch_related
if not all:
if hasattr(self.item, 'relevant_questionnaires'):
children = list(copy.copy(qc) for qq in self.item.relevant_questionnaires for qc in qq.childlist)
if hasattr(self.item, 'questions_to_ask'):
questions = list(copy.copy(q) for q in self.item.questions_to_ask)
else:
children = list(copy.copy(qc) for qq in self.item.questionnaires.filter(type='PS') for qc in qq.children.all())
questions = list(copy.copy(q) for q in self.item.questions.filter(ask_during_checkin=False,
hidden=False))
else:
children = list(copy.copy(qc) for qq in self.item.questionnaires.filter(type__startswith='P') for qc in qq.children.all())
questions = list(copy.copy(q) for q in self.item.questions.all())
qc_cache = {
q.pk: q for q in children
question_cache = {
q.pk: q for q in questions
}
def qc_is_visible(parentid, qvals):
if parentid not in qc_cache:
def question_is_visible(parentid, qvals):
if parentid not in question_cache:
return False
parentqc = qc_cache[parentid]
if parentqc.dependency_question_id and not qc_is_visible(parentqc.dependency_question_id, parentqc.dependency_values):
parentq = question_cache[parentid]
if parentq.dependency_question_id and not question_is_visible(parentq.dependency_question_id, parentq.dependency_values):
return False
answer_values = self.get_dependency_answer_values(parentqc)
return any(qval in answer_values for qval in qvals)
if parentid not in self.answ:
return False
return (
('True' in qvals and self.answ[parentid].answer == 'True')
or ('False' in qvals and self.answ[parentid].answer == 'False')
or (any(qval in [o.identifier for o in self.answ[parentid].options.all()] for qval in qvals))
)
self.questions = []
for qc in children:
if qc.user_datafield_id and qc.user_datafield_id in self.answer_cache:
qc.answer = self.answer_cache[qc.user_datafield_id]
#qc.answer.question = qc # cache object
elif qc.system_datafield:
qc.answer = self.get_system_answer(qc.system_datafield)
#qc.answer.question = qc # cache object
for q in questions:
if q.id in self.answ:
q.answer = self.answ[q.id]
q.answer.question = q # cache object
else:
qc.answer = ""
if not qc.dependency_question_id or qc_is_visible(qc.dependency_question_id, qc.dependency_values):
self.questions.append(qc)
@cached_property
def answer_cache(self):
return {
aw.question_id: aw for aw in getattr(self, 'answerlist', self.answers.all())
}
def get_dependency_answer_values(self, qc):
if qc.user_datafield_id:
if qc.user_datafield_id not in self.answer_cache:
return None
answer = self.answer_cache[qc.user_datafield_id]
return answer.to_dependency_values()
elif qc.system_datafield:
return [self.get_system_answer(qc.system_datafield)]
else:
raise ValueError('Questionnaire child without datafield has no answer')
def get_system_answer(self, system_datafield_name):
if system_datafield_name == 'attendee_name_parts':
return self.attendee_name_parts
elif system_datafield_name == 'attendee_email':
return self.attendee_email
elif system_datafield_name == 'street':
return self.street
elif system_datafield_name == 'zipcode':
return self.zipcode
elif system_datafield_name == 'city':
return self.city
elif system_datafield_name == 'state':
return self.state
elif system_datafield_name == 'country':
return self.country
else:
raise ValueError('Unknown system question name')
q.answer = ""
if not q.dependency_question_id or question_is_visible(q.dependency_question_id, q.dependency_values):
self.questions.append(q)
@property
def net_price(self):
+3 -3
View File
@@ -72,7 +72,7 @@ from pretix.helpers.countries import CachedCountries
from pretix.helpers.format import format_map
from pretix.helpers.money import DecimalTextInput
from pretix.multidomain.urlreverse import eventreverse_absolute
from pretix.presale.views import get_cart_positions
from pretix.presale.views import get_cart
from pretix.presale.views.cart import cart_session, get_or_create_cart_id
logger = logging.getLogger(__name__)
@@ -1165,7 +1165,7 @@ class FreeOrderProvider(BasePaymentProvider):
def is_allowed(self, request: HttpRequest, total: Decimal=None) -> bool:
from .services.cart import get_fees
cart = get_cart_positions(request)
cart = get_cart(request)
try:
fees = get_fees(event=request.event, request=request,
@@ -1433,7 +1433,7 @@ class GiftCardPayment(BasePaymentProvider):
for p in cs.get('payments', [])
if p.get('info_data', {}).get('gift_card')
]
positions = get_cart_positions(request)
positions = get_cart(request)
testmode = self.event.testmode
else:
used_cards = []
+28 -13
View File
@@ -801,6 +801,18 @@ def generate_compressed_addon_list(op, order, event, only_checked_in=False):
return addonlist
def get_sizebox(page: pypdf.PageObject):
mediabox = page.mediabox
cropbox = page.cropbox
return pypdf.generic.RectangleObject((
max(mediabox[0], cropbox[0]),
max(mediabox[1], cropbox[1]),
min(mediabox[2], cropbox[2]),
min(mediabox[3], cropbox[3]),
))
class Renderer:
def __init__(self, event, layout, background_file):
@@ -1079,7 +1091,7 @@ class Renderer:
fontsize = float(o['fontsize'])
height = float(o['height']) * mm
width = float(o['width']) * mm
while True:
for _i in range(25): # try adapting the font size at most 25 times
p, ad, lineheight = self._text_paragraph(op, order, o, override_fontsize=fontsize)
w, h = p.wrapOn(canvas, width, 1000 * mm)
widths = p.getActualLineWidths0()
@@ -1153,11 +1165,10 @@ class Renderer:
elif o['type'] == "poweredby":
self._draw_poweredby(canvas, op, o)
if self.bg_pdf:
page_size = (
self.bg_pdf.pages[0].mediabox[2] - self.bg_pdf.pages[0].mediabox[0],
self.bg_pdf.pages[0].mediabox[3] - self.bg_pdf.pages[0].mediabox[1]
)
if self.bg_pdf.pages[0].get('/Rotate') in (90, 270):
first_page = self.bg_pdf.pages[0]
sizebox = get_sizebox(first_page)
page_size = (sizebox.width, sizebox.height)
if first_page.rotation in (90, 270):
# swap dimensions due to pdf being rotated
page_size = page_size[::-1]
canvas.setPageSize(page_size)
@@ -1312,14 +1323,18 @@ def merge_background(fg_pdf: PdfWriter, bg_pdf: PdfWriter, out_file, compress):
def _merge_with_correct_page_media_box(output: pypdf.PdfWriter, fg_page: pypdf.PageObject, bg_page: pypdf.PageObject):
if bg_page.rotation != 0:
bg_page.transfer_rotation_to_content()
media_box = bg_page.mediabox
"""
Adds fg_page to output, merging bg_page behind it.
If bg_page has a non-zero mergebox/cropbox or is rotated via /Rotate, a transformation is applied to fix this."""
trsf = pypdf.Transformation()
if media_box.bottom != 0:
trsf = trsf.translate(0, -media_box.bottom)
if media_box.left != 0:
trsf = trsf.translate(-media_box.left, 0)
if bg_page.rotation != 0:
trsf = trsf.rotate(-bg_page.rotation)
mb = get_sizebox(bg_page)
pt1 = trsf.apply_on(mb.lower_left)
pt2 = trsf.apply_on(mb.upper_right)
trsf = trsf.translate(-min(pt1[0], pt2[0]), -min(pt1[1], pt2[1]))
fg_page = output.add_page(fg_page)
fg_page.merge_transformed_page(bg_page, trsf, over=False, expand=False)
+5 -3
View File
@@ -54,7 +54,7 @@ from celery.exceptions import MaxRetriesExceededError
from django.conf import settings
from django.core.files.storage import default_storage
from django.core.mail import EmailMultiAlternatives, SafeMIMEMultipart
from django.core.mail.message import SafeMIMEText
from django.core.mail.message import SafeMIMEText, utf8_charset_qp
from django.db import connection, transaction
from django.db.models import Q
from django.dispatch import receiver
@@ -380,6 +380,8 @@ def mail(email: Union[str, Sequence[str]], subject: Union[str, FormattedString],
class CustomEmail(EmailMultiAlternatives):
encoding = utf8_charset_qp
def _create_mime_attachment(self, content, mimetype):
"""
Convert the content, mimetype pair into a MIME attachment object.
@@ -449,9 +451,9 @@ def mail_send_task(self, **kwargs) -> bool:
# Rewrite all <img> tags from real URLs or data URLs to inline attachments referred to by content ID
if outgoing_mail.body_html is not None:
html_message = SafeMIMEMultipart(_subtype='related', encoding=settings.DEFAULT_CHARSET)
html_message = SafeMIMEMultipart(_subtype='related')
html_with_cid, cid_images = replace_images_with_cid_paths(outgoing_mail.body_html)
html_message.attach(SafeMIMEText(html_with_cid, 'html', settings.DEFAULT_CHARSET))
html_message.attach(SafeMIMEText(html_with_cid, 'html', utf8_charset_qp))
attach_cid_images(html_message, cid_images, verify_ssl=True)
email.attach_alternative(html_message, "multipart/related")
File diff suppressed because one or more lines are too long
+22 -10
View File
@@ -50,8 +50,8 @@ from pretix.api.serializers.order import (
from pretix.api.serializers.waitinglist import WaitingListSerializer
from pretix.base.i18n import LazyLocaleException
from pretix.base.models import (
CachedCombinedTicket, CachedTicket, Event, InvoiceAddress, OrderPayment,
OrderPosition, OrderRefund, OutgoingMail, QuestionAnswer,
CachedCombinedTicket, CachedTicket, Event, Invoice, InvoiceAddress,
OrderPayment, OrderPosition, OrderRefund, OutgoingMail, QuestionAnswer,
)
from pretix.base.services.invoices import invoice_pdf_task
from pretix.base.signals import register_data_shredders
@@ -598,18 +598,30 @@ class InvoiceShredder(BaseDataShredder):
def shred_data(self, progress_callback=None):
qs_i = self.event.invoices.filter(shredded=False)
total = qs_i.count()
ignore_fields = (
'prefix', 'invoice_no', 'full_invoice_no', 'invoice_from', 'invoice_from_name', 'invoice_from_zipcode',
'invoice_from_city', 'invoice_from_state', 'invoice_from_country', 'invoice_from_tax_id',
'invoice_from_vat_id', 'locale', 'payment_provider_stamp', 'footer_text', 'foreign_currency_display',
'foreign_currency_source', 'transmission_type', 'transmission_provider', 'transmission_status',
)
for i in _progress_helper(qs_i, progress_callback, 0, total):
if i.file:
i.file.delete()
i.shredded = True
i.introductory_text = "█"
i.additional_text = "█"
i.invoice_to = "█"
i.payment_provider_text = "█"
i.transmission_info = {"_shredded": True}
i.save()
i.lines.update(description="█")
i.shredded = True
for f in Invoice._meta.fields:
if f.name in ignore_fields:
continue
val = getattr(i, f.name, None)
if val and isinstance(val, str):
setattr(i, f.name, "█")
elif val and isinstance(val, list): # jsonfield
setattr(i, f.name, [])
elif val and isinstance(val, dict): # jsonfield
setattr(i, f.name, {"_shredded": True})
i.save()
i.lines.update(description="█", attendee_name="█")
class CachedTicketShredder(BaseDataShredder):
+52 -23
View File
@@ -20,6 +20,7 @@
# <https://www.gnu.org/licenses/>.
#
from decimal import ROUND_HALF_UP, Decimal
from typing import Optional
from babel import Locale, UnknownLocaleError
from babel.numbers import format_currency
@@ -35,32 +36,32 @@ register = template.Library()
@register.filter("money")
def money_filter(value: Decimal, arg='', hide_currency=False):
if isinstance(value, (float, int)):
def money_filter(value: Optional[Decimal | float | int | str], arg='', hide_currency=False):
if isinstance(value, (float, int, str)):
if value == '':
return value
value = Decimal(value)
if value is None:
value = Decimal('0.00')
if not isinstance(value, Decimal):
if value == '':
return value
raise TypeError("Invalid data type passed to money filter: %r" % type(value))
if not arg:
raise ValueError("No currency passed.")
arg = arg.upper()
places = settings.CURRENCY_PLACES.get(arg, 2)
rounded = value.quantize(Decimal('1') / 10 ** places, ROUND_HALF_UP)
if places < 2 and rounded != value:
# We display decimal places even if we shouldn't for this currency if rounding
# would make the numbers incorrect. If this branch executes, it's likely a bug in
# pretix, but we won't show wrong numbers!
if hide_currency:
return floatformat(value, "2g")
else:
return '{} {}'.format(arg, floatformat(value, "2g"))
if value.normalize().as_tuple().exponent < -9:
# Heuristic: It's unlikely we'll ever see values of less than 0.000000001 in any currency. Therefore, if we
# do see them, we very likely deal with a floating point error. This happens mostly in dev mode when computations
# are made in SQLite, which uses REAL precision, but it can also happen when we naively pass a float from Python
# land to this filter (even though it should not happen).
value = value.quantize(Decimal('1e-9'), ROUND_HALF_UP).normalize()
currency_places = settings.CURRENCY_PLACES.get(arg, 2)
required_places = -value.normalize().as_tuple().exponent
render_places = max(currency_places, required_places)
if hide_currency:
return floatformat(value, f"{places}g")
return floatformat(value, f"{render_places}g")
try:
locale = Locale(get_babel_locale())
@@ -68,14 +69,29 @@ def money_filter(value: Decimal, arg='', hide_currency=False):
locale = "en"
try:
return format_currency(value, arg, locale=locale)
return format_currency(
value,
arg,
locale=locale,
# We only allow Babel to restrict the digits to the digits defined by the currency if this does not remove any
# precision in case we have sub-currency precision (which we shouldn't have in most places, but it's still
# better than showing wrong data). Note: Weird precision effects can occur after in-database arithmetic
# on SQLite, since SQLite does not have fixed-decimal computation.
currency_digits=currency_places >= required_places,
decimal_quantization=currency_places >= required_places,
)
except:
return '{} {}'.format(arg, floatformat(value, f"{places}g"))
return '{} {}'.format(arg, floatformat(value, f"{render_places}g"))
@register.filter("money_without_currency")
def money_filter_without_currency(value: Optional[Decimal | float | int | str], arg=''):
return money_filter(value, arg, hide_currency=True)
@register.filter("money_numberfield")
def money_numberfield_filter(value: Decimal, arg=''):
if isinstance(value, (float, int)):
def money_numberfield_filter(value: Optional[Decimal | float | int | str], arg=''):
if isinstance(value, (float, int, str)):
value = Decimal(value)
if not isinstance(value, Decimal):
raise TypeError("Invalid data type passed to money filter: %r" % type(value))
@@ -87,15 +103,28 @@ def money_numberfield_filter(value: Decimal, arg=''):
@register.filter(is_safe=True)
def tax_rate_format(number):
def tax_rate_format(number: Optional[Decimal | float | int | str]):
"""
Display a Decimal to its significant decimal places, used for tax rates.
"""
assert isinstance(number, Decimal)
if isinstance(number, (float, int, str)):
if number == '':
return number
number = Decimal(number)
if number is None:
number = Decimal('0.00')
if not isinstance(number, Decimal):
raise TypeError("Invalid data type passed to tax rate format filter: %r" % type(number))
if number.normalize().as_tuple().exponent < -9:
# Heuristic: It's unlikely we'll ever see values of less than 0.000000001 in any currency. Therefore, if we
# do see them, we very likely deal with a floating point error. This happens mostly in dev mode when computations
# are made in SQLite, which uses REAL precision, but it can also happen when we naively pass a float from Python
# land to this filter (even though it should not happen).
number = number.quantize(Decimal('1e-9'), ROUND_HALF_UP).normalize()
return mark_safe(
formats.number_format(
number.normalize(),
-number.as_tuple().exponent,
number,
-number.normalize().as_tuple().exponent,
use_l10n=True,
force_grouping=False,
)
+2 -2
View File
@@ -21,8 +21,8 @@
#
import contextvars
from contextlib import contextmanager
from datetime import datetime
from dateutil.parser import parse
from django.utils.timezone import now
from pretix.base.auth import has_event_access_permission
@@ -34,7 +34,7 @@ timemachine_now_var = contextvars.ContextVar('timemachine_now', default=None)
def time_machine_now_assigned_from_request(request):
if hasattr(request, 'event') and f'timemachine_now_dt:{request.event.pk}' in request.session and \
request.event.testmode and has_event_access_permission(request):
request.now_dt = parse(request.session[f'timemachine_now_dt:{request.event.pk}'])
request.now_dt = datetime.fromisoformat(request.session[f'timemachine_now_dt:{request.event.pk}'])
request.now_dt_is_fake = True
else:
request.now_dt = now()
+7 -2
View File
@@ -19,6 +19,7 @@
# You should have received a copy of the GNU Affero General Public License along with this program. If not, see
# <https://www.gnu.org/licenses/>.
#
from django.conf import settings
from django.http import (
HttpResponseForbidden, HttpResponseNotFound, HttpResponseServerError,
)
@@ -27,7 +28,6 @@ from django.template import TemplateDoesNotExist, loader
from django.template.loader import get_template
from django.utils.functional import Promise
from django.utils.translation import gettext as _
from sentry_sdk import last_event_id
from pretix.base.i18n import language
from pretix.base.middleware import get_language_from_request
@@ -106,9 +106,14 @@ def server_error(request):
template = loader.get_template('500.html')
except TemplateDoesNotExist:
return HttpResponseServerError('<h1>Server Error (500)</h1>', content_type='text/html')
if settings.SENTRY_ENABLED:
from sentry_sdk import last_event_id
sentry_id = last_event_id()
else:
sentry_id = None
r = HttpResponseServerError(template.render({
'request': request,
'sentry_event_id': last_event_id(),
'sentry_event_id': sentry_id,
}))
r.xframe_options_exempt = True
return r
+15 -25
View File
@@ -27,7 +27,7 @@ from decimal import Decimal
from django import forms
from django.core.files.uploadedfile import UploadedFile
from django.db import IntegrityError
from django.db.models import Prefetch, Q, QuerySet
from django.db.models import Prefetch, QuerySet
from django.utils.functional import cached_property
from django.utils.timezone import make_aware
@@ -37,7 +37,7 @@ from pretix.base.forms.questions import (
)
from pretix.base.models import (
CartPosition, InvoiceAddress, OrderPosition, Question, QuestionAnswer,
QuestionnaireChild, QuestionOption,
QuestionOption,
)
from pretix.base.models.customers import AttendeeProfile
from pretix.base.models.orders import CheckoutSession, Order
@@ -348,37 +348,27 @@ class OrderQuestionsViewMixin(BaseQuestionsViewMixin):
@cached_property
def positions(self):
qqs = self.request.event.questionnaires.all()
qqs = self.request.event.questions.all()
if self.only_user_visible:
qqs = qqs.filter(type='PS')
else:
qqs = qqs.filter(type__startswith='P')
qqs = qqs.filter(
Q(all_sales_channels=True) | Q(limit_sales_channels__identifier=self.order.sales_channel.identifier)
)
qqs = qqs.filter(ask_during_checkin=False, hidden=False, container_type=Question.ContainerType.ORDERPOSITION)
return list(self.order.positions.select_related(
'item', 'variation'
).prefetch_related(
Prefetch('answers',
QuestionAnswer.objects.prefetch_related('options'),
to_attr='answerlist'),
Prefetch('item__questionnaires',
Prefetch('item__questions',
qqs.prefetch_related(
Prefetch('children', QuestionnaireChild.objects.prefetch_related(
Prefetch('user_datafield', Question.objects.prefetch_related(
Prefetch('options', QuestionOption.objects.prefetch_related(Prefetch(
# This prefetch statement is utter bullshit, but it actually prevents Django from doing
# a lot of queries since ModelChoiceIterator stops trying to be clever once we have
# a prefetch lookup on this query...
'question',
Question.objects.none(),
to_attr='dummy'
)))
))
),
to_attr='childlist')
),
to_attr='relevant_questionnaires')
Prefetch('options', QuestionOption.objects.prefetch_related(Prefetch(
# This prefetch statement is utter bullshit, but it actually prevents Django from doing
# a lot of queries since ModelChoiceIterator stops trying to be clever once we have
# a prefetch lookup on this query...
'question',
Question.objects.none(),
to_attr='dummy'
)))
).select_related('dependency_question'),
to_attr='questions_to_ask')
))
@cached_property
-2
View File
@@ -26,7 +26,6 @@ from django.core import signing
from django.http import HttpResponseBadRequest, HttpResponseRedirect
from django.shortcuts import render
from django.urls import reverse
from django.utils.html import format_html
logger = logging.getLogger(__name__)
@@ -61,7 +60,6 @@ def redir_view(request):
u = urllib.parse.urlparse(url)
return render(request, 'pretixbase/redirect.html', {
'hostname': u.hostname,
'bold_hostname': format_html("<strong>{}</strong>", u.hostname),
'url': url,
})
+16
View File
@@ -20,6 +20,7 @@
# <https://www.gnu.org/licenses/>.
#
import logging
import multiprocessing
import os
from celery import Celery, signals
@@ -54,6 +55,21 @@ def on_task_received(sender, request, **kwargs):
logger.info(f"Task {request.id} has trace {trace}")
@receiver(signals.after_setup_task_logger)
def on_after_setup_task_logger(sender, logger, loglevel, logfile, format, colorize, **kwargs):
# This hack seems to be required to get celery to log internal events from eg billiard/pool.py such as
# "worker killed because it used too much memory"
# You can test that it is working by starting a celery worker with a low value like
# --max-memory-per-child 300000
# and then trigger a task. Result should look like this:
# [2026-09-23 10:42:26,234: WARNING/ForkPoolWorker-16]: [???:???] child process exiting after exceeding memory limit (394540KiB / 300000KiB)
# The ???:??? are likely because by copying the handlers, we are also copying the format, but I was unable to find
# a better compatible way.
multi_logger = multiprocessing.get_logger()
multi_logger.setLevel(logging.WARNING)
multi_logger.handlers = logger.handlers
@receiver(signals.task_prerun)
def on_task_prerun(sender, task_id, task, **kwargs):
from pretix.helpers.logs import local
+15 -9
View File
@@ -400,10 +400,10 @@ class EventMetaValueForm(forms.ModelForm):
if self.disabled:
self.fields['value'].widget.attrs['readonly'] = 'readonly'
def clean_slug(self):
def clean_value(self):
if self.disabled:
return self.instance.value if self.instance else None
return self.cleaned_data['slug']
return self.cleaned_data['value']
class Meta:
model = EventMetaValue
@@ -838,9 +838,10 @@ class CancelSettingsForm(SettingsForm):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
if self.obj.settings.giftcard_expiry_years is not None:
self.fields['cancel_allow_user_paid_refund_as_giftcard'].help_text = gettext(
'You have configured gift cards to be valid {} years plus the year the gift card is issued in.'
).format(self.obj.settings.giftcard_expiry_years)
self.fields['cancel_allow_user_paid_refund_as_giftcard'].help_text = format_html(
gettext('You have configured gift cards to be valid {} years plus the year the gift card is issued in.'),
self.obj.settings.giftcard_expiry_years
)
class PaymentSettingsForm(EventSettingsValidationMixin, SettingsForm):
@@ -1635,10 +1636,15 @@ class MailSettingsForm(FormPlaceholderMixin, SettingsForm):
self._set_field_placeholders(k, v, rich=k.startswith('mail_text_') and k not in self.plain_rendering)
for k, v in list(self.fields.items()):
if k.endswith('_attendee') and not event.settings.attendee_emails_asked:
# If we don't ask for attendee emails, we can't send them anything and we don't need to clutter
# the user interface with it
del self.fields[k]
if k.endswith('_attendee'):
if not event.settings.attendee_emails_asked:
# If we don't ask for attendee emails, we can't send them anything and we don't need to clutter
# the user interface with it
del self.fields[k]
elif 'subject' in k and k.replace("subject", "send") in self.fields:
v.widget.attrs["data-display-dependency"] = f'#id_{k.replace("subject", "send")}'
elif 'text' in k and k.replace("text", "send") in self.fields:
v.widget.attrs["data-display-dependency"] = f'#id_{k.replace("text", "send")}'
class TicketSettingsForm(SettingsForm):
@@ -105,13 +105,6 @@ class GlobalSettingsForm(SettingsForm):
domain=settings.SITE_URL
)
)),
('widget_vue2_origins', forms.CharField(
widget=forms.Textarea(attrs={'rows': '3'}),
required=False,
# Not translated on purpose, this is a temporary feature and contains too many special case words
label="Vue2 widget origins",
help_text="One origin per line (e.g. https://example.com). Requests from these origins will be served the old vue2-based widget.",
))
])
responses = register_global_settings.send(self)
for r, response in sorted(responses, key=lambda r: str(r[0])):
+2 -2
View File
@@ -22,7 +22,7 @@
from django import forms
from django.core.exceptions import ValidationError
from django.utils.functional import lazy
from django.utils.html import format_html
from django.utils.html import conditional_escape, format_html
from django.utils.translation import gettext_lazy as _
from pretix.base.modelimport_orders import get_order_import_columns
@@ -66,7 +66,7 @@ class ProcessForm(forms.Form):
widget=forms.Select(
attrs={'data-static': 'true'}
),
help_text=c.help_text,
help_text=conditional_escape(c.help_text),
)
def get_columns(self):
+2 -2
View File
@@ -364,7 +364,7 @@ class TeamForm(forms.ModelForm):
for opt in pg.options
],
label=pg.label,
help_text=pg.help_text,
help_text=conditional_escape(pg.help_text),
initial=initial,
widget=forms.RadioSelect,
)
@@ -389,7 +389,7 @@ class TeamForm(forms.ModelForm):
for opt in pg.options
],
label=pg.label,
help_text=pg.help_text,
help_text=conditional_escape(pg.help_text),
initial=initial,
widget=forms.RadioSelect,
)
+2 -2
View File
@@ -435,10 +435,10 @@ class SubEventMetaValueForm(forms.ModelForm):
if self.disabled:
self.fields['value'].widget.attrs['readonly'] = 'readonly'
def clean_slug(self):
def clean_value(self):
if self.disabled:
return self.instance.value if self.instance else None
return self.cleaned_data['slug']
return self.cleaned_data['value']
class Meta:
model = SubEventMetaValue
+2 -1
View File
@@ -44,6 +44,7 @@ from django.db.models import Count, F, Max
from django.db.models.functions import Upper
from django.forms.utils import ErrorDict
from django.urls import reverse
from django.utils.html import escape
from django.utils.timezone import now
from django.utils.translation import gettext_lazy as _, pgettext_lazy
from django_scopes.forms import SafeModelChoiceField
@@ -176,7 +177,7 @@ class VoucherForm(I18nModelForm):
required=False,
widget=forms.TextInput(attrs={'data-seat-guid-field': '1'}),
initial=self.instance.seat.seat_guid if self.instance.seat else '',
help_text=str(self.instance.seat) if self.instance.seat else '',
help_text=escape(str(self.instance.seat) if self.instance.seat else ''),
)
def parse_itemvar(self, data):
+5 -3
View File
@@ -717,6 +717,10 @@ class CoreUserImpersonatedLogEntryType(UserImpersonatedLogEntryType):
'pretix.organizer.export.schedule.failed': _('A scheduled export has failed: {reason}.'),
'pretix.organizer.outgoingmails.retried': _('Failed emails have been scheduled to be retried.'),
'pretix.organizer.outgoingmails.aborted': _('Queued emails have been aborted.'),
'pretix.property.created': _('An organizer meta property has been created.'),
'pretix.property.deleted': _('An organizer meta property has been deleted.'),
'pretix.property.changed': _('An organizer meta property has been changed.'),
'pretix.property.reordered': _('An organizer meta property has been reordered.'),
'pretix.giftcards.acceptance.added': _('Gift card acceptance for another organizer has been added.'),
'pretix.giftcards.acceptance.removed': _('Gift card acceptance for another organizer has been removed.'),
'pretix.giftcards.acceptance.acceptor.invited': _('A new gift card acceptor has been invited.'),
@@ -774,6 +778,7 @@ class CoreUserImpersonatedLogEntryType(UserImpersonatedLogEntryType):
'pretix.user.settings.2fa.disabled': _('Two-factor authentication has been disabled.'),
'pretix.user.settings.2fa.regenemergency': _('Your two-factor emergency codes have been regenerated.'),
'pretix.user.settings.2fa.emergency': _('A two-factor emergency code has been generated.'),
'pretix.user.settings.2fa.resetdrift': _('Drift and throttle values for two-factor devices have been reset.'),
'pretix.user.settings.2fa.device.added': _('A new two-factor authentication device "{name}" has been added to '
'your account.'),
'pretix.user.settings.2fa.device.deleted': _('The two-factor authentication device "{name}" has been removed '
@@ -861,9 +866,6 @@ class OrganizerPluginStateLogEntryType(LogEntryType):
'pretix.event.question.option.added': _('An answer option has been added to the question.'),
'pretix.event.question.option.deleted': _('An answer option has been removed from the question.'),
'pretix.event.question.option.changed': _('An answer option has been changed.'),
'pretix.event.questionnaire.added': _('A questionnaire has been created.'),
'pretix.event.questionnaire.deleted': _('A questionnaire has been deleted.'),
'pretix.event.questionnaire.changed': _('A questionnaire has been changed.'),
'pretix.event.permissions.added': _('A user has been added to the event team.'),
'pretix.event.permissions.invited': _('A user has been invited to the event team.'),
'pretix.event.permissions.changed': _('A user\'s permissions have been changed.'),
+2 -2
View File
@@ -85,8 +85,8 @@ class PermissionMiddleware:
"user.settings.2fa.enable",
"user.settings.2fa.disable",
"user.settings.2fa.regenemergency",
"user.settings.2fa.confirm.totp",
"user.settings.2fa.confirm.webauthn",
"user.settings.2fa.confirm.otp_totp.totpdevice",
"user.settings.2fa.confirm.pretixbase.webauthndevice",
"user.settings.2fa.delete",
"user.settings.2fa.leaveteams",
"auth.logout",
+3 -3
View File
@@ -182,12 +182,12 @@ def get_event_navigation(request: HttpRequest):
'active': 'event.items.categories' in url.url_name,
},
{
'label': _('Questionnaires'),
'url': reverse('control:event.items.questionnaires', kwargs={
'label': _('Questions'),
'url': reverse('control:event.items.questions', kwargs={
'event': request.event.slug,
'organizer': request.event.organizer.slug,
}),
'active': 'event.items.questionnaires' in url.url_name or 'event.items.questions' in url.url_name,
'active': 'event.items.questions' in url.url_name,
},
{
'label': _('Discounts'),
@@ -45,8 +45,8 @@
</p>
<div class="form-group buttons">
<input type="submit" class="btn btn-large btn-default" value="Cancel"/>
<input type="submit" class="btn btn-large btn-primary" name="allow" value="Authorize"/>
<input type="submit" class="btn btn-large btn-default" value="{% trans "Cancel" %}"/>
<input type="submit" class="btn btn-large btn-primary" name="allow" value="{% trans "Authorize" %}"/>
</div>
</form>
{% else %}
@@ -33,7 +33,7 @@
</div>
<div class="slug-length alert alert-warning helper-display-none-soft">
{% blocktrans trimmed %}
We strongly recommend against using short forms of more then 16 characters.
We strongly recommend against using short forms of more than 16 characters.
{% endblocktrans %}
</div>
</div>
@@ -12,120 +12,151 @@
{% endblock %}
{% block inside %}
{% if question %}
<h1>{% blocktrans with name=question.question %}Data field: {{ name }}{% endblocktrans %}</h1>
<h1>{% blocktrans with name=question.question %}Question: {{ name }}{% endblocktrans %}</h1>
{% else %}
<h1>{% trans "Data field" %}</h1>
<h1>{% trans "Question" %}</h1>
{% endif %}
<form action="" method="post" class="form-horizontal">
{% csrf_token %}
{% bootstrap_form_errors form %}
{% bootstrap_field form.question layout="control" %}
{% bootstrap_field form.type layout="control" %}
<div id="valid-number">
{% bootstrap_field form.valid_number_min layout="control" %}
{% bootstrap_field form.valid_number_max layout="control" %}
</div>
<div id="valid-date">
{% bootstrap_field form.valid_date_min layout="control" %}
{% bootstrap_field form.valid_date_max layout="control" %}
</div>
<div id="valid-datetime">
{% bootstrap_field form.valid_datetime_min layout="control" %}
{% bootstrap_field form.valid_datetime_max layout="control" %}
</div>
<div id="valid-string">
{% bootstrap_field form.valid_string_length_min layout="control" %}
{% bootstrap_field form.valid_string_length_max layout="control" %}
</div>
<div id="valid-file">
{% bootstrap_field form.valid_file_portrait layout="control" %}
</div>
<div id="answer-options">
<h3>{% trans "Answer options" %}</h3>
<noscript>
<p>{% trans "Only applicable if you choose 'Choose one/multiple from a list' above." %}</p>
</noscript>
<div class="formset" data-formset data-formset-prefix="{{ formset.prefix }}" data-formset-delete-confirm-text="{% trans "If you delete an answer option, you will no longer be able to see statistical data on customers who previously selected this option, and when such customers edit their answers, they need to select a different option." %}">
{{ formset.management_form }}
{% bootstrap_formset_errors formset %}
<div data-formset-body>
{% for form in formset %}
<div data-formset-form>
<div class="sr-only">
{{ form.id }}
{% bootstrap_field form.DELETE form_group_class="" layout="inline" %}
{% bootstrap_field form.ORDER form_group_class="" layout="inline" %}
</div>
<div class="row question-option-row">
<div class="col-xs-10">
<span class="text-muted">
{% blocktrans trimmed with id=form.instance.identifier %}
Answer option {{ id }}
{% endblocktrans %}
</span>
{% bootstrap_form_errors form %}
{% bootstrap_field form.answer layout='inline' form_group_class="" %}
</div>
<div class="col-xs-2 text-right flip">
<span>&nbsp;</span><br>
<button type="button" class="btn btn-default" data-formset-move-up-button>
<i class="fa fa-arrow-up"></i></button>
<button type="button" class="btn btn-default" data-formset-move-down-button>
<i class="fa fa-arrow-down"></i></button>
<button type="button" class="btn btn-danger" data-formset-delete-button>
<i class="fa fa-trash"></i></button>
</div>
</div>
</div>
{% endfor %}
<div class="tabbed-form">
<fieldset>
<legend>{% trans "General" %}</legend>
{% bootstrap_field form.question layout="control" %}
{% bootstrap_field form.type layout="control" %}
{% if form.items %}
{% bootstrap_field form.items layout="control" %}
{% endif %}
{% bootstrap_field form.required layout="control" %}
<div class="alert alert-info alert-required-boolean">
{% blocktrans trimmed %}
If you mark a Yes/No question as required, it means that the user has to select Yes and No is not
accepted. If you want to allow both options, do not make this field required.
{% endblocktrans %}
</div>
<script type="form-template" data-formset-empty-form>
{% escapescript %}
<div data-formset-form>
<div class="sr-only">
{{ formset.empty_form.id }}
{% bootstrap_field formset.empty_form.DELETE form_group_class="" layout="inline" %}
{% bootstrap_field formset.empty_form.ORDER form_group_class="" layout="inline" %}
</div>
<div class="row question-option-row">
<div class="col-xs-10">
<span class="text-muted">
{% trans "New answer option" %}
</span>
{% bootstrap_field formset.empty_form.answer layout='inline' form_group_class="" %}
<div id="valid-number">
{% bootstrap_field form.valid_number_min layout="control" %}
{% bootstrap_field form.valid_number_max layout="control" %}
</div>
<div id="valid-date">
{% bootstrap_field form.valid_date_min layout="control" %}
{% bootstrap_field form.valid_date_max layout="control" %}
</div>
<div id="valid-datetime">
{% bootstrap_field form.valid_datetime_min layout="control" %}
{% bootstrap_field form.valid_datetime_max layout="control" %}
</div>
<div id="valid-string">
{% bootstrap_field form.valid_string_length_min layout="control" %}
{% bootstrap_field form.valid_string_length_max layout="control" %}
</div>
<div id="valid-file">
{% bootstrap_field form.valid_file_portrait layout="control" %}
</div>
<div id="answer-options">
<h3>{% trans "Answer options" %}</h3>
<noscript>
<p>{% trans "Only applicable if you choose 'Choose one/multiple from a list' above." %}</p>
</noscript>
<div class="formset" data-formset data-formset-prefix="{{ formset.prefix }}" data-formset-delete-confirm-text="{% trans "If you delete an answer option, you will no longer be able to see statistical data on customers who previously selected this option, and when such customers edit their answers, they need to select a different option." %}">
{{ formset.management_form }}
{% bootstrap_formset_errors formset %}
<div data-formset-body>
{% for form in formset %}
<div data-formset-form>
<div class="sr-only">
{{ form.id }}
{% bootstrap_field form.DELETE form_group_class="" layout="inline" %}
{% bootstrap_field form.ORDER form_group_class="" layout="inline" %}
</div>
<div class="row question-option-row">
<div class="col-xs-10">
<span class="text-muted">
{% blocktrans trimmed with id=form.instance.identifier %}
Answer option {{ id }}
{% endblocktrans %}
</span>
{% bootstrap_form_errors form %}
{% bootstrap_field form.answer layout='inline' form_group_class="" %}
</div>
<div class="col-xs-2 text-right flip">
<span>&nbsp;</span><br>
<button type="button" class="btn btn-default" data-formset-move-up-button>
<i class="fa fa-arrow-up"></i></button>
<button type="button" class="btn btn-default" data-formset-move-down-button>
<i class="fa fa-arrow-down"></i></button>
<button type="button" class="btn btn-danger" data-formset-delete-button>
<i class="fa fa-trash"></i></button>
</div>
</div>
</div>
<div class="col-xs-2 text-right flip">
<span>&nbsp;</span><br>
<button type="button" class="btn btn-default" data-formset-move-up-button>
<i class="fa fa-arrow-up"></i></button>
<button type="button" class="btn btn-default" data-formset-move-down-button>
<i class="fa fa-arrow-down"></i></button>
<button type="button" class="btn btn-danger" data-formset-delete-button>
<i class="fa fa-trash"></i></button>
</div>
</div>
{% endfor %}
</div>
{% endescapescript %}
</script>
<p>
<button type="button" class="btn btn-default" data-formset-add>
<i class="fa fa-plus"></i> {% trans "Add a new option" %}</button>
</p>
</div>
<script type="form-template" data-formset-empty-form>
{% escapescript %}
<div data-formset-form>
<div class="sr-only">
{{ formset.empty_form.id }}
{% bootstrap_field formset.empty_form.DELETE form_group_class="" layout="inline" %}
{% bootstrap_field formset.empty_form.ORDER form_group_class="" layout="inline" %}
</div>
<div class="row question-option-row">
<div class="col-xs-10">
<span class="text-muted">
{% trans "New answer option" %}
</span>
{% bootstrap_field formset.empty_form.answer layout='inline' form_group_class="" %}
</div>
<div class="col-xs-2 text-right flip">
<span>&nbsp;</span><br>
<button type="button" class="btn btn-default" data-formset-move-up-button>
<i class="fa fa-arrow-up"></i></button>
<button type="button" class="btn btn-default" data-formset-move-down-button>
<i class="fa fa-arrow-down"></i></button>
<button type="button" class="btn btn-danger" data-formset-delete-button>
<i class="fa fa-trash"></i></button>
</div>
</div>
</div>
{% endescapescript %}
</script>
<p>
<button type="button" class="btn btn-default" data-formset-add>
<i class="fa fa-plus"></i> {% trans "Add a new option" %}</button>
</p>
</div>
</div>
</fieldset>
<fieldset>
<legend>{% trans "Advanced" %}</legend>
{% bootstrap_field form.help_text layout="control" %}
{% bootstrap_field form.identifier layout="control" %}
{% if form.ask_during_checkin %}
{% bootstrap_field form.ask_during_checkin layout="control" %}
{% endif %}
{% if form.show_during_checkin %}
{% bootstrap_field form.show_during_checkin layout="control" %}
{% endif %}
{% bootstrap_field form.hidden layout="control" %}
{% if form.print_on_invoice %}
{% bootstrap_field form.print_on_invoice layout="control" %}
{% endif %}
<div class="form-group">
<label class="col-md-3 control-label" for="id_dependency_question">
{% trans "Question dependency" %}
<br><span class="optional">{% trans "Optional" context "form" %}</span>
</label>
<div class="col-md-4">
{% bootstrap_field form.dependency_question layout="inline" form_group_class="inner" %}
</div>
<div class="col-md-5">
<script type="text/plain" id="dependency_value_val">{{ form.instance.dependency_values|escapejson_dumps }}</script>
{% bootstrap_field form.dependency_values layout="inline" form_group_class="inner" %}
</div>
</div>
</fieldset>
</div>
{% bootstrap_field form.identifier layout="control" %}
{% if form.ask_during_checkin %}
{% bootstrap_field form.ask_during_checkin layout="control" %}
{% endif %}
{% if form.show_during_checkin %}
{% bootstrap_field form.show_during_checkin layout="control" %}
{% endif %}
{% bootstrap_field form.hidden layout="control" %}
{% if form.print_on_invoice %}
{% bootstrap_field form.print_on_invoice layout="control" %}
{% endif %}
<div class="form-group submit-group">
<button type="submit" class="btn btn-primary btn-save">
{% trans "Save" %}
@@ -1,41 +0,0 @@
{% extends "pretixcontrol/items/base.html" %}
{% load i18n %}
{% load bootstrap3 %}
{% load static %}
{% load icon %}
{% load compress %}
{% load vite %}
{% block title %}
{% trans "Questionnaires" %}
{% endblock %}
{% block inside %}
<h1>
{% trans "Questionnaires" %}
<a href="{% url "control:event.items.questions" organizer=request.event.organizer.slug event=request.event.slug %}" class="btn btn-default pull-right">
{% icon "wrench" %} {% trans "Manage data fields" %}
</a>
</h1>
<p>
{% blocktrans trimmed %}
Questionaires allow your attendees to fill in additional data about their ticket. If you provide food, one
example might be to ask your users about dietary requirements.
{% endblocktrans %}
</p>
<p>
TODO(questionnaires) : add more specific explanation of the questionnaire concept.
</p>
{{ request.event.settings.locales|json_script:"event_locales" }}
{{ questionnaire_type_choices|json_script:"questionnaire_type_choices" }}
{% url "control:event.items.questions.edit" organizer=request.event.organizer.slug event=request.event.slug question=0 as datafield_edit_url %}
{{ datafield_edit_url|json_script:"datafield_edit_url" }}
<div id="questionnaires-editor">
<!-- Vue app mount point -->
</div>
{% vite_hmr %}
{% vite_asset "src/pretix/static/pretixcontrol/js/ui/questionnaires/index.ts" %}
{% endblock %}
@@ -1,8 +1,8 @@
{% extends "pretixcontrol/items/base.html" %}
{% load i18n %}
{% block title %}{% trans "Data fields" %}{% endblock %}
{% block title %}{% trans "Questions" %}{% endblock %}
{% block inside %}
<h1>{% trans "Data fields" %}</h1>
<h1>{% trans "Questions" %}</h1>
<p>
{% blocktrans trimmed %}
Questions allow your attendees to fill in additional data about their ticket. If you provide food, one
@@ -14,19 +14,19 @@
{% if request.event.settings.feature_flag_order_level_questions %}
{% if 'event.items:write' in request.eventpermset %}
<p>
<a href="{% url "control:event.items.questions.add" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=P" class="btn btn-default"><i class="fa fa-plus"></i> {% trans "Create a new per-ticket data field" %}
<a href="{% url "control:event.items.questions.add" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=P" class="btn btn-default"><i class="fa fa-plus"></i> {% trans "Create a new per-ticket question" %}
</a>
<a href="{% url "control:event.items.questions.add" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=O" class="btn btn-default"><i class="fa fa-plus"></i> {% trans "Create a new order-level data field" %}
<a href="{% url "control:event.items.questions.add" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=O" class="btn btn-default"><i class="fa fa-plus"></i> {% trans "Create a new order-level question" %}
</a>
</p>
{% endif %}
<h2>{% trans "Per-ticket data fields" %}</h2>
<p>{% trans "These data field can be used on individual tickets." %}</p>
<h2>{% trans "Per-ticket questions" %}</h2>
<p>{% trans "These questions are asked for every ticket, so possibly multiple times in the same order." %}</p>
{% else %}
{% if 'event.items:write' in request.eventpermset %}
<p>
<a href="{% url "control:event.items.questions.add" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=P" class="btn btn-default"><i class="fa fa-plus"></i> {% trans "Create a new data field" %}
<a href="{% url "control:event.items.questions.add" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=P" class="btn btn-default"><i class="fa fa-plus"></i> {% trans "Create a new question" %}
</a>
</p>
{% endif %}
@@ -35,27 +35,39 @@
<table class="table table-hover table-quotas">
<thead>
<tr>
<th>{% trans "Internal name" %}</th>
<th>{% trans "Question" %}</th>
<th>{% trans "Type" %}</th>
<th class="iconcol"></th>
<th class="iconcol"></th>
<th class="iconcol"></th>
<th>{% trans "Products" %}</th>
{% if 'event.items:write' in request.eventpermset %}
<th class="action-col-2"></th>
{% endif %}
<th class="action-col-2"></th>
</tr>
</thead>
<tbody>
<tbody data-dnd-url="{% url "control:event.items.questions.reorder" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=P">
{% for q in questions %}{% if q.container_type == "P" %}
<tr>
<tr data-dnd-id="{{ q.id }}">
<td>
<strong>
<a href="{% url "control:event.items.questions.show" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}">
{{ q.question }}
</a>
{% if q.pk %}
<a href="{% url "control:event.items.questions.show" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}">
{% endif %}
{{ q.question }}
{% if q.pk %}
</a>
{% endif %}
</strong><br>
<small class="text-muted">{{ q.identifier }}</small>
</td>
<td>
{{ q.get_type_display }}
{% if q.pk %}
{{ q.get_type_display }}
{% else %}
{% trans "System question" %}
{% endif %}
</td>
<td>
{% if q.required %}
@@ -72,11 +84,35 @@
<span class="fa fa-eye-slash text-muted" data-toggle="tooltip" title="{% trans "Hidden question" %}"></span>
{% endif %}
</td>
<td>
{% if q.pk %}
<ul>
{% for item in q.items.all %}
<li>
<a href="{% url "control:event.item" organizer=request.event.organizer.slug event=request.event.slug item=item.id %}">{{ item }}</a>
</li>
{% endfor %}
</ul>
{% else %}
<small>{% trans "All personalized products" %}</small>
{% endif %}
</td>
{% if 'event.items:write' in request.eventpermset %}
<td class="dnd-container">
</td>
{% endif %}
<td class="text-right flip">
<a href="{% url "control:event.items.questions.show" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}" class="btn btn-default btn-sm"><i class="fa fa-bar-chart"></i></a>
{% if 'event.items:write' in request.eventpermset %}
<a href="{% url "control:event.items.questions.edit" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}" class="btn btn-default btn-sm"><i class="fa fa-edit"></i></a>
<a href="{% url "control:event.items.questions.delete" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}" class="btn btn-danger btn-sm"><i class="fa fa-trash"></i></a>
{% if q.pk %}
<a href="{% url "control:event.items.questions.show" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}" class="btn btn-default btn-sm"><i class="fa fa-bar-chart"></i></a>
{% if 'event.items:write' in request.eventpermset %}
<a href="{% url "control:event.items.questions.edit" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}" class="btn btn-default btn-sm"><i class="fa fa-edit"></i></a>
<a href="{% url "control:event.items.questions.delete" organizer=request.event.organizer.slug event=request.event.slug question=q.id %}" class="btn btn-danger btn-sm"><i class="fa fa-trash"></i></a>
{% endif %}
{% else %}
{% if 'event.settings.general:write' in request.eventpermset %}
<a href="{% url "control:event.settings" organizer=request.event.organizer.slug event=request.event.slug %}#tab-0-2-open"
class="btn btn-default btn-sm"><i class="fa fa-wrench"></i></a>
{% endif %}
{% endif %}
</td>
</tr>
@@ -87,31 +123,34 @@
{% if request.event.settings.feature_flag_order_level_questions %}
<h2>
{% trans "Per-order data fields" %}
{% trans "Per-order questions" %}
<small><span class="label label-info" title="
{% trans "This functionality is in active development and expected to change significantly over the coming months." %}
{% trans "In pretixPOS, per-order data fields are currently not supported and will not be displayed." %}
{% trans "Per-order questions are currently not supported and will not be displayed in pretixPOS." %}
" data-toggle="tooltip">
<span class="fa fa-flask" aria-hidden="true"></span>
{% trans "Experimental feature" %}
</span></small>
</h2>
<p>{% trans "These data fields are asked once per order." %}</p>
<p>{% trans "These questions are asked once per order." %}</p>
<div class="table-responsive">
<table class="table table-hover table-quotas">
<thead>
<tr>
<th>{% trans "Internal name" %}</th>
<th>{% trans "Question" %}</th>
<th>{% trans "Type" %}</th>
<th class="iconcol"></th>
<th class="iconcol"></th>
<th class="iconcol"></th>
{% if 'event.items:write' in request.eventpermset %}
<th class="action-col-2"></th>
{% endif %}
<th class="action-col-2"></th>
</tr>
</thead>
<tbody>
<tbody data-dnd-url="{% url "control:event.items.questions.reorder" organizer=request.event.organizer.slug event=request.event.slug %}?container_type=O">
{% for q in questions %}{% if q.container_type == "O" %}
<tr>
<tr data-dnd-id="{{ q.id }}">
<td>
<strong>
{{ q.question }}
@@ -119,7 +158,11 @@
<small class="text-muted">{{ q.identifier }}</small>
</td>
<td>
{{ q.get_type_display }}
{% if q.pk %}
{{ q.get_type_display }}
{% else %}
{% trans "System question" %}
{% endif %}
</td>
<td>
{% if q.required %}
@@ -136,6 +179,10 @@
<span class="fa fa-eye-slash text-muted" data-toggle="tooltip" title="{% trans "Hidden question" %}"></span>
{% endif %}
</td>
{% if 'event.items:write' in request.eventpermset %}
<td class="dnd-container">
</td>
{% endif %}
<td class="text-right flip">
{% if q.pk %}
{% if 'event.items:write' in request.eventpermset %}
@@ -20,10 +20,8 @@
{% endif %}
{% elif question.type == "M" %}
{{ answer.to_string_i18n|rich_text_snippet }}
{% elif question.type %}
{{ answer.to_string_i18n|rich_text_snippet }}
{% else %}
{{ answer|linebreaksbr }}
{{ answer.to_string_i18n|linebreaksbr }}
{% endif %}
{% else %}
<em>{% trans "not answered" %}</em>
@@ -610,9 +610,60 @@
{% endif %}
{% if line.has_questions %}
<dl>
{% if line.item.ask_attendee_data and event.settings.attendee_names_asked %}
<dt>{% trans "Attendee name" %}</dt>
<dd>{% if line.attendee_name %}{{ line.attendee_name_all_components }}{% else %}
<em>{% trans "not answered" %}</em>{% endif %}</dd>
{% endif %}
{% if line.item.ask_attendee_data and event.settings.attendee_emails_asked %}
<dt>{% trans "Attendee email" %}</dt>
<dd>
{% if line.attendee_email %}
{{ line.attendee_email }}
{% if not line.addon_to %}
<form class="form-inline helper-display-inline" method="post"
action="{% url "control:event.order.resendlink" event=request.event.slug organizer=request.event.organizer.slug code=order.code position=line.pk %}">
{% csrf_token %}
<a href="{% url "control:event.order.position.sendmail" event=request.event.slug organizer=request.event.organizer.slug code=order.code position=line.pk %}"
class="btn btn-default btn-xs">
<span class="fa fa-envelope-o"></span>
</a>
<button class="btn btn-default btn-xs">
{% trans "Resend link" %}
</button>
</form>
{% endif %}
{% else %}
<em>{% trans "not answered" %}</em>
{% endif %}
</dd>
{% endif %}
{% if line.item.ask_attendee_data and event.settings.attendee_company_asked %}
<dt>
{% trans "Attendee company" %}
</dt>
<dd>
{% if line.company %}{{ line.company }}{% else %}<em>{% trans "not answered" %}</em>{% endif %}
</dd>
{% endif %}
{% if line.item.ask_attendee_data and event.settings.attendee_addresses_asked %}
<dt>
{% trans "Attendee address" %}
</dt>
<dd>
{% if line.street or line.zipcode or line.city or line.country %}
{{ line.street|default_if_none:""|linebreaksbr }}<br>
{{ line.zipcode|default_if_none:"" }} {{ line.city|default_if_none:"" }}<br>
{% if line.state %}{{ line.state_for_address }}<br>{% endif %}
{{ line.country.name|default_if_none:"" }}
{% else %}
<em>{% trans "not answered" %}</em>
{% endif %}
</dd>
{% endif %}
{% for q in line.questions %}
<dt>
{{ q.label }}
{{ q.question }}
{% if q.ask_during_checkin %}
<span class="fa fa-qrcode text-muted"
data-toggle="tooltip"
@@ -621,49 +672,7 @@
{% endif %}
</dt>
<dd>
{#
{% if q.answer %}
{% if q.answer.file %}
<span class="fa fa-file"></span>
<a href="{{ q.answer.backend_file_url }}?token={% answer_token request q.answer %}">
{{ q.answer.file_name }}
</a>
<span class="label label-danger" data-toggle="tooltip"
title="{% trans "This file has been uploaded by a user and could contain viruses or other malicious content." %}">
{% trans "UNSAFE" %}
</span>
{% if q.answer.is_image %}
<br>
<a href="{{ q.answer.backend_file_url }}?token={% answer_token request q.answer %}" data-lightbox="order"
class="answer-thumb">
<img src="{{ q.answer.backend_file_url }}?token={% answer_token request q.answer %}">
</a>
{% endif %}
{% elif q.type == "M" %}
{{ q.answer.to_string_i18n|rich_text_snippet }}
{% elif q.type %}
{{ q.answer.to_string_i18n|linebreaksbr }}
{% else %}<!-- TODO(questionnaires): proper separation of QuestionAnswer objects and system answers...... -->
{{ q.answer|linebreaksbr }}
{% endif %}
{% else %}
<em>{% trans "not answered" %}</em>
{% endif %}
#}
{% include "pretixcontrol/order/fragment_question_answer.html" with request=request question=q answer=q.answer %}
{% if q.system_datafield == "attendee_email" and not line.addon_to %}
<form class="form-inline helper-display-inline" method="post"
action="{% url "control:event.order.resendlink" event=request.event.slug organizer=request.event.organizer.slug code=order.code position=line.pk %}">
{% csrf_token %}
<a href="{% url "control:event.order.position.sendmail" event=request.event.slug organizer=request.event.organizer.slug code=order.code position=line.pk %}"
class="btn btn-default btn-xs">
<span class="fa fa-envelope-o"></span>
</a>
<button class="btn btn-default btn-xs">
{% trans "Resend link" %}
</button>
</form>
{% endif %}
</dd>
{% endfor %}
{% for q in line.additional_fields %}
@@ -15,7 +15,7 @@
<div>
<div class="big-radio radio">
<label>
<input type="radio" required value="totp" name="{{ form.devicetype.html_name }}" {% if form.devicetype.value == "totp" %}checked{% endif %}>
<input type="radio" required value="otp_totp.totpdevice" name="{{ form.devicetype.html_name }}" {% if form.devicetype.value == "otp_totp.totpdevice" %}checked{% endif %}>
<strong>{% trans "Smartphone with Authenticator app" %}</strong><br>
<div class="help-block">
{% blocktrans trimmed %}
@@ -26,7 +26,7 @@
</div>
<div class="big-radio radio">
<label>
<input type="radio" required value="webauthn" name="{{ form.devicetype.html_name }}" {% if form.devicetype.value == "webauthn" %}checked{% endif %}>
<input type="radio" required value="pretixbase.webauthndevice" name="{{ form.devicetype.html_name }}" {% if form.devicetype.value == "pretixbase.webauthndevice" %}checked{% endif %}>
<strong>{% trans "WebAuthn-compatible hardware token" %}</strong><br>
<div class="help-block">
{% blocktrans trimmed %}
@@ -116,14 +116,14 @@
{% for d in devices %}
<li class="list-group-item">
<a class="btn btn-danger btn-xs pull-right flip"
href="{% url "control:user.settings.2fa.delete" devicetype=d.devicetype device=d.pk %}">
href="{% url "control:user.settings.2fa.delete" devicetype=d.model_label device=d.pk %}">
Delete
</a>
{% if d.devicetype == "totp" %}
{% if d.model_label == "otp_totp.totpdevice" %}
<span class="fa fa-mobile"></span>
{% elif d.devicetype == "webauthn" %}
{% elif d.model_label == "pretixbase.webauthndevice" %}
<span class="fa fa-usb"></span>
{% elif d.devicetype == "u2f" %}
{% elif d.model_label == "pretixbase.u2fdevice" %}
<span class="fa fa-usb"></span>
{% endif %}
{{ d.name }}
@@ -1,6 +1,7 @@
{% extends "pretixcontrol/base.html" %}
{% load i18n %}
{% load bootstrap3 %}
{% load icon %}
{% block title %}{% trans "User" %}{% endblock %}
{% block content %}
<h1>{% trans "User" %} {{ user.email }}</h1>
@@ -59,8 +60,83 @@
{% bootstrap_field form.is_verified layout='control' %}
{% endif %}
{% bootstrap_field form.last_login layout='control' %}
{% bootstrap_field form.require_2fa layout='control' %}
{% bootstrap_field form.needs_password_change layout='control' %}
{% bootstrap_field form.require_2fa layout='control' %}
<div class="form-group">
<div class="col-md-9 col-md-offset-3">
<div class="panel panel-default">
<div class="panel-heading">
<button class="btn btn-default btn-xs pull-right" type="submit" form="resetdriftthrottle">
{% trans "Reset drift and throttle" %}
</button>
<h3 class="panel-title">
{% trans "Available two-factor authentication methods" %}
</h3>
</div>
<table class="panel-body table table-hover">
{% for d in devices %}
<tr>
<td>
{% if d.model_label == 'otp_totp.totpdevice' %}
TOTP
{% elif d.model_label == 'pretixbase.u2fdevice' %}
U2F
{% elif d.model_label == 'pretixbase.webauthndevice' %}
WebAuthn
{% elif d.model_label == 'otp_static.staticdevice' %}
{% trans "Emergency tokens" %}
{% endif %}
{% if d.confirmed %}
{% icon "check" %}
{% else %}
{% icon "warning" %}
{% endif %}
</td>
<td>
{{ d.name }}
</td>
<td>
{% if d.throttling_failure_timestamp %}
{% blocktrans trimmed with date=d.throttling_failure_timestamp|date:"SHORT_DATETIME_FORMAT" count cnt=d.throttling_failure_count %}
1 failed attempt since {{ date }}
{% plural %}
{{ cnt }} failed attempts since {{ date }}
{% endblocktrans %}
<br>
{% endif %}
{% if d.throttling_enabled and not d.verify_is_allowed.0 %}
<strong>
{% blocktrans trimmed with date=d.verify_is_allowed.1.locked_until|date:"SHORT_DATETIME_FORMAT" %}
Currently locked until {{ date }}
{% endblocktrans %}
</strong>
<br>
{% endif %}
{% if d.model_label == 'otp_totp.totpdevice' %}
<small>
<code>step = {{ d.step }},
t0 = {{ d.t0 }},
digits = {{ d.digits }},
tolerance = {{ d.tolerance }},
drift = {{ d.drift }},
last_t = {{ d.last_t }}</code>
</small>
{% elif d.model_label == 'pretixbase.u2fdevice' %}
<small>
<code>sign_count = {{ d.sign_count }}</code>
</small>
{% elif d.model_label == 'otp_static.staticdevice' %}
<small>
<code>token_count = {{ d.token_set.count }}</code>
</small>
{% endif %}
</td>
</tr>
{% endfor %}
</table>
</div>
</div>
</div>
</fieldset>
<fieldset>
<legend>{% trans "Team memberships" %}</legend>
@@ -102,4 +178,8 @@
</div>
</div>
</div>
<form action="{% url "control:users.resetdriftthrottle" id=user.pk %}" id="resetdriftthrottle" method="post">
{% csrf_token %}
</form>
{% endblock %}
+3 -3
View File
@@ -78,6 +78,7 @@ urlpatterns = [
re_path(r'^users/(?P<id>\d+)/impersonate$', users.UserImpersonateView.as_view(), name='users.impersonate'),
re_path(r'^users/(?P<id>\d+)/anonymize$', users.UserAnonymizeView.as_view(), name='users.anonymize'),
re_path(r'^users/(?P<id>\d+)/emergencytoken$', users.UserEmergencyTokenView.as_view(), name='users.emergencytoken'),
re_path(r'^users/(?P<id>\d+)/resetdriftthrottle$', users.Reset2FADriftThrottleView.as_view(), name='users.resetdriftthrottle'),
re_path(r'^pdf/editor/webfonts.css', pdf.FontsCSSView.as_view(), name='pdf.css'),
re_path(r'^settings/?$', user.UserSettings.as_view(), name='user.settings'),
re_path(r'^settings/history/$', user.UserHistoryView.as_view(), name='user.settings.history'),
@@ -106,9 +107,9 @@ urlpatterns = [
re_path(r'^settings/2fa/regenemergency', user.User2FARegenerateEmergencyView.as_view(),
name='user.settings.2fa.regenemergency'),
re_path(r'^settings/2fa/totp/(?P<device>[0-9]+)/confirm', user.User2FADeviceConfirmTOTPView.as_view(),
name='user.settings.2fa.confirm.totp'),
name='user.settings.2fa.confirm.otp_totp.totpdevice'),
re_path(r'^settings/2fa/webauthn/(?P<device>[0-9]+)/confirm', user.User2FADeviceConfirmWebAuthnView.as_view(),
name='user.settings.2fa.confirm.webauthn'),
name='user.settings.2fa.confirm.pretixbase.webauthndevice'),
re_path(r'^settings/2fa/(?P<devicetype>[^/]+)/(?P<device>[0-9]+)/delete', user.User2FADeviceDeleteView.as_view(),
name='user.settings.2fa.delete'),
re_path(r'^settings/email/confirm$', user.UserEmailConfirmView.as_view(), name='user.settings.email.confirm'),
@@ -350,7 +351,6 @@ urlpatterns = [
re_path(r'^questions/(?P<question>\d+)/change$', item.QuestionUpdate.as_view(),
name='event.items.questions.edit'),
re_path(r'^questions/add$', item.QuestionCreate.as_view(), name='event.items.questions.add'),
re_path(r'^questionnaires/$', item.QuestionnairesEditor.as_view(), name='event.items.questionnaires'),
re_path(r'^quotas/$', item.QuotaList.as_view(), name='event.items.quotas'),
re_path(r'^quotas/bulk_action$', item.QuotaBulkAction.as_view(), name='event.items.quotas.bulkaction'),
re_path(r'^quotas/bulk_edit$', item.QuotaBulkUpdateView.as_view(), name='event.items.quotas.bulkedit'),
+41 -6
View File
@@ -35,6 +35,7 @@
import base64
import json
import logging
import math
import time
from urllib.parse import quote, urljoin, urlparse
@@ -50,11 +51,12 @@ from django.shortcuts import redirect, render
from django.urls import reverse
from django.utils.functional import cached_property
from django.utils.http import url_has_allowed_host_and_scheme
from django.utils.translation import gettext_lazy as _
from django.utils.timezone import now
from django.utils.translation import gettext_lazy as _, ngettext
from django.views.decorators.csrf import csrf_exempt
from django.views.decorators.http import require_http_methods
from django.views.generic import TemplateView
from django_otp import match_token
from django_otp import devices_for_user
from django_otp.plugins.otp_static.models import StaticDevice
from webauthn.helpers import generate_challenge
@@ -463,6 +465,7 @@ class Login2FAView(TemplateView):
token = request.POST.get('token', '').strip().replace(' ', '')
valid = False
retry_after = None
if 'webauthn_challenge' in self.request.session and token.startswith('{'):
challenge = self.request.session['webauthn_challenge']
@@ -518,12 +521,28 @@ class Login2FAView(TemplateView):
valid = True
break
else:
valid = match_token(self.user, token)
if isinstance(valid, StaticDevice):
with transaction.atomic():
for device in devices_for_user(self.user, for_verify=True):
if isinstance(device, StaticDevice) and len(token) < 12:
# If we enter a wrong TOTP token (which is 6 characters), do not even try if it is a valid
# emergency token, which will only "lock up" the StaticDevice due to the throttling plugin
# and just locks people out without security gain.
continue
if device.verify_token(token):
valid = True
break
elif hasattr(device, 'verify_is_allowed'):
verify_allowed, reason_dict = device.verify_is_allowed()
if not verify_allowed:
if not retry_after or reason_dict['locked_until'] > retry_after:
retry_after = reason_dict['locked_until']
else:
device = None
if isinstance(device, StaticDevice):
self.user.send_security_notice([
_("A recovery code for two-factor authentification was used to log in.")
])
if valid:
logger.info(f"Backend login successful for user {self.user.pk} with 2FA.")
pretix_successful_logins.inc(1)
@@ -536,7 +555,23 @@ class Login2FAView(TemplateView):
return redirect('control:index')
else:
pretix_failed_logins.inc(1, reason="2fa")
messages.error(request, _('Invalid code, please try again.'))
msg = _('Invalid code, please try again.')
if retry_after:
seconds = (retry_after - now()).total_seconds()
minutes = seconds / 60
if minutes >= 1:
msg = ngettext(
'Invalid code. Please try again after waiting {value} minute.',
'Invalid code. Please try again after waiting {value} minutes.',
minutes,
).format(value=math.ceil(minutes))
elif seconds >= 1:
msg = ngettext(
'Invalid code. Please try again after waiting {value} second.',
'Invalid code. Please try again after waiting {value} seconds.',
seconds,
).format(value=math.ceil(seconds))
messages.error(request, msg)
return redirect('control:auth.login.2fa')
def get_context_data(self, **kwargs):
+5 -2
View File
@@ -402,9 +402,12 @@ def event_index_widgets_lazy(request, organizer, event):
except SubEvent.DoesNotExist:
pass
can_view_orders = request.user.has_event_permission(request.organizer, request.event, 'event.orders:read',
request=request)
widgets = []
for r, result in event_dashboard_widgets.send(sender=request.event, subevent=subevent, lazy=False):
widgets.extend(result)
if can_view_orders:
for r, result in event_dashboard_widgets.send(sender=request.event, subevent=subevent, lazy=False):
widgets.extend(result)
return build_json_response(widgets)
+62 -7
View File
@@ -56,7 +56,7 @@ from django.utils.functional import cached_property
from django.utils.timezone import now
from django.utils.translation import gettext, gettext_lazy as _
from django.views.decorators.http import require_http_methods
from django.views.generic import FormView, ListView, TemplateView, View
from django.views.generic import FormView, ListView, View
from django.views.generic.detail import DetailView, SingleObjectMixin
from django_countries.fields import Country
@@ -65,6 +65,7 @@ from pretix.api.serializers.item import (
ItemVariationSerializer,
)
from pretix.base.forms import I18nFormSet
from pretix.base.forms.questions import get_fake_attendee_questions
from pretix.base.models import (
CartPosition, Item, ItemCategory, ItemProgramTime, ItemVariation, LogEntry,
OrderPosition, Question, QuestionAnswer, QuestionOption, Quota,
@@ -436,7 +437,66 @@ class QuestionList(ListView):
template_name = 'pretixcontrol/items/questions.html'
def get_queryset(self):
return self.request.event.questions
return self.request.event.questions.prefetch_related('items')
def get_context_data(self, **kwargs):
ctx = super().get_context_data(**kwargs)
questions = get_fake_attendee_questions(self.request.event.settings)
questions += list(ctx['questions'])
questions.sort(key=lambda q: q.position)
ctx['questions'] = questions
return ctx
@transaction.atomic
@event_permission_required("event.items:write")
@require_http_methods(["POST"])
def reorder_questions(request, organizer, event):
try:
ids = json.loads(request.body.decode('utf-8'))['ids']
except (JSONDecodeError, KeyError, ValueError):
return HttpResponseBadRequest("expected JSON: {ids:[]}")
qs = request.event.questions.filter(container_type=request.GET['container_type'])
# filter system_questions - normal questions are int/digit, system_questions strings
custom_question_ids = [i for i in ids if i.isdigit()]
input_questions = list(qs.filter(id__in=custom_question_ids))
if len(input_questions) != len(custom_question_ids):
raise Http404(_("Some of the provided object ids are invalid."))
if len(input_questions) != qs.count():
raise Http404(_("Not all objects have been selected."))
for q in input_questions:
pos = ids.index(str(q.pk))
if pos != q.position: # Save unneccessary UPDATE queries
q.position = pos
q.save(update_fields=['position'])
q.log_action(
'pretix.event.question.reordered', user=request.user, data={
'position': pos,
}
)
if request.GET['container_type'] == Question.ContainerType.ORDERPOSITION:
system_question_order = {}
for s in ('attendee_name_parts', 'attendee_email', 'company', 'street', 'zipcode', 'city', 'country'):
if s in ids:
system_question_order[s] = ids.index(s)
else:
system_question_order[s] = -1
request.event.settings.system_question_order = system_question_order
request.event.log_action(
'pretix.event.settings', user=request.user, data={
'system_question_order': system_question_order,
}
)
return HttpResponse()
class QuestionDelete(EventPermissionRequiredMixin, CompatDeleteView):
@@ -706,11 +766,6 @@ class QuestionCreate(EventPermissionRequiredMixin, QuestionMixin, CreateView):
return ret
class QuestionnairesEditor(EventPermissionRequiredMixin, TemplateView):
permission = 'can_change_items'
template_name = 'pretixcontrol/items/questionnaires.html'
class QuotaQueryMixin:
@cached_property
+20 -4
View File
@@ -1177,6 +1177,8 @@ class OrderRefundView(OrderView):
manual_value = formats.sanitize_separators(manual_value)
try:
manual_value = Decimal(manual_value)
if manual_value < Decimal("0.00"):
raise TypeError("Please do not use negative numbers")
except (DecimalException, TypeError):
messages.error(self.request, _('You entered an invalid number.'))
is_valid = False
@@ -1206,6 +1208,8 @@ class OrderRefundView(OrderView):
giftcard_value = formats.sanitize_separators(giftcard_value)
try:
giftcard_value = Decimal(giftcard_value)
if giftcard_value < Decimal("0.00"):
raise TypeError("Please do not use negative numbers")
except (DecimalException, TypeError):
messages.error(self.request, _('You entered an invalid number.'))
is_valid = False
@@ -1255,6 +1259,8 @@ class OrderRefundView(OrderView):
offsetting_value = formats.sanitize_separators(offsetting_value)
try:
offsetting_value = Decimal(offsetting_value)
if offsetting_value < Decimal("0.00"):
raise TypeError("Please do not use negative numbers")
except (DecimalException, TypeError):
messages.error(self.request, _('You entered an invalid number.'))
is_valid = False
@@ -1271,6 +1277,9 @@ class OrderRefundView(OrderView):
if offset_order.event.currency != self.request.event.currency:
messages.error(self.request, _('You entered an order in an event with a different currency.'))
is_valid = False
if not self.request.user.has_event_permission(self.request.organizer, offset_order.event, 'event.orders:write', request=self.request):
messages.error(self.request, _('You entered an order in an event that you do not have access to.'))
is_valid = False
refunds.append(OrderRefund(
order=order,
payment=None,
@@ -1286,10 +1295,13 @@ class OrderRefundView(OrderView):
))
for identifier, prov in self.request.event.get_payment_providers().items():
# prof = process form, not a typo for prov(ider)
prof_value = self.request.POST.get(f'newrefund-{identifier}', '0') or '0'
prof_value = formats.sanitize_separators(prof_value)
try:
prof_value = Decimal(prof_value)
if prof_value < Decimal("0.00"):
raise TypeError("Please do not use negative numbers")
except (DecimalException, TypeError):
messages.error(self.request, _('You entered an invalid number.'))
is_valid = False
@@ -1313,6 +1325,8 @@ class OrderRefundView(OrderView):
value = formats.sanitize_separators(value)
try:
value = Decimal(value)
if value < Decimal("0.00"):
raise TypeError("Please do not use negative numbers")
except (DecimalException, TypeError):
messages.error(self.request, _('You entered an invalid number.'))
is_valid = False
@@ -1342,7 +1356,12 @@ class OrderRefundView(OrderView):
))
any_success = False
if refund_selected == full_refund and is_valid:
if refund_selected != full_refund:
messages.error(self.request, _('The refunds you selected do not match the selected total refund '
'amount.'))
is_valid = False
if is_valid:
for r in refunds:
r.save()
order.log_action('pretix.event.order.refund.created', {
@@ -1414,9 +1433,6 @@ class OrderRefundView(OrderView):
)
}))
return redirect(self.get_order_url())
else:
messages.error(self.request, _('The refunds you selected do not match the selected total refund '
'amount.'))
def post(self, *args, **kwargs):
if self.start_form.is_valid():
+4 -4
View File
@@ -778,9 +778,9 @@ class OrganizerPluginEvents(OrganizerDetailViewMixin, OrganizerPermissionRequire
def get_form_kwargs(self):
kwargs = super().get_form_kwargs()
kwargs["events"] = self.request.user.get_events_with_permission(
"event.settings.general:write", request=self.request
).filter(organizer=self.request.organizer)
# Assumption: Who has access to modify organizer settings may see all events and disable/enable plugins
# for them. Otherwise, inconsistent situations occur.
kwargs["events"] = self.request.organizer.events.all()
kwargs["initial"] = {
"events": self.request.organizer.events.filter(plugins__regex='(^|,)' + self.plugin.module + '(,|$)')
}
@@ -2202,7 +2202,7 @@ class ExportView(OrganizerPermissionRequiredMixin, ExportMixin, ListView):
owner=self.request.user,
timezone=str(get_current_timezone()),
)
if not self.scheduled:
if not self.scheduled and not self.scheduled_copy_from:
initial = {
"mail_subject": gettext("Export: {title}").format(title=self.exporter.verbose_name),
"mail_template": gettext(
+5
View File
@@ -1276,6 +1276,11 @@ class SubEventBulkEdit(SubEventQueryMixin, EventPermissionRequiredMixin, FormVie
self._default_meta = self.request.event.meta_data
for p in self.request.organizer.meta_properties.all():
if p.protected and not self.request.user.has_organizer_permission(
self.request.organizer, 'organizer.settings.general:write', request=self.request
):
continue
inst = SubEventMetaValue(property=p)
if len(matches[p.id]) == 1 and matches[p.id][0]['c'] == total:
inst.value = matches[p.id][0]['value']
+15 -25
View File
@@ -59,6 +59,7 @@ from django.utils.translation import gettext_lazy as _
from django.views import View
from django.views.decorators.cache import never_cache
from django.views.generic import FormView, ListView, TemplateView, UpdateView
from django_otp import devices_for_user
from django_otp.plugins.otp_static.models import StaticDevice
from django_otp.plugins.otp_totp.models import TOTPDevice
from django_scopes import scopes_disabled
@@ -85,7 +86,6 @@ from pretix.helpers.ratelimit import rate_limit, rate_limit_reset
from pretix.helpers.security import session_reauth
from pretix.helpers.u2f import websafe_encode
REAL_DEVICE_TYPES = (TOTPDevice, WebAuthnDevice, U2FDevice)
logger = logging.getLogger(__name__)
@@ -313,17 +313,7 @@ class User2FAMainView(RecentAuthenticationRequiredMixin, TemplateView):
except StaticDevice.DoesNotExist:
ctx['static_tokens_device'] = None
ctx['devices'] = []
for dt in REAL_DEVICE_TYPES:
objs = list(dt.objects.filter(user=self.request.user, confirmed=True))
for obj in objs:
if dt == TOTPDevice:
obj.devicetype = 'totp'
elif dt == U2FDevice:
obj.devicetype = 'u2f'
elif dt == WebAuthnDevice:
obj.devicetype = 'webauthn'
ctx['devices'] += objs
ctx['devices'] = [d for d in devices_for_user(self.request.user) if not isinstance(d, StaticDevice)]
ctx['obligatory'] = None
if settings.PRETIX_OBLIGATORY_2FA is True:
@@ -342,9 +332,9 @@ class User2FADeviceAddView(RecentAuthenticationRequiredMixin, FormView):
template_name = 'pretixcontrol/user/2fa_add.html'
def form_valid(self, form):
if form.cleaned_data['devicetype'] == 'totp':
if form.cleaned_data['devicetype'] == 'otp_totp.totpdevice':
dev = TOTPDevice.objects.create(user=self.request.user, confirmed=False, name=form.cleaned_data['name'])
elif form.cleaned_data['devicetype'] == 'webauthn':
elif form.cleaned_data['devicetype'] == 'pretixbase.webauthndevice':
if not self.request.is_secure():
messages.error(self.request,
_('Security devices are only available if pretix is served via HTTPS.'))
@@ -364,11 +354,11 @@ class User2FADeviceDeleteView(RecentAuthenticationRequiredMixin, TemplateView):
@cached_property
def device(self):
if self.kwargs['devicetype'] == 'totp':
if self.kwargs['devicetype'] == 'otp_totp.totpdevice':
return get_object_or_404(TOTPDevice, user=self.request.user, pk=self.kwargs['device'], confirmed=True)
elif self.kwargs['devicetype'] == 'webauthn':
elif self.kwargs['devicetype'] == 'pretixbase.webauthndevice':
return get_object_or_404(WebAuthnDevice, user=self.request.user, pk=self.kwargs['device'], confirmed=True)
elif self.kwargs['devicetype'] == 'u2f':
elif self.kwargs['devicetype'] == 'pretixbase.u2fdevice':
return get_object_or_404(U2FDevice, user=self.request.user, pk=self.kwargs['device'], confirmed=True)
def get_context_data(self, **kwargs):
@@ -386,7 +376,7 @@ class User2FADeviceDeleteView(RecentAuthenticationRequiredMixin, TemplateView):
msgs = [
_('A two-factor authentication device has been removed from your account.')
]
if not any(dt.objects.filter(user=self.request.user, confirmed=True) for dt in REAL_DEVICE_TYPES):
if not any(d.confirmed for d in devices_for_user(self.request.user) if not isinstance(d, StaticDevice)):
self.request.user.require_2fa = False
self.request.user.save()
self.request.user.log_action('pretix.user.settings.2fa.disabled', user=self.request.user)
@@ -461,7 +451,7 @@ class User2FADeviceConfirmWebAuthnView(RecentAuthenticationRequiredMixin, Templa
).first()
if credential_id_exists:
messages.error(request, _('This security device is already registered.'))
return redirect(reverse('control:user.settings.2fa.confirm.webauthn', kwargs={
return redirect(reverse('control:user.settings.2fa.confirm.pretixbase.webauthndevice', kwargs={
'device': self.device.pk
}))
@@ -475,7 +465,7 @@ class User2FADeviceConfirmWebAuthnView(RecentAuthenticationRequiredMixin, Templa
self.device.save()
self.request.user.log_action('pretix.user.settings.2fa.device.added', user=self.request.user, data={
'id': self.device.pk,
'devicetype': 'u2f',
'devicetype': 'pretixbase.webauthndevice',
'name': self.device.name,
})
notices = [
@@ -503,7 +493,7 @@ class User2FADeviceConfirmWebAuthnView(RecentAuthenticationRequiredMixin, Templa
except Exception:
messages.error(request, _('The registration could not be completed. Please try again.'))
logger.exception('WebAuthn registration failed')
return redirect(reverse('control:user.settings.2fa.confirm.webauthn', kwargs={
return redirect(reverse('control:user.settings.2fa.confirm.pretixbase.webauthndevice', kwargs={
'device': self.device.pk
}))
@@ -537,7 +527,7 @@ class User2FADeviceConfirmTOTPView(RecentAuthenticationRequiredMixin, TemplateVi
self.request.user.log_action('pretix.user.settings.2fa.device.added', user=self.request.user, data={
'id': self.device.pk,
'name': self.device.name,
'devicetype': 'totp'
'devicetype': 'otp_totp.totpdevice'
})
notices = [
_('A new two-factor authentication device has been added to your account.')
@@ -563,7 +553,7 @@ class User2FADeviceConfirmTOTPView(RecentAuthenticationRequiredMixin, TemplateVi
else:
messages.error(request, _('The code you entered was not valid. If this problem persists, please check '
'that the date and time of your phone are configured correctly.'))
return redirect(reverse('control:user.settings.2fa.confirm.totp', kwargs={
return redirect(reverse('control:user.settings.2fa.confirm.otp_totp.totpdevice', kwargs={
'device': self.device.pk
}))
@@ -594,7 +584,7 @@ class User2FAEnableView(RecentAuthenticationRequiredMixin, TemplateView):
template_name = 'pretixcontrol/user/2fa_enable.html'
def dispatch(self, request, *args, **kwargs):
if not any(dt.objects.filter(user=self.request.user, confirmed=True) for dt in REAL_DEVICE_TYPES):
if not any(d.confirmed for d in devices_for_user(self.request.user) if not isinstance(d, StaticDevice)):
messages.error(request, _('Please configure at least one device before enabling two-factor '
'authentication.'))
return redirect(reverse('control:user.settings.2fa'))
@@ -956,7 +946,7 @@ class UserEmailConfirmView(FormView):
@transaction.atomic()
def form_valid(self, form):
reason = self.request.GET['reason']
reason = self.request.GET.get('reason')
if reason not in ('email_change', 'email_verify'):
raise PermissionDenied
try:
+23
View File
@@ -40,6 +40,7 @@ from django.utils.functional import cached_property
from django.utils.translation import gettext_lazy as _
from django.views import View
from django.views.generic import ListView, TemplateView
from django_otp import devices_for_user
from django_otp.plugins.otp_static.models import StaticDevice
from hijack import signals
@@ -107,6 +108,9 @@ class UserEditView(AdministratorPermissionRequiredMixin, RecentAuthenticationReq
ctx['backend'] = (
b[self.object.auth_backend].verbose_name if self.object.auth_backend in b else self.object.auth_backend
)
ctx['devices'] = devices_for_user(self.object)
return ctx
def get_success_url(self):
@@ -183,6 +187,25 @@ class UserEmergencyTokenView(AdministratorPermissionRequiredMixin, RecentAuthent
return reverse('control:users.edit', kwargs=self.kwargs)
class Reset2FADriftThrottleView(AdministratorPermissionRequiredMixin, RecentAuthenticationRequiredMixin, View):
def get(self, request, *args, **kwargs):
return redirect(reverse('control:users.edit', kwargs=self.kwargs))
def post(self, request, *args, **kwargs):
self.object = get_object_or_404(User, pk=self.kwargs.get("id"))
self.object.totpdevice_set.update(drift=0, throttling_failure_timestamp=None, throttling_failure_count=0)
self.object.staticdevice_set.update(throttling_failure_timestamp=None, throttling_failure_count=0)
self.object.log_action('pretix.user.settings.2fa.resetdrift', user=self.request.user)
messages.success(request, _(
'The drift values for TOTP devices have been reset.'
))
return redirect(self.get_success_url())
def get_success_url(self):
return reverse('control:users.edit', kwargs=self.kwargs)
class UserAnonymizeView(AdministratorPermissionRequiredMixin, RecentAuthenticationRequiredMixin, TemplateView):
template_name = "pretixcontrol/users/anonymize.html"
+18
View File
@@ -27,6 +27,7 @@ from http import cookies
from django.conf import settings
from django.core.exceptions import SuspiciousFileOperation
from django.middleware.csrf import CsrfViewMiddleware as BaseCsrfMiddleware
from PIL import Image
from requests.adapters import HTTPAdapter
from urllib3.connection import HTTPConnection, HTTPSConnection
@@ -42,6 +43,7 @@ from urllib3.util.timeout import _DEFAULT_TIMEOUT
from pretix.helpers.reportlab import ThumbnailingImageReader
from pretix.helpers.ssrf import should_block_access
from pretix.multidomain.middlewares import CsrfViewMiddleware
def monkeypatch_vobject_performance():
@@ -242,6 +244,20 @@ def monkeypatch_reportlab_imagereader():
utils.ImageReader.__init__ = new_init
def monkeypatch_csrf_middleware():
# Some views from django or plugins use the middleware or the derived decorators directly,
# so we have to also patch the stock middleware
BaseCsrfMiddleware._get_secret = CsrfViewMiddleware._get_secret
BaseCsrfMiddleware._set_csrf_cookie = CsrfViewMiddleware._set_csrf_cookie
def monkeypatch_json_constants():
from json.decoder import _CONSTANTS # noqa
del _CONSTANTS['-Infinity']
del _CONSTANTS['Infinity']
del _CONSTANTS['NaN']
def monkeypatch_all_at_ready():
monkeypatch_vobject_performance()
monkeypatch_pillow_safer()
@@ -249,3 +265,5 @@ def monkeypatch_all_at_ready():
monkeypatch_urllib3_ssrf_protection()
monkeypatch_cookie_morsel()
monkeypatch_reportlab_imagereader()
monkeypatch_csrf_middleware()
monkeypatch_json_constants()
+346 -274
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-08-24 15:35+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2026-07-15 14:20+0000\n"
"Last-Translator: Llewelyn Barkhuizen <llewelyn@akademia.ac.za>\n"
"Language-Team: Afrikaans <https://translate.pretix.eu/projects/pretix/pretix/"
@@ -198,7 +198,7 @@ msgid "Allowed Post Logout URIs list, space separated"
msgstr ""
#: pretix/api/models.py pretix/base/models/customers.py
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/payment.py
msgid "Client ID"
msgstr ""
@@ -1718,6 +1718,18 @@ msgstr ""
msgid "Payment providers"
msgstr ""
#: pretix/base/exporters/invoices.py pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission status"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission date"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Cancellation"
msgstr ""
@@ -2361,7 +2373,6 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/organizers/giftcard.html
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_form.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
@@ -2385,7 +2396,6 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_cart.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Quantity"
msgstr ""
@@ -2467,7 +2477,6 @@ msgstr ""
#: pretix/base/exporters/orderlist.py
#: pretix/control/templates/pretixcontrol/search/payments.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payment ID"
msgstr ""
@@ -4225,6 +4234,10 @@ msgstr ""
msgid "Initialization date"
msgstr ""
#: pretix/base/models/devices.py
msgid "Security profile"
msgstr ""
#: pretix/base/models/discount.py
msgctxt "subevent"
msgid "Dates can be mixed without limitation"
@@ -5440,6 +5453,10 @@ msgstr ""
msgid "Maximum value"
msgstr ""
#: pretix/base/models/items.py
msgid "Minimum length"
msgstr ""
#: pretix/base/models/items.py
msgid "Maximum length"
msgstr ""
@@ -5506,6 +5523,10 @@ msgstr ""
msgid "The maximum value must not be lower than the minimum value."
msgstr ""
#: pretix/base/models/items.py
msgid "The maximum length must not be shorter than the minimum length."
msgstr ""
#: pretix/base/models/items.py
msgid ""
"The system already contains answers to this question that are not compatible "
@@ -5999,10 +6020,6 @@ msgstr ""
msgid "This reference will be printed on your invoice for your convenience."
msgstr ""
#: pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/models/orders.py
#: pretix/plugins/badges/templates/pretixplugins/badges/control_order_position_buttons.html
msgid "Badge"
@@ -9476,6 +9493,17 @@ msgid ""
"'Last date of payments' configured above."
msgstr ""
#: pretix/base/settings.py
msgid "Allow postponed payment choice for sales channels"
msgstr ""
#: pretix/base/settings.py
msgid ""
"If postponed payment is allowed on a sales channel, customers can complete "
"their order without selecting a payment method. This is useful whenever "
"orders are not created by the same person who is making the payment."
msgstr ""
#: pretix/base/settings.py
msgid "Show start date"
msgstr ""
@@ -9997,12 +10025,6 @@ msgstr ""
msgid "Hide all unavailable dates from calendar or list views"
msgstr ""
#: pretix/base/settings.py
msgid ""
"This option currently only affects the calendar of this event series, not "
"the organizer-wide calendar."
msgstr ""
#: pretix/base/settings.py
msgid "Hide all past dates from calendar"
msgstr ""
@@ -14691,6 +14713,11 @@ msgctxt "rrule"
msgid "third"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "fourth"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "last"
@@ -15674,6 +15701,22 @@ msgstr ""
msgid "Queued emails have been aborted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been created."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been deleted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been changed."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been reordered."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Gift card acceptance for another organizer has been added."
msgstr ""
@@ -15876,6 +15919,10 @@ msgstr ""
msgid "A two-factor emergency code has been generated."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Drift and throttle values for two-factor devices have been reset."
msgstr ""
#: pretix/control/logdisplay.py
#, python-brace-format
msgid ""
@@ -16708,6 +16755,87 @@ msgid ""
"Granting access to your pretix account happens at your own risk."
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Authorize"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Error:"
msgstr ""
@@ -17069,82 +17197,6 @@ msgid_plural ""
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/event/delete.html
@@ -19256,7 +19308,7 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
msgid ""
"We strongly recommend against using short forms of more then 16 characters."
"We strongly recommend against using short forms of more than 16 characters."
msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
@@ -24196,6 +24248,7 @@ msgid "Add a new device"
msgstr ""
#: pretix/control/templates/pretixcontrol/user/2fa_main.html
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Emergency tokens"
msgstr ""
@@ -24440,6 +24493,26 @@ msgstr ""
msgid "Authentication backend"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Reset drift and throttle"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Available two-factor authentication methods"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "1 failed attempt since %(date)s"
msgid_plural "%(cnt)s failed attempts since %(date)s"
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "Currently locked until %(date)s"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Team memberships"
msgstr ""
@@ -24893,6 +24966,20 @@ msgstr ""
msgid "Invalid code, please try again."
msgstr ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} minute."
msgid_plural "Invalid code. Please try again after waiting {value} minutes."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} second."
msgid_plural "Invalid code. Please try again after waiting {value} seconds."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/checkin.py
msgid "The selected check-ins have been reverted."
msgstr ""
@@ -25645,6 +25732,10 @@ msgstr ""
msgid "You entered an order in an event with a different currency."
msgstr ""
#: pretix/control/views/orders.py
msgid "You entered an order in an event that you do not have access to."
msgstr ""
#: pretix/control/views/orders.py
msgid ""
"You can not refund more than the amount of a payment that is not yet "
@@ -25657,6 +25748,10 @@ msgid ""
"refunds."
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
#, python-brace-format
msgid ""
@@ -25698,10 +25793,6 @@ msgid ""
"Your {event} team"
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
msgid "The payment has been created successfully."
msgstr ""
@@ -26413,6 +26504,10 @@ msgid ""
"remain active."
msgstr ""
#: pretix/control/views/users.py
msgid "The drift values for TOTP devices have been reset."
msgstr ""
#: pretix/control/views/users.py
msgid "The new user has been created."
msgstr ""
@@ -26425,6 +26520,14 @@ msgstr ""
msgid "Bypass quota"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget used"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "The requested voucher does not exist."
msgstr ""
@@ -26577,12 +26680,11 @@ msgstr ""
#: pretix/plugins/autocheckin/apps.py pretix/plugins/badges/apps.py
#: pretix/plugins/banktransfer/apps.py pretix/plugins/checkinlists/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal/apps.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/pretixdroid/apps.py
#: pretix/plugins/reports/apps.py pretix/plugins/returnurl/apps.py
#: pretix/plugins/sendmail/apps.py pretix/plugins/statistics/apps.py
#: pretix/plugins/stripe/apps.py pretix/plugins/ticketoutputpdf/apps.py
#: pretix/plugins/webcheckin/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal2/apps.py
#: pretix/plugins/pretixdroid/apps.py pretix/plugins/reports/apps.py
#: pretix/plugins/returnurl/apps.py pretix/plugins/sendmail/apps.py
#: pretix/plugins/statistics/apps.py pretix/plugins/stripe/apps.py
#: pretix/plugins/ticketoutputpdf/apps.py pretix/plugins/webcheckin/apps.py
msgid "the pretix team"
msgstr ""
@@ -27133,7 +27235,6 @@ msgstr ""
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/control.html
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_assign.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payer"
@@ -27627,8 +27728,7 @@ msgstr ""
msgid "Automatically checked in"
msgstr ""
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal2/payment.py
msgid "Secret"
msgstr ""
@@ -27687,152 +27787,6 @@ msgstr ""
msgid "A fully customizable payment method for manual processing."
msgstr ""
#: pretix/plugins/paypal/apps.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal/apps.py
msgid ""
"Accept payments with your PayPal account. PayPal is one of the most popular "
"payment methods world-wide."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal/payment.py
msgid "PayPal account"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_confirm.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_form.html
msgid ""
"After you clicked continue, we will redirect you to PayPal to fill in your "
"payment details. You will then be redirected back here to review and confirm "
"your order."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
msgid ""
"Our attempt to execute your Payment via PayPal has failed. Please try again "
"or contact us."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/paypal2/apps.py
msgid ""
"Accept payments with your PayPal account. In addition to regular PayPal "
@@ -27842,10 +27796,23 @@ msgid ""
"methods world-wide."
msgstr ""
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal Merchant ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal2/payment.py pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Even if a customer chooses an Alternative Payment Method, they will always "
@@ -27914,6 +27881,26 @@ msgid ""
"while the last payment is still under investigation."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "-- Automatic --"
msgstr ""
@@ -27934,6 +27921,10 @@ msgstr ""
msgid "Connect with {icon} PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Please configure a PayPal Webhook to the following endpoint in order to "
@@ -27962,6 +27953,12 @@ msgstr ""
msgid "An error occurred during connecting with PayPal, please try again."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
@@ -27970,6 +27967,10 @@ msgid ""
"attempt. You can also try other payment methods, if available."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Something went wrong when requesting the payment status. Please try again."
@@ -27979,12 +27980,41 @@ msgstr ""
msgid "You may need to enable JavaScript for PayPal payments."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Refunding the amount via PayPal failed: The original payment does not "
"contain the required information to issue an automated refund."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal APM"
msgstr ""
@@ -28072,6 +28102,12 @@ msgstr ""
msgid "We will then charge your PayPal account and finalize the order."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"After placing your order, you will be able to select your desired payment "
@@ -28103,6 +28139,11 @@ msgid ""
"different payment method, if you prefer."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
msgid "Capture status"
msgstr ""
@@ -28113,6 +28154,17 @@ msgid ""
"money will not be disbursed and the order remain in its pending state."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca_return.html
@@ -28146,6 +28198,12 @@ msgid ""
"to resolve this case."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid ""
"An error occurred returning from PayPal: request parameters missing. Please "
@@ -28176,6 +28234,18 @@ msgid ""
"in detail below."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/pretixdroid/apps.py
msgid "Old check-in device API"
msgstr ""
@@ -30195,7 +30265,6 @@ msgstr ""
#: pretix/presale/forms/order.py
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "plus taxes"
msgstr ""
@@ -30616,6 +30685,31 @@ msgid ""
"Please go to the payment settings and activate one or more payment providers."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"Not sure yet? You can complete your order first and then select a payment "
"method later."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"To do so, please first remove the payment methods you already selected above."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed within %(minutes)s minutes."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed by %(deadline)s."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid "Proceed without selection"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_questions.html
msgid "Before we continue, we need you to answer some questions."
msgstr ""
@@ -30682,14 +30776,12 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "minimum amount to order: %(num)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "price"
msgid "free"
msgstr ""
@@ -30718,66 +30810,56 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Original price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "New price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s, at least %(price)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "<strong>plus</strong> %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "incl. %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "checkbox"
msgid "Select"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Decrease quantity"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Increase quantity"
msgstr ""
@@ -31238,12 +31320,10 @@ msgid "Your order qualifies for a discount"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Uncategorized items"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Show full-size image of %(item)s"
msgstr ""
@@ -31256,19 +31336,16 @@ msgstr[0] ""
msgstr[1] ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s without taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Set price in %(currency)s for %(item)s"
msgstr ""
@@ -31927,11 +32004,6 @@ msgid ""
"products at the specified price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "from %(minprice)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "You need to select at least %(number)s products."
+1 -84
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-07 09:33+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: Automatically generated\n"
"Language-Team: none\n"
@@ -765,194 +765,163 @@ msgstr ""
msgid "Google Pay"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -960,25 +929,21 @@ msgid ""
"in a new tab to continue."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -986,13 +951,11 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1000,115 +963,96 @@ msgid ""
"products, they will be added to your existing cart."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1117,138 +1061,111 @@ msgid ""
"again."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr ""
+346 -274
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-08-24 15:35+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: Automatically generated\n"
"Language-Team: none\n"
@@ -196,7 +196,7 @@ msgid "Allowed Post Logout URIs list, space separated"
msgstr ""
#: pretix/api/models.py pretix/base/models/customers.py
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/payment.py
msgid "Client ID"
msgstr ""
@@ -1716,6 +1716,18 @@ msgstr ""
msgid "Payment providers"
msgstr ""
#: pretix/base/exporters/invoices.py pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission status"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission date"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Cancellation"
msgstr ""
@@ -2359,7 +2371,6 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/organizers/giftcard.html
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_form.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
@@ -2383,7 +2394,6 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_cart.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Quantity"
msgstr ""
@@ -2465,7 +2475,6 @@ msgstr ""
#: pretix/base/exporters/orderlist.py
#: pretix/control/templates/pretixcontrol/search/payments.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payment ID"
msgstr ""
@@ -4223,6 +4232,10 @@ msgstr ""
msgid "Initialization date"
msgstr ""
#: pretix/base/models/devices.py
msgid "Security profile"
msgstr ""
#: pretix/base/models/discount.py
msgctxt "subevent"
msgid "Dates can be mixed without limitation"
@@ -5438,6 +5451,10 @@ msgstr ""
msgid "Maximum value"
msgstr ""
#: pretix/base/models/items.py
msgid "Minimum length"
msgstr ""
#: pretix/base/models/items.py
msgid "Maximum length"
msgstr ""
@@ -5504,6 +5521,10 @@ msgstr ""
msgid "The maximum value must not be lower than the minimum value."
msgstr ""
#: pretix/base/models/items.py
msgid "The maximum length must not be shorter than the minimum length."
msgstr ""
#: pretix/base/models/items.py
msgid ""
"The system already contains answers to this question that are not compatible "
@@ -5997,10 +6018,6 @@ msgstr ""
msgid "This reference will be printed on your invoice for your convenience."
msgstr ""
#: pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/models/orders.py
#: pretix/plugins/badges/templates/pretixplugins/badges/control_order_position_buttons.html
msgid "Badge"
@@ -9474,6 +9491,17 @@ msgid ""
"'Last date of payments' configured above."
msgstr ""
#: pretix/base/settings.py
msgid "Allow postponed payment choice for sales channels"
msgstr ""
#: pretix/base/settings.py
msgid ""
"If postponed payment is allowed on a sales channel, customers can complete "
"their order without selecting a payment method. This is useful whenever "
"orders are not created by the same person who is making the payment."
msgstr ""
#: pretix/base/settings.py
msgid "Show start date"
msgstr ""
@@ -9995,12 +10023,6 @@ msgstr ""
msgid "Hide all unavailable dates from calendar or list views"
msgstr ""
#: pretix/base/settings.py
msgid ""
"This option currently only affects the calendar of this event series, not "
"the organizer-wide calendar."
msgstr ""
#: pretix/base/settings.py
msgid "Hide all past dates from calendar"
msgstr ""
@@ -14689,6 +14711,11 @@ msgctxt "rrule"
msgid "third"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "fourth"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "last"
@@ -15672,6 +15699,22 @@ msgstr ""
msgid "Queued emails have been aborted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been created."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been deleted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been changed."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been reordered."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Gift card acceptance for another organizer has been added."
msgstr ""
@@ -15874,6 +15917,10 @@ msgstr ""
msgid "A two-factor emergency code has been generated."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Drift and throttle values for two-factor devices have been reset."
msgstr ""
#: pretix/control/logdisplay.py
#, python-brace-format
msgid ""
@@ -16706,6 +16753,87 @@ msgid ""
"Granting access to your pretix account happens at your own risk."
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Authorize"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Error:"
msgstr ""
@@ -17067,82 +17195,6 @@ msgid_plural ""
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/event/delete.html
@@ -19254,7 +19306,7 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
msgid ""
"We strongly recommend against using short forms of more then 16 characters."
"We strongly recommend against using short forms of more than 16 characters."
msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
@@ -24194,6 +24246,7 @@ msgid "Add a new device"
msgstr ""
#: pretix/control/templates/pretixcontrol/user/2fa_main.html
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Emergency tokens"
msgstr ""
@@ -24438,6 +24491,26 @@ msgstr ""
msgid "Authentication backend"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Reset drift and throttle"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Available two-factor authentication methods"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "1 failed attempt since %(date)s"
msgid_plural "%(cnt)s failed attempts since %(date)s"
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "Currently locked until %(date)s"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Team memberships"
msgstr ""
@@ -24891,6 +24964,20 @@ msgstr ""
msgid "Invalid code, please try again."
msgstr ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} minute."
msgid_plural "Invalid code. Please try again after waiting {value} minutes."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} second."
msgid_plural "Invalid code. Please try again after waiting {value} seconds."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/checkin.py
msgid "The selected check-ins have been reverted."
msgstr ""
@@ -25643,6 +25730,10 @@ msgstr ""
msgid "You entered an order in an event with a different currency."
msgstr ""
#: pretix/control/views/orders.py
msgid "You entered an order in an event that you do not have access to."
msgstr ""
#: pretix/control/views/orders.py
msgid ""
"You can not refund more than the amount of a payment that is not yet "
@@ -25655,6 +25746,10 @@ msgid ""
"refunds."
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
#, python-brace-format
msgid ""
@@ -25696,10 +25791,6 @@ msgid ""
"Your {event} team"
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
msgid "The payment has been created successfully."
msgstr ""
@@ -26411,6 +26502,10 @@ msgid ""
"remain active."
msgstr ""
#: pretix/control/views/users.py
msgid "The drift values for TOTP devices have been reset."
msgstr ""
#: pretix/control/views/users.py
msgid "The new user has been created."
msgstr ""
@@ -26423,6 +26518,14 @@ msgstr ""
msgid "Bypass quota"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget used"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "The requested voucher does not exist."
msgstr ""
@@ -26575,12 +26678,11 @@ msgstr ""
#: pretix/plugins/autocheckin/apps.py pretix/plugins/badges/apps.py
#: pretix/plugins/banktransfer/apps.py pretix/plugins/checkinlists/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal/apps.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/pretixdroid/apps.py
#: pretix/plugins/reports/apps.py pretix/plugins/returnurl/apps.py
#: pretix/plugins/sendmail/apps.py pretix/plugins/statistics/apps.py
#: pretix/plugins/stripe/apps.py pretix/plugins/ticketoutputpdf/apps.py
#: pretix/plugins/webcheckin/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal2/apps.py
#: pretix/plugins/pretixdroid/apps.py pretix/plugins/reports/apps.py
#: pretix/plugins/returnurl/apps.py pretix/plugins/sendmail/apps.py
#: pretix/plugins/statistics/apps.py pretix/plugins/stripe/apps.py
#: pretix/plugins/ticketoutputpdf/apps.py pretix/plugins/webcheckin/apps.py
msgid "the pretix team"
msgstr ""
@@ -27131,7 +27233,6 @@ msgstr ""
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/control.html
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_assign.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payer"
@@ -27625,8 +27726,7 @@ msgstr ""
msgid "Automatically checked in"
msgstr ""
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal2/payment.py
msgid "Secret"
msgstr ""
@@ -27685,152 +27785,6 @@ msgstr ""
msgid "A fully customizable payment method for manual processing."
msgstr ""
#: pretix/plugins/paypal/apps.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal/apps.py
msgid ""
"Accept payments with your PayPal account. PayPal is one of the most popular "
"payment methods world-wide."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal/payment.py
msgid "PayPal account"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_confirm.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_form.html
msgid ""
"After you clicked continue, we will redirect you to PayPal to fill in your "
"payment details. You will then be redirected back here to review and confirm "
"your order."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
msgid ""
"Our attempt to execute your Payment via PayPal has failed. Please try again "
"or contact us."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/paypal2/apps.py
msgid ""
"Accept payments with your PayPal account. In addition to regular PayPal "
@@ -27840,10 +27794,23 @@ msgid ""
"methods world-wide."
msgstr ""
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal Merchant ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal2/payment.py pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Even if a customer chooses an Alternative Payment Method, they will always "
@@ -27912,6 +27879,26 @@ msgid ""
"while the last payment is still under investigation."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "-- Automatic --"
msgstr ""
@@ -27932,6 +27919,10 @@ msgstr ""
msgid "Connect with {icon} PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Please configure a PayPal Webhook to the following endpoint in order to "
@@ -27960,6 +27951,12 @@ msgstr ""
msgid "An error occurred during connecting with PayPal, please try again."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
@@ -27968,6 +27965,10 @@ msgid ""
"attempt. You can also try other payment methods, if available."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Something went wrong when requesting the payment status. Please try again."
@@ -27977,12 +27978,41 @@ msgstr ""
msgid "You may need to enable JavaScript for PayPal payments."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Refunding the amount via PayPal failed: The original payment does not "
"contain the required information to issue an automated refund."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal APM"
msgstr ""
@@ -28070,6 +28100,12 @@ msgstr ""
msgid "We will then charge your PayPal account and finalize the order."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"After placing your order, you will be able to select your desired payment "
@@ -28101,6 +28137,11 @@ msgid ""
"different payment method, if you prefer."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
msgid "Capture status"
msgstr ""
@@ -28111,6 +28152,17 @@ msgid ""
"money will not be disbursed and the order remain in its pending state."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca_return.html
@@ -28144,6 +28196,12 @@ msgid ""
"to resolve this case."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid ""
"An error occurred returning from PayPal: request parameters missing. Please "
@@ -28174,6 +28232,18 @@ msgid ""
"in detail below."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/pretixdroid/apps.py
msgid "Old check-in device API"
msgstr ""
@@ -30193,7 +30263,6 @@ msgstr ""
#: pretix/presale/forms/order.py
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "plus taxes"
msgstr ""
@@ -30614,6 +30683,31 @@ msgid ""
"Please go to the payment settings and activate one or more payment providers."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"Not sure yet? You can complete your order first and then select a payment "
"method later."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"To do so, please first remove the payment methods you already selected above."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed within %(minutes)s minutes."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed by %(deadline)s."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid "Proceed without selection"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_questions.html
msgid "Before we continue, we need you to answer some questions."
msgstr ""
@@ -30680,14 +30774,12 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "minimum amount to order: %(num)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "price"
msgid "free"
msgstr ""
@@ -30716,66 +30808,56 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Original price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "New price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s, at least %(price)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "<strong>plus</strong> %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "incl. %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "checkbox"
msgid "Select"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Decrease quantity"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Increase quantity"
msgstr ""
@@ -31236,12 +31318,10 @@ msgid "Your order qualifies for a discount"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Uncategorized items"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Show full-size image of %(item)s"
msgstr ""
@@ -31254,19 +31334,16 @@ msgstr[0] ""
msgstr[1] ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s without taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Set price in %(currency)s for %(item)s"
msgstr ""
@@ -31925,11 +32002,6 @@ msgid ""
"products at the specified price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "from %(minprice)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "You need to select at least %(number)s products."
+1 -84
View File
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -766,194 +766,163 @@ msgstr ""
msgid "Google Pay"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -961,25 +930,21 @@ msgid ""
"in a new tab to continue."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -987,13 +952,11 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1001,115 +964,96 @@ msgid ""
"products, they will be added to your existing cart."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1118,138 +1062,111 @@ msgid ""
"again."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr ""
File diff suppressed because it is too large Load Diff
+7 -89
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2026-07-13 11:28+0000\n"
"Last-Translator: ahmed badr <ahmedbadr@oma.com.eg>\n"
"Language-Team: Arabic <https://translate.pretix.eu/projects/pretix/pretix-js/"
@@ -648,7 +648,8 @@ msgstr "خطأ غير معروف."
#: pretix/static/pretixcontrol/js/ui/main.js
msgid "Your color has great contrast and will provide excellent accessibility."
msgstr "يتميز لونك بتباين رائع ويسهل قراءته للغاية! وسيوفر إمكانية وصول ممتازة."
msgstr ""
"يتميز لونك بتباين رائع ويسهل قراءته للغاية! وسيوفر إمكانية وصول ممتازة."
#: pretix/static/pretixcontrol/js/ui/main.js
msgid ""
@@ -663,8 +664,8 @@ msgid ""
"Your color has insufficient contrast to white. Accessibility of your site "
"will be impacted."
msgstr ""
"اللون الذي اخترته لا يتمتع بتباين كافٍ مع اللون الأبيض. وسيؤثر ذلك على إمكانية "
"الوصول إلى موقعك."
"اللون الذي اخترته لا يتمتع بتباين كافٍ مع اللون الأبيض. وسيؤثر ذلك على "
"إمكانية الوصول إلى موقعك."
#: pretix/static/pretixcontrol/js/ui/main.js
msgid "Search query"
@@ -794,194 +795,163 @@ msgstr "التوقيت المحلي:"
msgid "Google Pay"
msgstr "Google Pay"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr "الكمية"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr "تقليل الكمية"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr "زيادة الكمية"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr "تصفية الأحداث حسب"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr "فلتر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr "السعر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr "السعر الأصلي: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr "السعر الجديد: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr "المختارة فقط"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr "تم اختيار %s فقط"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr "اختر النوع %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr "تم البيع بالكامل"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr "اشتري"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr "سجل"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr "محجوز"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr "مجاني"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr "من %(currency) s %(price)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr "صورة لـ %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr "يشمل %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr "بالإضافة إلى %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr "شامل الضريبة"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr "بالإضافة إلى الضرائب"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr "متوفر حاليا: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr "متوفرة مع القسيمة فقط"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr "حاليًا غير متوفر: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr "لم يعد متوفراً"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr "غير متوفر حاليًا: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr "الحد الأدنى للطلب: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr "إغلاق متجر التذاكر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr "لا يمكن تحميل متجر التذاكر."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -991,25 +961,21 @@ msgstr ""
"يوجد حالياً عدد كبير من المستخدمين في متجر التذاكر هذا. يرجى فتح المتجر في "
"علامة تبويب جديدة للمتابعة."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr "إغلاق/فتح متجر التذاكر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr "استئناف عملية الدفع"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr "لا يمكن إنشاء سلة التسوق. الرجاء المحاولة مرة أخرى في وقت لاحق"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1017,16 +983,14 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
"لم نتمكن من إنشاء سلة التسوق الخاصة بك، نظرًا لوجود عدد كبير جدًّا من "
"المستخدمين حاليًّا في متجر التذاكر هذا. يرجى النقر على «متابعة» لإعادة المحاولة "
"في علامة تبويب جديدة."
"المستخدمين حاليًّا في متجر التذاكر هذا. يرجى النقر على «متابعة» لإعادة "
"المحاولة في علامة تبويب جديدة."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr "قائمة الإنتظار"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1036,115 +1000,96 @@ msgstr ""
"لديك الآن سلة تسوق مفعلة لهذا الحدث. إذا قمت باختيار منتجات أخرى سيتم "
"إضافتها إلى سلة التسوق الموجودة حالياً."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr "استئناف الدفع"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr "استبدال قسيمة"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr "استبدال"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr "رمز القسيمة"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr "إغلاق"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr "إغلاق عملية الدفع"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr "لا يمكنك إلغاء هذه العملية. يرجى الانتظار حتى ينتهي التحميل."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr "استمرار"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr "انظر الاختلافات"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr "إخفاء الاختلافات"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr "اختر فعالية أخرى"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr "اختر تاريخا آخر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr "العودة"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr "الشهر القادم"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr "الشهر السابق"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr "الأسبوع القادم"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr "الأسبوع السابق"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr "خيارات المقاعد"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1155,138 +1100,111 @@ msgstr ""
"تم بيع جميع فئات التذاكر أو بعضها حاليًا. إذا أردت، يمكنك إضافة اسمك إلى "
"قائمة الانتظار. وسنقوم بإخطارك إذا توفرت مقاعد مرة أخرى."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr "تحميل المزيد"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr "الإثنين"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr "الثلاثاء"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr "الأربعاء"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr "الخميس"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr "الجمعة"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr "السبت"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr "الأحد"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr "الاثنين"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr "الثلاثاء"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr "الأربعاء"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr "الخميس"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr "الجمعة"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr "السبت"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr "الأحد"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr "يناير"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr "فبراير"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr "مارس"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr "أبريل"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr "هناك"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr "يونيو"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr "يوليو"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr "أغسطس"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr "سبتمبر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr "أكتوبر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr "نوفمبر"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr "ديسمبر"
+346 -274
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-08-24 15:35+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2024-12-11 01:00+0000\n"
"Last-Translator: Neriman Memmedli <nerim4n@pm.me>\n"
"Language-Team: Azerbaijani <https://translate.pretix.eu/projects/pretix/"
@@ -198,7 +198,7 @@ msgid "Allowed Post Logout URIs list, space separated"
msgstr ""
#: pretix/api/models.py pretix/base/models/customers.py
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/payment.py
msgid "Client ID"
msgstr ""
@@ -1718,6 +1718,18 @@ msgstr ""
msgid "Payment providers"
msgstr ""
#: pretix/base/exporters/invoices.py pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission status"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission date"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Cancellation"
msgstr ""
@@ -2361,7 +2373,6 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/organizers/giftcard.html
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_form.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
@@ -2385,7 +2396,6 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_cart.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Quantity"
msgstr ""
@@ -2467,7 +2477,6 @@ msgstr ""
#: pretix/base/exporters/orderlist.py
#: pretix/control/templates/pretixcontrol/search/payments.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payment ID"
msgstr ""
@@ -4225,6 +4234,10 @@ msgstr ""
msgid "Initialization date"
msgstr ""
#: pretix/base/models/devices.py
msgid "Security profile"
msgstr ""
#: pretix/base/models/discount.py
msgctxt "subevent"
msgid "Dates can be mixed without limitation"
@@ -5440,6 +5453,10 @@ msgstr ""
msgid "Maximum value"
msgstr ""
#: pretix/base/models/items.py
msgid "Minimum length"
msgstr ""
#: pretix/base/models/items.py
msgid "Maximum length"
msgstr ""
@@ -5506,6 +5523,10 @@ msgstr ""
msgid "The maximum value must not be lower than the minimum value."
msgstr ""
#: pretix/base/models/items.py
msgid "The maximum length must not be shorter than the minimum length."
msgstr ""
#: pretix/base/models/items.py
msgid ""
"The system already contains answers to this question that are not compatible "
@@ -5999,10 +6020,6 @@ msgstr ""
msgid "This reference will be printed on your invoice for your convenience."
msgstr ""
#: pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/models/orders.py
#: pretix/plugins/badges/templates/pretixplugins/badges/control_order_position_buttons.html
msgid "Badge"
@@ -9476,6 +9493,17 @@ msgid ""
"'Last date of payments' configured above."
msgstr ""
#: pretix/base/settings.py
msgid "Allow postponed payment choice for sales channels"
msgstr ""
#: pretix/base/settings.py
msgid ""
"If postponed payment is allowed on a sales channel, customers can complete "
"their order without selecting a payment method. This is useful whenever "
"orders are not created by the same person who is making the payment."
msgstr ""
#: pretix/base/settings.py
msgid "Show start date"
msgstr ""
@@ -9997,12 +10025,6 @@ msgstr ""
msgid "Hide all unavailable dates from calendar or list views"
msgstr ""
#: pretix/base/settings.py
msgid ""
"This option currently only affects the calendar of this event series, not "
"the organizer-wide calendar."
msgstr ""
#: pretix/base/settings.py
msgid "Hide all past dates from calendar"
msgstr ""
@@ -14691,6 +14713,11 @@ msgctxt "rrule"
msgid "third"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "fourth"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "last"
@@ -15674,6 +15701,22 @@ msgstr ""
msgid "Queued emails have been aborted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been created."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been deleted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been changed."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been reordered."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Gift card acceptance for another organizer has been added."
msgstr ""
@@ -15876,6 +15919,10 @@ msgstr ""
msgid "A two-factor emergency code has been generated."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Drift and throttle values for two-factor devices have been reset."
msgstr ""
#: pretix/control/logdisplay.py
#, python-brace-format
msgid ""
@@ -16708,6 +16755,87 @@ msgid ""
"Granting access to your pretix account happens at your own risk."
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Authorize"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Error:"
msgstr ""
@@ -17069,82 +17197,6 @@ msgid_plural ""
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/event/delete.html
@@ -19256,7 +19308,7 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
msgid ""
"We strongly recommend against using short forms of more then 16 characters."
"We strongly recommend against using short forms of more than 16 characters."
msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
@@ -24196,6 +24248,7 @@ msgid "Add a new device"
msgstr ""
#: pretix/control/templates/pretixcontrol/user/2fa_main.html
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Emergency tokens"
msgstr ""
@@ -24440,6 +24493,26 @@ msgstr ""
msgid "Authentication backend"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Reset drift and throttle"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Available two-factor authentication methods"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "1 failed attempt since %(date)s"
msgid_plural "%(cnt)s failed attempts since %(date)s"
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "Currently locked until %(date)s"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Team memberships"
msgstr ""
@@ -24893,6 +24966,20 @@ msgstr ""
msgid "Invalid code, please try again."
msgstr ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} minute."
msgid_plural "Invalid code. Please try again after waiting {value} minutes."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} second."
msgid_plural "Invalid code. Please try again after waiting {value} seconds."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/checkin.py
msgid "The selected check-ins have been reverted."
msgstr ""
@@ -25645,6 +25732,10 @@ msgstr ""
msgid "You entered an order in an event with a different currency."
msgstr ""
#: pretix/control/views/orders.py
msgid "You entered an order in an event that you do not have access to."
msgstr ""
#: pretix/control/views/orders.py
msgid ""
"You can not refund more than the amount of a payment that is not yet "
@@ -25657,6 +25748,10 @@ msgid ""
"refunds."
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
#, python-brace-format
msgid ""
@@ -25698,10 +25793,6 @@ msgid ""
"Your {event} team"
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
msgid "The payment has been created successfully."
msgstr ""
@@ -26413,6 +26504,10 @@ msgid ""
"remain active."
msgstr ""
#: pretix/control/views/users.py
msgid "The drift values for TOTP devices have been reset."
msgstr ""
#: pretix/control/views/users.py
msgid "The new user has been created."
msgstr ""
@@ -26425,6 +26520,14 @@ msgstr ""
msgid "Bypass quota"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget used"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "The requested voucher does not exist."
msgstr ""
@@ -26579,12 +26682,11 @@ msgstr ""
#: pretix/plugins/autocheckin/apps.py pretix/plugins/badges/apps.py
#: pretix/plugins/banktransfer/apps.py pretix/plugins/checkinlists/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal/apps.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/pretixdroid/apps.py
#: pretix/plugins/reports/apps.py pretix/plugins/returnurl/apps.py
#: pretix/plugins/sendmail/apps.py pretix/plugins/statistics/apps.py
#: pretix/plugins/stripe/apps.py pretix/plugins/ticketoutputpdf/apps.py
#: pretix/plugins/webcheckin/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal2/apps.py
#: pretix/plugins/pretixdroid/apps.py pretix/plugins/reports/apps.py
#: pretix/plugins/returnurl/apps.py pretix/plugins/sendmail/apps.py
#: pretix/plugins/statistics/apps.py pretix/plugins/stripe/apps.py
#: pretix/plugins/ticketoutputpdf/apps.py pretix/plugins/webcheckin/apps.py
msgid "the pretix team"
msgstr ""
@@ -27135,7 +27237,6 @@ msgstr ""
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/control.html
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_assign.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payer"
@@ -27629,8 +27730,7 @@ msgstr ""
msgid "Automatically checked in"
msgstr ""
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal2/payment.py
msgid "Secret"
msgstr ""
@@ -27689,152 +27789,6 @@ msgstr ""
msgid "A fully customizable payment method for manual processing."
msgstr ""
#: pretix/plugins/paypal/apps.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal/apps.py
msgid ""
"Accept payments with your PayPal account. PayPal is one of the most popular "
"payment methods world-wide."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal/payment.py
msgid "PayPal account"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_confirm.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_form.html
msgid ""
"After you clicked continue, we will redirect you to PayPal to fill in your "
"payment details. You will then be redirected back here to review and confirm "
"your order."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
msgid ""
"Our attempt to execute your Payment via PayPal has failed. Please try again "
"or contact us."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/paypal2/apps.py
msgid ""
"Accept payments with your PayPal account. In addition to regular PayPal "
@@ -27844,10 +27798,23 @@ msgid ""
"methods world-wide."
msgstr ""
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal Merchant ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal2/payment.py pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Even if a customer chooses an Alternative Payment Method, they will always "
@@ -27916,6 +27883,26 @@ msgid ""
"while the last payment is still under investigation."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "-- Automatic --"
msgstr ""
@@ -27936,6 +27923,10 @@ msgstr ""
msgid "Connect with {icon} PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Please configure a PayPal Webhook to the following endpoint in order to "
@@ -27964,6 +27955,12 @@ msgstr ""
msgid "An error occurred during connecting with PayPal, please try again."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
@@ -27972,6 +27969,10 @@ msgid ""
"attempt. You can also try other payment methods, if available."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Something went wrong when requesting the payment status. Please try again."
@@ -27981,12 +27982,41 @@ msgstr ""
msgid "You may need to enable JavaScript for PayPal payments."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Refunding the amount via PayPal failed: The original payment does not "
"contain the required information to issue an automated refund."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal APM"
msgstr ""
@@ -28074,6 +28104,12 @@ msgstr ""
msgid "We will then charge your PayPal account and finalize the order."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"After placing your order, you will be able to select your desired payment "
@@ -28105,6 +28141,11 @@ msgid ""
"different payment method, if you prefer."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
msgid "Capture status"
msgstr ""
@@ -28115,6 +28156,17 @@ msgid ""
"money will not be disbursed and the order remain in its pending state."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca_return.html
@@ -28148,6 +28200,12 @@ msgid ""
"to resolve this case."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid ""
"An error occurred returning from PayPal: request parameters missing. Please "
@@ -28178,6 +28236,18 @@ msgid ""
"in detail below."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/pretixdroid/apps.py
msgid "Old check-in device API"
msgstr ""
@@ -30197,7 +30267,6 @@ msgstr ""
#: pretix/presale/forms/order.py
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "plus taxes"
msgstr ""
@@ -30618,6 +30687,31 @@ msgid ""
"Please go to the payment settings and activate one or more payment providers."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"Not sure yet? You can complete your order first and then select a payment "
"method later."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"To do so, please first remove the payment methods you already selected above."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed within %(minutes)s minutes."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed by %(deadline)s."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid "Proceed without selection"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_questions.html
msgid "Before we continue, we need you to answer some questions."
msgstr ""
@@ -30684,14 +30778,12 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "minimum amount to order: %(num)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "price"
msgid "free"
msgstr ""
@@ -30720,66 +30812,56 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Original price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "New price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s, at least %(price)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "<strong>plus</strong> %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "incl. %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "checkbox"
msgid "Select"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Decrease quantity"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Increase quantity"
msgstr ""
@@ -31240,12 +31322,10 @@ msgid "Your order qualifies for a discount"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Uncategorized items"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Show full-size image of %(item)s"
msgstr ""
@@ -31258,19 +31338,16 @@ msgstr[0] ""
msgstr[1] ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s without taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Set price in %(currency)s for %(item)s"
msgstr ""
@@ -31929,11 +32006,6 @@ msgid ""
"products at the specified price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "from %(minprice)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "You need to select at least %(number)s products."
+1 -84
View File
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -766,194 +766,163 @@ msgstr ""
msgid "Google Pay"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -961,25 +930,21 @@ msgid ""
"in a new tab to continue."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -987,13 +952,11 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1001,115 +964,96 @@ msgid ""
"products, they will be added to your existing cart."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1118,138 +1062,111 @@ msgid ""
"again."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr ""
File diff suppressed because it is too large Load Diff
+1 -84
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2025-10-31 17:00+0000\n"
"Last-Translator: Núria Masclans <nuriamasclansserrat@gmail.com>\n"
"Language-Team: Catalan <https://translate.pretix.eu/projects/pretix/pretix-"
@@ -787,194 +787,163 @@ msgstr "La teva hora local:"
msgid "Google Pay"
msgstr "Google Pay"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr "Quantitat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr "Disminueix quantitat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr "Augmenta quantitat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr "Filtra els esdeveniments per"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr "Filtra"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr "Preu"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr "Preu original: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr "Nou preu: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr "Selecciona"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr "Selecciona %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr "Selecciona la variant %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr "Esgotat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr "Compra"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr "Registrar-vos"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr "Reservat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr "GRATUÏT"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr "des de %(price)s %(currency)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr "Imatge de %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr "Inclòs %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr "més %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr "incl. impostos"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr "més impostos"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr "disponibles: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr "Només disponible amb un cupó"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr "Encara no disponible"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr "Ja no està disponible"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr "No disponible"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr "Comanda mínima: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr "Tanca la botiga d'entrades"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr "No s'ha pogut carregar la botiga d'entrades."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -982,25 +951,21 @@ msgid ""
"in a new tab to continue."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1008,13 +973,11 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1022,115 +985,96 @@ msgid ""
"products, they will be added to your existing cart."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1139,138 +1083,111 @@ msgid ""
"again."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr ""
File diff suppressed because it is too large Load Diff
+1 -84
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2026-01-08 04:00+0000\n"
"Last-Translator: Jiří Pastrňák <jiri@pastrnak.email>\n"
"Language-Team: Czech <https://translate.pretix.eu/projects/pretix/pretix-js/"
@@ -801,194 +801,163 @@ msgstr "Místní čas:"
msgid "Google Pay"
msgstr "Google Pay"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr "Počet"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr "Snížit počet"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr "Zvýšit počet"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr "Filtrovat události"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr "Filtrovat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr "Cena"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr "Původní cena: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr "Nová cena: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr "Vybrat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr "Vybrat %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr "Vybrat variantu %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr "Vyprodáno"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr "Koupit"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr "Zaregistrovat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr "Rezervováno"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr "ZDARMA"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr "od %(currency)s %(price)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr "Obrázek%s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr "včetně %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr "plus %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr "včetně daní"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr "plus daně"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr "aktuálně k dispozici: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr "K dispozici pouze s poukazem"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr "Zatím není k dispozici"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr "Již není k dispozici"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr "Momentálně není k dispozici"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr "minimální množství pro objednávku: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr "Zavřít obchod"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr "Obchod vstupenek nemohl být načten."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -998,25 +967,21 @@ msgstr ""
"V současné době je v tomto obchodě s vstupenkami mnoho uživatelů. Otevřete "
"prosím obchod v nové kartě."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr "Obchod vstupenek otevřit"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr "Přejít k platbě"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr "Nákupní košík se nepodařilo vytvořit. Zkuste to prosím znovu"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1027,13 +992,11 @@ msgstr ""
"mnoho uživatelů. Klikněte prosím na \"Pokračovat\" a zkuste to znovu na nové "
"kartě."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr "Čekací listina"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1043,37 +1006,31 @@ msgstr ""
"V současné době máte aktivní košík pro tuto událost. Pokud vyberete další "
"produkty, budou přidány do vašeho košíku."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr "Obnovit checkout"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr "Uplatnit poukázku"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr "Uplatnit"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr "Kód poukázky"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr "Zavřít"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1082,79 +1039,66 @@ msgctxt "widget"
msgid "Close checkout"
msgstr "Obnovit checkout"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr "Pokračovat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr "Zobrazit možnosti"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr "Skrýt možnosti"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr "Vybrat jinou událost"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr "Vybrat jiný datum"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr "Zpět"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr "Následující měsíc"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr "Předchozí měsíc"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr "Příští týden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr "Předchozí týden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr "Otevřete výběr míst"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1166,138 +1110,111 @@ msgstr ""
"Pokud chcete, můžete se přidat na čekací listinu. Poté vás budeme "
"informovat, pokud budou místa opět volná."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr "Načíst více"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr "Po"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr "Út"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr "St"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr "Čt"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr "Pá"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr "So"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr "Ne"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr "Pondělí"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr "Úterý"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr "Středa"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr "Čtvrtek"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr "Pátek"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr "Sobota"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr "Neděle"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr "Leden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr "Únor"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr "Březen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr "Duben"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr "Květen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr "červen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr "Červenec"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr "Srpen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr "Září"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr "Říjen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr "Listopad"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr "Prosinec"
File diff suppressed because it is too large Load Diff
+1 -84
View File
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -767,194 +767,163 @@ msgstr ""
msgid "Google Pay"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -962,25 +931,21 @@ msgid ""
"in a new tab to continue."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -988,13 +953,11 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1002,115 +965,96 @@ msgid ""
"products, they will be added to your existing cart."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1119,138 +1063,111 @@ msgid ""
"again."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr ""
File diff suppressed because it is too large Load Diff
+1 -84
View File
@@ -6,7 +6,7 @@ msgid ""
msgstr ""
"Project-Id-Version: \n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2026-07-31 18:00+0000\n"
"Last-Translator: Nikolai <nikolai@lengefeldt.de>\n"
"Language-Team: Danish <https://translate.pretix.eu/projects/pretix/pretix-js/"
@@ -848,70 +848,59 @@ msgstr "Din lokaltid:"
msgid "Google Pay"
msgstr "Apple Pay"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy, javascript-format
#| msgctxt "widget"
@@ -920,87 +909,73 @@ msgctxt "widget"
msgid "Select variant %s"
msgstr "Vis varianter"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr "Udsolgt"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr "Læg i kurv"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr "Book nu"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr "Reserveret"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr "GRATIS"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr "fra %(currency)s %(price)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr "inkl. %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr "plus %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr "inkl. moms"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr "plus moms"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr "tilgængelig: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr "Kun tilgængelig med en rabatkode"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgid "Payment method unavailable"
@@ -1008,13 +983,11 @@ msgctxt "widget"
msgid "Not yet available"
msgstr "Betalingsmetode er ikke tilgængelig"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1023,26 +996,22 @@ msgctxt "widget"
msgid "Currently not available"
msgstr "tilgængelig: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr "minimumsantal: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr "Luk billetbutik"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr "Billetbutikken kunne ikke hentes."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1050,7 +1019,6 @@ msgid ""
"in a new tab to continue."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1059,7 +1027,6 @@ msgctxt "widget"
msgid "Open ticket shop"
msgstr "Luk billetbutik"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1068,13 +1035,11 @@ msgctxt "widget"
msgid "Checkout"
msgstr "Fortsæt booking"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr "Kurven kunne ikke oprettes. Prøv igen senere"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1082,13 +1047,11 @@ msgid ""
"this ticket shop. Please click \"Continue\" to retry in a new tab."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr "Venteliste"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1098,37 +1061,31 @@ msgstr ""
"Du har allerede en aktiv booking i gang for dette arrangement. Hvis du "
"vælger flere produkter, så vil de blive tilføjet din eksisterende booking."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr "Fortsæt booking"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr "Indløs rabatkode"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr "Indløs"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr "Rabatkode"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr "Luk"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1137,19 +1094,16 @@ msgctxt "widget"
msgid "Close checkout"
msgstr "Fortsæt booking"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr "Fortsæt"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1158,7 +1112,6 @@ msgctxt "widget"
msgid "Show variants"
msgstr "Vis varianter"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1167,43 +1120,36 @@ msgctxt "widget"
msgid "Hide variants"
msgstr "Vis varianter"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr "Vælg et andet arrangement"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr "Vælg en anden dato"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr "Tilbage"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr "Næste måned"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr "Forrige måned"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr "Næste uge"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, fuzzy
#| msgctxt "widget"
@@ -1212,13 +1158,11 @@ msgctxt "widget"
msgid "Previous week"
msgstr "Forrige måned"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr "Åbn sædevalg"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1227,138 +1171,111 @@ msgid ""
"again."
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr "Hent flere"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr "Man"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr "Tirs"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr "Ons"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr "Tors"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr "Fre"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr "Lør"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr "Søn"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr ""
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr "januar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr "februar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr "marts"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr "april"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr "maj"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr "juni"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr "juli"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr "august"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr "september"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr "oktober"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr "november"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr "december"
File diff suppressed because it is too large Load Diff
+1 -84
View File
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: \n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2026-07-06 02:00+0000\n"
"Last-Translator: Benedikt Bormann <mail@bbormann.de>\n"
"Language-Team: German <https://translate.pretix.eu/projects/pretix/pretix-js/"
@@ -800,194 +800,163 @@ msgstr "Deine lokale Zeit:"
msgid "Google Pay"
msgstr "Google Pay"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr "Menge"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr "Menge reduzieren"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr "Menge erhöhen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr "Veranstaltungen filtern nach"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr "Filtern"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr "Preis"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr "Originalpreis: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr "Neuer Preis: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr "Auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr "%s auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr "Variante %s auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr "Ausverkauft"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr "In den Warenkorb"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr "Anmelden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr "Reserviert"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr "GRATIS"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr "ab %(currency)s %(price)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr "Bild von %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr "inkl. %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr "zzgl. %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr "inkl. Steuern"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr "zzgl. Steuern"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr "aktuell verfügbar: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr "Nur mit Gutschein verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr "Noch nicht verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr "Nicht mehr verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr "Aktuell nicht verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr "minimale Bestellmenge: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr "Ticketshop schließen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr "Der Ticketshop konnte nicht geladen werden."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -997,25 +966,21 @@ msgstr ""
"Es sind derzeit sehr viele Benutzer in diesem Ticketshop. Bitte öffnen Sie "
"diesen Ticketshop in einem neuen Tab um fortzufahren."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr "Ticketshop öffnen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr "Buchung"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr "Der Warenkorb konnte nicht erstellt werden. Bitte erneut versuchen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1026,13 +991,11 @@ msgstr ""
"diesem Ticketshop sind. Bitte klicken Sie \"Weiter\" um es in einem neuen "
"Tab erneut zu versuchen."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr "Warteliste"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1042,43 +1005,36 @@ msgstr ""
"Sie haben einen aktiven Warenkorb für diese Veranstaltung. Wenn Sie mehr "
"Produkte auswählen, werden diese zu Ihrem Warenkorb hinzugefügt."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr "Kauf fortsetzen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr "Gutschein einlösen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr "Einlösen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr "Gutscheincode"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr "Schließen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr "Kauf schließen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
@@ -1086,73 +1042,61 @@ msgstr ""
"Sie können diese Aktion nicht abbrechen. Bitte warten Sie, bis der "
"Ladevorgang abgeschlossen ist."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr "Fortfahren"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr "Varianten zeigen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr "Varianten verstecken"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr "Andere Veranstaltung auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr "Anderen Termin auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr "Zurück"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr "Nächster Monat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr "Vorheriger Monat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr "Nächste Woche"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr "Vorherige Woche"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr "Sitzplan öffnen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1164,138 +1108,111 @@ msgstr ""
"möchten, können Sie sich in die Warteliste eintragen. Wir benachrichtigen "
"Sie dann, wenn die gewünschten Plätze wieder verfügbar sind."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr "Mehr laden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr "Mo"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr "Di"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr "Mi"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr "Do"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr "Fr"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr "Sa"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr "So"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr "Montag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr "Dienstag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr "Mittwoch"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr "Donnerstag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr "Freitag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr "Samstag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr "Sonntag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr "Januar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr "Februar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr "März"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr "April"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr "Mai"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr "Juni"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr "Juli"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr "August"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr "September"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr "Oktober"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr "November"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr "Dezember"
+1
View File
@@ -159,6 +159,7 @@ Erstattungsstatus
Erstattungsweg
erstmalig
etc
EU-USt-ID
EU-USt-ID-Nr
Event
Event-Absage
File diff suppressed because it is too large Load Diff
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: \n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-07-06 15:52+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: 2026-07-13 11:28+0000\n"
"Last-Translator: Raphael Michel <michel@rami.io>\n"
"Language-Team: German (informal) <https://translate.pretix.eu/projects/"
@@ -799,194 +799,163 @@ msgstr "Deine lokale Zeit:"
msgid "Google Pay"
msgstr "Google Pay"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Quantity"
msgstr "Menge"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Decrease quantity"
msgstr "Menge reduzieren"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Increase quantity"
msgstr "Menge erhöhen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter events by"
msgstr "Veranstaltungen filtern nach"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Filter"
msgstr "Filtern"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Price"
msgstr "Preis"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Original price: %s"
msgstr "Originalpreis: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "New price: %s"
msgstr "Neuer Preis: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Select"
msgstr "Auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select %s"
msgstr "%s auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Select variant %s"
msgstr "Variante %s auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Sold out"
msgstr "Ausverkauft"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Buy"
msgstr "In den Warenkorb"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Register"
msgstr "Anmelden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Reserved"
msgstr "Reserviert"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "FREE"
msgstr "GRATIS"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "from %(currency)s %(price)s"
msgstr "ab %(currency)s %(price)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "Image of %s"
msgstr "Bild von %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. %(rate)s% %(taxname)s"
msgstr "inkl. %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus %(rate)s% %(taxname)s"
msgstr "zzgl. %(rate)s% %(taxname)s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "incl. taxes"
msgstr "inkl. Steuern"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "plus taxes"
msgstr "zzgl. Steuern"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "currently available: %s"
msgstr "aktuell verfügbar: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Only available with a voucher"
msgstr "Nur mit Gutschein verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not yet available"
msgstr "Noch nicht verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Not available anymore"
msgstr "Nicht mehr verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Currently not available"
msgstr "Aktuell nicht verfügbar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
#, javascript-format
msgctxt "widget"
msgid "minimum amount to order: %s"
msgstr "minimale Bestellmenge: %s"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close ticket shop"
msgstr "Ticketshop schließen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The ticket shop could not be loaded."
msgstr "Der Ticketshop konnte nicht geladen werden."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -996,25 +965,21 @@ msgstr ""
"Es sind derzeit sehr viele Benutzer in diesem Ticketshop. Bitte öffne diesen "
"Ticketshop in einem neuen Tab um fortzufahren."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open ticket shop"
msgstr "Ticketshop öffnen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Checkout"
msgstr "Buchung"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "The cart could not be created. Please try again later"
msgstr "Der Warenkorb konnte nicht erstellt werden. Bitte erneut versuchen."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1025,13 +990,11 @@ msgstr ""
"diesem Ticketshop sind. Bitte klicke \"Weiter\" um es in einem neuen Tab "
"erneut zu versuchen."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Waiting list"
msgstr "Warteliste"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1041,43 +1004,36 @@ msgstr ""
"Du hast einen aktiven Warenkorb für diese Veranstaltung. Wenn du mehr "
"Produkte auswählst, werden diese zu deinem Warenkorb hinzugefügt."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Resume checkout"
msgstr "Kauf fortsetzen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem a voucher"
msgstr "Gutschein einlösen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Redeem"
msgstr "Einlösen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Voucher code"
msgstr "Gutscheincode"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close"
msgstr "Schließen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Close checkout"
msgstr "Kauf schließen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "You cannot cancel this operation. Please wait for loading to finish."
@@ -1085,73 +1041,61 @@ msgstr ""
"Du kannst diese Aktion nicht abbrechen. Bitte warte, bis der Ladevorgang "
"abgeschlossen ist."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Continue"
msgstr "Fortfahren"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Show variants"
msgstr "Varianten zeigen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Hide variants"
msgstr "Varianten verstecken"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different event"
msgstr "Andere Veranstaltung auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Choose a different date"
msgstr "Anderen Termin auswählen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Back"
msgstr "Zurück"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next month"
msgstr "Nächster Monat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous month"
msgstr "Vorheriger Monat"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Next week"
msgstr "Nächste Woche"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Previous week"
msgstr "Vorherige Woche"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Open seat selection"
msgstr "Sitzplan öffnen"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid ""
@@ -1163,138 +1107,111 @@ msgstr ""
"möchtest, kannst du dich in die Warteliste eintragen. Wir benachrichtigen "
"dich dann, wenn die gewünschten Plätze wieder verfügbar sind."
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgctxt "widget"
msgid "Load more"
msgstr "Mehr laden"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Mo"
msgstr "Mo"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tu"
msgstr "Di"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "We"
msgstr "Mi"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Th"
msgstr "Do"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Fr"
msgstr "Fr"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sa"
msgstr "Sa"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Su"
msgstr "So"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Monday"
msgstr "Montag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Tuesday"
msgstr "Dienstag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Wednesday"
msgstr "Mittwoch"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Thursday"
msgstr "Donnerstag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Friday"
msgstr "Freitag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Saturday"
msgstr "Samstag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "Sunday"
msgstr "Sonntag"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "January"
msgstr "Januar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "February"
msgstr "Februar"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "March"
msgstr "März"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "April"
msgstr "April"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "May"
msgstr "Mai"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "June"
msgstr "Juni"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "July"
msgstr "Juli"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "August"
msgstr "August"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "September"
msgstr "September"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "October"
msgstr "Oktober"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "November"
msgstr "November"
#: pretix/static/pretixpresale/js/widget/widget.js
#: pretix/static/pretixpresale/widget/src/i18n.ts
msgid "December"
msgstr "Dezember"
@@ -159,6 +159,7 @@ Erstattungsstatus
Erstattungsweg
erstmalig
etc
EU-USt-ID
EU-USt-ID-Nr
Event
Event-Absage
+346 -274
View File
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2026-08-24 15:35+0000\n"
"POT-Creation-Date: 2026-09-30 07:26+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -197,7 +197,7 @@ msgid "Allowed Post Logout URIs list, space separated"
msgstr ""
#: pretix/api/models.py pretix/base/models/customers.py
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/payment.py
msgid "Client ID"
msgstr ""
@@ -1717,6 +1717,18 @@ msgstr ""
msgid "Payment providers"
msgstr ""
#: pretix/base/exporters/invoices.py pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission status"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Transmission date"
msgstr ""
#: pretix/base/exporters/invoices.py
msgid "Cancellation"
msgstr ""
@@ -2360,7 +2372,6 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/organizers/giftcard.html
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_form.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
@@ -2384,7 +2395,6 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_cart.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Quantity"
msgstr ""
@@ -2466,7 +2476,6 @@ msgstr ""
#: pretix/base/exporters/orderlist.py
#: pretix/control/templates/pretixcontrol/search/payments.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payment ID"
msgstr ""
@@ -4224,6 +4233,10 @@ msgstr ""
msgid "Initialization date"
msgstr ""
#: pretix/base/models/devices.py
msgid "Security profile"
msgstr ""
#: pretix/base/models/discount.py
msgctxt "subevent"
msgid "Dates can be mixed without limitation"
@@ -5439,6 +5452,10 @@ msgstr ""
msgid "Maximum value"
msgstr ""
#: pretix/base/models/items.py
msgid "Minimum length"
msgstr ""
#: pretix/base/models/items.py
msgid "Maximum length"
msgstr ""
@@ -5505,6 +5522,10 @@ msgstr ""
msgid "The maximum value must not be lower than the minimum value."
msgstr ""
#: pretix/base/models/items.py
msgid "The maximum length must not be shorter than the minimum length."
msgstr ""
#: pretix/base/models/items.py
msgid ""
"The system already contains answers to this question that are not compatible "
@@ -5998,10 +6019,6 @@ msgstr ""
msgid "This reference will be printed on your invoice for your convenience."
msgstr ""
#: pretix/base/models/orders.py
msgid "Transmission type"
msgstr ""
#: pretix/base/models/orders.py
#: pretix/plugins/badges/templates/pretixplugins/badges/control_order_position_buttons.html
msgid "Badge"
@@ -9475,6 +9492,17 @@ msgid ""
"'Last date of payments' configured above."
msgstr ""
#: pretix/base/settings.py
msgid "Allow postponed payment choice for sales channels"
msgstr ""
#: pretix/base/settings.py
msgid ""
"If postponed payment is allowed on a sales channel, customers can complete "
"their order without selecting a payment method. This is useful whenever "
"orders are not created by the same person who is making the payment."
msgstr ""
#: pretix/base/settings.py
msgid "Show start date"
msgstr ""
@@ -9996,12 +10024,6 @@ msgstr ""
msgid "Hide all unavailable dates from calendar or list views"
msgstr ""
#: pretix/base/settings.py
msgid ""
"This option currently only affects the calendar of this event series, not "
"the organizer-wide calendar."
msgstr ""
#: pretix/base/settings.py
msgid "Hide all past dates from calendar"
msgstr ""
@@ -14690,6 +14712,11 @@ msgctxt "rrule"
msgid "third"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "fourth"
msgstr ""
#: pretix/control/forms/rrule.py
msgctxt "rrule"
msgid "last"
@@ -15673,6 +15700,22 @@ msgstr ""
msgid "Queued emails have been aborted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been created."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been deleted."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been changed."
msgstr ""
#: pretix/control/logdisplay.py
msgid "An organizer meta property has been reordered."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Gift card acceptance for another organizer has been added."
msgstr ""
@@ -15875,6 +15918,10 @@ msgstr ""
msgid "A two-factor emergency code has been generated."
msgstr ""
#: pretix/control/logdisplay.py
msgid "Drift and throttle values for two-factor devices have been reset."
msgstr ""
#: pretix/control/logdisplay.py
#, python-brace-format
msgid ""
@@ -16707,6 +16754,87 @@ msgid ""
"Granting access to your pretix account happens at your own risk."
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Authorize"
msgstr ""
#: pretix/control/templates/pretixcontrol/auth/oauth_authorization.html
msgid "Error:"
msgstr ""
@@ -17068,82 +17196,6 @@ msgid_plural ""
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/checkin/reset.html
#: pretix/control/templates/pretixcontrol/datasync/control_order_info.html
#: pretix/control/templates/pretixcontrol/email_setup_simple.html
#: pretix/control/templates/pretixcontrol/event/tax_delete.html
#: pretix/control/templates/pretixcontrol/item/delete.html
#: pretix/control/templates/pretixcontrol/items/category_delete.html
#: pretix/control/templates/pretixcontrol/items/discount_delete.html
#: pretix/control/templates/pretixcontrol/items/question_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete.html
#: pretix/control/templates/pretixcontrol/items/quota_delete_bulk.html
#: pretix/control/templates/pretixcontrol/oauth/app_delete.html
#: pretix/control/templates/pretixcontrol/oauth/app_rollkeys.html
#: pretix/control/templates/pretixcontrol/oauth/auth_revoke.html
#: pretix/control/templates/pretixcontrol/order/change.html
#: pretix/control/templates/pretixcontrol/order/change_contact.html
#: pretix/control/templates/pretixcontrol/order/change_locale.html
#: pretix/control/templates/pretixcontrol/order/change_questions.html
#: pretix/control/templates/pretixcontrol/order/extend.html
#: pretix/control/templates/pretixcontrol/order/pay.html
#: pretix/control/templates/pretixcontrol/order/pay_complete.html
#: pretix/control/templates/pretixcontrol/order/reactivate.html
#: pretix/control/templates/pretixcontrol/order/refund_choose.html
#: pretix/control/templates/pretixcontrol/order/refund_done.html
#: pretix/control/templates/pretixcontrol/order/refund_process.html
#: pretix/control/templates/pretixcontrol/order/refund_start.html
#: pretix/control/templates/pretixcontrol/orders/bulk_action.html
#: pretix/control/templates/pretixcontrol/orders/export_delete.html
#: pretix/control/templates/pretixcontrol/orders/refunds.html
#: pretix/control/templates/pretixcontrol/organizers/channel_delete.html
#: pretix/control/templates/pretixcontrol/organizers/customer_anonymize.html
#: pretix/control/templates/pretixcontrol/organizers/customer_membership_delete.html
#: pretix/control/templates/pretixcontrol/organizers/device_revoke.html
#: pretix/control/templates/pretixcontrol/organizers/export_delete.html
#: pretix/control/templates/pretixcontrol/organizers/gate_delete.html
#: pretix/control/templates/pretixcontrol/organizers/membershiptype_delete.html
#: pretix/control/templates/pretixcontrol/organizers/property_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoclient_delete.html
#: pretix/control/templates/pretixcontrol/organizers/ssoprovider_delete.html
#: pretix/control/templates/pretixcontrol/organizers/team_delete.html
#: pretix/control/templates/pretixcontrol/pdf/index.html
#: pretix/control/templates/pretixcontrol/subevents/bulk_edit.html
#: pretix/control/templates/pretixcontrol/subevents/delete.html
#: pretix/control/templates/pretixcontrol/subevents/delete_bulk.html
#: pretix/control/templates/pretixcontrol/subevents/edit.html
#: pretix/control/templates/pretixcontrol/user/2fa_delete.html
#: pretix/control/templates/pretixcontrol/user/2fa_disable.html
#: pretix/control/templates/pretixcontrol/user/2fa_enable.html
#: pretix/control/templates/pretixcontrol/user/2fa_leaveteams.html
#: pretix/control/templates/pretixcontrol/user/2fa_regenemergency.html
#: pretix/control/templates/pretixcontrol/user/change_email.html
#: pretix/control/templates/pretixcontrol/user/change_password.html
#: pretix/control/templates/pretixcontrol/user/confirmation_code_dialog.html
#: pretix/control/templates/pretixcontrol/vouchers/delete.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_bulk.html
#: pretix/control/templates/pretixcontrol/vouchers/delete_carts.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete.html
#: pretix/control/templates/pretixcontrol/waitinglist/delete_bulk.html
#: pretix/control/templates/pretixcontrol/waitinglist/edit.html
#: pretix/plugins/autocheckin/templates/pretixplugins/autocheckin/delete.html
#: pretix/plugins/badges/templates/pretixplugins/badges/delete.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/sendmail/templates/pretixplugins/sendmail/rule_delete.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/ticketoutputpdf/templates/pretixplugins/ticketoutputpdf/delete.html
#: pretix/presale/templates/pretixpresale/event/order_change.html
#: pretix/presale/templates/pretixpresale/event/order_modify.html
#: pretix/presale/templates/pretixpresale/event/order_pay.html
#: pretix/presale/templates/pretixpresale/event/order_pay_change.html
#: pretix/presale/templates/pretixpresale/event/order_pay_confirm.html
#: pretix/presale/templates/pretixpresale/event/position_change.html
#: pretix/presale/templates/pretixpresale/event/position_modify.html
msgid "Cancel"
msgstr ""
#: pretix/control/templates/pretixcontrol/checkin/bulk_revert_confirm.html
#: pretix/control/templates/pretixcontrol/checkin/list_delete.html
#: pretix/control/templates/pretixcontrol/event/delete.html
@@ -19255,7 +19307,7 @@ msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
msgid ""
"We strongly recommend against using short forms of more then 16 characters."
"We strongly recommend against using short forms of more than 16 characters."
msgstr ""
#: pretix/control/templates/pretixcontrol/events/create_basics.html
@@ -24195,6 +24247,7 @@ msgid "Add a new device"
msgstr ""
#: pretix/control/templates/pretixcontrol/user/2fa_main.html
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Emergency tokens"
msgstr ""
@@ -24439,6 +24492,26 @@ msgstr ""
msgid "Authentication backend"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Reset drift and throttle"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Available two-factor authentication methods"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "1 failed attempt since %(date)s"
msgid_plural "%(cnt)s failed attempts since %(date)s"
msgstr[0] ""
msgstr[1] ""
#: pretix/control/templates/pretixcontrol/users/form.html
#, python-format
msgid "Currently locked until %(date)s"
msgstr ""
#: pretix/control/templates/pretixcontrol/users/form.html
msgid "Team memberships"
msgstr ""
@@ -24892,6 +24965,20 @@ msgstr ""
msgid "Invalid code, please try again."
msgstr ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} minute."
msgid_plural "Invalid code. Please try again after waiting {value} minutes."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/auth.py
#, python-brace-format
msgid "Invalid code. Please try again after waiting {value} second."
msgid_plural "Invalid code. Please try again after waiting {value} seconds."
msgstr[0] ""
msgstr[1] ""
#: pretix/control/views/checkin.py
msgid "The selected check-ins have been reverted."
msgstr ""
@@ -25644,6 +25731,10 @@ msgstr ""
msgid "You entered an order in an event with a different currency."
msgstr ""
#: pretix/control/views/orders.py
msgid "You entered an order in an event that you do not have access to."
msgstr ""
#: pretix/control/views/orders.py
msgid ""
"You can not refund more than the amount of a payment that is not yet "
@@ -25656,6 +25747,10 @@ msgid ""
"refunds."
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
#, python-brace-format
msgid ""
@@ -25697,10 +25792,6 @@ msgid ""
"Your {event} team"
msgstr ""
#: pretix/control/views/orders.py
msgid "The refunds you selected do not match the selected total refund amount."
msgstr ""
#: pretix/control/views/orders.py
msgid "The payment has been created successfully."
msgstr ""
@@ -26412,6 +26503,10 @@ msgid ""
"remain active."
msgstr ""
#: pretix/control/views/users.py
msgid "The drift values for TOTP devices have been reset."
msgstr ""
#: pretix/control/views/users.py
msgid "The new user has been created."
msgstr ""
@@ -26424,6 +26519,14 @@ msgstr ""
msgid "Bypass quota"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "Budget used"
msgstr ""
#: pretix/control/views/vouchers.py
msgid "The requested voucher does not exist."
msgstr ""
@@ -26576,12 +26679,11 @@ msgstr ""
#: pretix/plugins/autocheckin/apps.py pretix/plugins/badges/apps.py
#: pretix/plugins/banktransfer/apps.py pretix/plugins/checkinlists/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal/apps.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/pretixdroid/apps.py
#: pretix/plugins/reports/apps.py pretix/plugins/returnurl/apps.py
#: pretix/plugins/sendmail/apps.py pretix/plugins/statistics/apps.py
#: pretix/plugins/stripe/apps.py pretix/plugins/ticketoutputpdf/apps.py
#: pretix/plugins/webcheckin/apps.py
#: pretix/plugins/manualpayment/apps.py pretix/plugins/paypal2/apps.py
#: pretix/plugins/pretixdroid/apps.py pretix/plugins/reports/apps.py
#: pretix/plugins/returnurl/apps.py pretix/plugins/sendmail/apps.py
#: pretix/plugins/statistics/apps.py pretix/plugins/stripe/apps.py
#: pretix/plugins/ticketoutputpdf/apps.py pretix/plugins/webcheckin/apps.py
msgid "the pretix team"
msgstr ""
@@ -27132,7 +27234,6 @@ msgstr ""
#: pretix/plugins/banktransfer/refund_export.py
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/control.html
#: pretix/plugins/banktransfer/templates/pretixplugins/banktransfer/import_assign.html
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Payer"
@@ -27626,8 +27727,7 @@ msgstr ""
msgid "Automatically checked in"
msgstr ""
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/checkinlists/exporters.py pretix/plugins/paypal2/payment.py
msgid "Secret"
msgstr ""
@@ -27686,152 +27786,6 @@ msgstr ""
msgid "A fully customizable payment method for manual processing."
msgstr ""
#: pretix/plugins/paypal/apps.py pretix/plugins/paypal/payment.py
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal/apps.py
msgid ""
"Accept payments with your PayPal account. PayPal is one of the most popular "
"payment methods world-wide."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal/payment.py
msgid "PayPal account"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal/payment.py pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_confirm.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/checkout_payment_form.html
msgid ""
"After you clicked continue, we will redirect you to PayPal to fill in your "
"payment details. You will then be redirected back here to review and confirm "
"your order."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
msgid ""
"Our attempt to execute your Payment via PayPal has failed. Please try again "
"or contact us."
msgstr ""
#: pretix/plugins/paypal/templates/pretixplugins/paypal/pending.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal/views.py pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/paypal2/apps.py
msgid ""
"Accept payments with your PayPal account. In addition to regular PayPal "
@@ -27841,10 +27795,23 @@ msgid ""
"methods world-wide."
msgstr ""
#: pretix/plugins/paypal2/apps.py pretix/plugins/paypal2/payment.py
#: pretix/plugins/stripe/payment.py
msgid "PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal Merchant ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Click here for a tutorial on how to obtain the required keys"
msgstr ""
#: pretix/plugins/paypal2/payment.py pretix/plugins/stripe/payment.py
msgid "Endpoint"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Even if a customer chooses an Alternative Payment Method, they will always "
@@ -27913,6 +27880,26 @@ msgid ""
"while the last payment is still under investigation."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference prefix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added in front of the regular booking "
"reference containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Reference postfix"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Any value entered here will be added behind the regular booking reference "
"containing the order number."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "-- Automatic --"
msgstr ""
@@ -27933,6 +27920,10 @@ msgstr ""
msgid "Connect with {icon} PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "Disconnect from PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Please configure a PayPal Webhook to the following endpoint in order to "
@@ -27961,6 +27952,12 @@ msgstr ""
msgid "An error occurred during connecting with PayPal, please try again."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"The PayPal sandbox is being used, you can test without actually sending "
"money but you will need a PayPal sandbox user to log in."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
@@ -27969,6 +27966,10 @@ msgid ""
"attempt. You can also try other payment methods, if available."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "We had trouble communicating with PayPal"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Something went wrong when requesting the payment status. Please try again."
@@ -27978,12 +27979,41 @@ msgstr ""
msgid "You may need to enable JavaScript for PayPal payments."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"We were unable to process your payment. See below for details on how to "
"proceed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"PayPal has not yet approved the payment. We will inform you as soon as the "
"payment completed."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid ""
"Refunding the amount via PayPal failed: The original payment does not "
"contain the required information to issue an automated refund."
msgstr ""
#: pretix/plugins/paypal2/payment.py
#, python-brace-format
msgid "Refunding the amount via PayPal failed: {}"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "The payment for this invoice has already been received."
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal payment ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal sale ID"
msgstr ""
#: pretix/plugins/paypal2/payment.py
msgid "PayPal APM"
msgstr ""
@@ -28071,6 +28101,12 @@ msgstr ""
msgid "We will then charge your PayPal account and finalize the order."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"The total amount listed above will be withdrawn from your PayPal account "
"after the confirmation of your purchase."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/checkout_payment_confirm.html
msgid ""
"After placing your order, you will be able to select your desired payment "
@@ -28102,6 +28138,11 @@ msgid ""
"different payment method, if you prefer."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Sale ID"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
msgid "Capture status"
msgstr ""
@@ -28112,6 +28153,17 @@ msgid ""
"money will not be disbursed and the order remain in its pending state."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
msgid "Last update"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control.html
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/control_legacy.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/control.html
msgid "Total value"
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pay.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca.html
#: pretix/plugins/stripe/templates/pretixplugins/stripe/sca_return.html
@@ -28145,6 +28197,12 @@ msgid ""
"to resolve this case."
msgstr ""
#: pretix/plugins/paypal2/templates/pretixplugins/paypal2/pending.html
msgid ""
"We're waiting for an answer from PayPal regarding your payment. Please "
"contact us, if this takes more than a few hours."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid ""
"An error occurred returning from PayPal: request parameters missing. Please "
@@ -28175,6 +28233,18 @@ msgid ""
"in detail below."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Invalid response from PayPal received."
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "It looks like you canceled the PayPal payment"
msgstr ""
#: pretix/plugins/paypal2/views.py
msgid "Your PayPal account has been disconnected."
msgstr ""
#: pretix/plugins/pretixdroid/apps.py
msgid "Old check-in device API"
msgstr ""
@@ -30194,7 +30264,6 @@ msgstr ""
#: pretix/presale/forms/order.py
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "plus taxes"
msgstr ""
@@ -30615,6 +30684,31 @@ msgid ""
"Please go to the payment settings and activate one or more payment providers."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"Not sure yet? You can complete your order first and then select a payment "
"method later."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid ""
"To do so, please first remove the payment methods you already selected above."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed within %(minutes)s minutes."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
#, python-format
msgid "Your payment needs to be completed by %(deadline)s."
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_payment.html
msgid "Proceed without selection"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/checkout_questions.html
msgid "Before we continue, we need you to answer some questions."
msgstr ""
@@ -30681,14 +30775,12 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "minimum amount to order: %(num)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "price"
msgid "free"
msgstr ""
@@ -30717,66 +30809,56 @@ msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Original price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "New price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s, at least %(price)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Modify price for %(item)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "<strong>plus</strong> %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "incl. %(rate)s%% %(name)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgctxt "checkbox"
msgid "Select"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Decrease quantity"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_addon_choice.html
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Increase quantity"
msgstr ""
@@ -31237,12 +31319,10 @@ msgid "Your order qualifies for a discount"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
msgid "Uncategorized items"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Show full-size image of %(item)s"
msgstr ""
@@ -31255,19 +31335,16 @@ msgstr[0] ""
msgstr[1] ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s incl. taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "%(value)s without taxes"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/fragment_product_list.html
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "Set price in %(currency)s for %(item)s"
msgstr ""
@@ -31926,11 +32003,6 @@ msgid ""
"products at the specified price:"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "from %(minprice)s"
msgstr ""
#: pretix/presale/templates/pretixpresale/event/voucher.html
#, python-format
msgid "You need to select at least %(number)s products."

Some files were not shown because too many files have changed in this diff Show More