mirror of
https://github.com/pretix/pretix.git
synced 2026-05-06 15:24:02 +00:00
Fix invalid handling of variations with quota-level vouchers
This commit is contained in:
@@ -344,6 +344,8 @@ class Voucher(LoggedModel):
|
|||||||
a variation).
|
a variation).
|
||||||
"""
|
"""
|
||||||
if self.quota_id:
|
if self.quota_id:
|
||||||
|
if variation:
|
||||||
|
return variation.quotas.filter(pk=self.quota_id).exists()
|
||||||
return item.quotas.filter(pk=self.quota_id).exists()
|
return item.quotas.filter(pk=self.quota_id).exists()
|
||||||
if self.item_id and not self.variation_id:
|
if self.item_id and not self.variation_id:
|
||||||
return self.item_id == item.pk
|
return self.item_id == item.pk
|
||||||
|
|||||||
@@ -94,6 +94,11 @@ def get_grouped_items(event, subevent=None, voucher=None, channel='web'):
|
|||||||
item_price_override = {}
|
item_price_override = {}
|
||||||
var_price_override = {}
|
var_price_override = {}
|
||||||
|
|
||||||
|
restrict_vars = set()
|
||||||
|
if voucher and voucher.quota_id:
|
||||||
|
# If a voucher is set to a specific quota, we need to filter out on that level
|
||||||
|
restrict_vars = set(voucher.quota.variations.all())
|
||||||
|
|
||||||
for item in items:
|
for item in items:
|
||||||
if voucher and voucher.item_id and voucher.variation_id:
|
if voucher and voucher.item_id and voucher.variation_id:
|
||||||
# Restrict variations if the voucher only allows one
|
# Restrict variations if the voucher only allows one
|
||||||
@@ -163,8 +168,11 @@ def get_grouped_items(event, subevent=None, voucher=None, channel='web'):
|
|||||||
display_add_to_cart = display_add_to_cart or var.order_max > 0
|
display_add_to_cart = display_add_to_cart or var.order_max > 0
|
||||||
|
|
||||||
item.available_variations = [
|
item.available_variations = [
|
||||||
v for v in item.available_variations if v._subevent_quotas
|
v for v in item.available_variations if v._subevent_quotas and (
|
||||||
|
not voucher or not voucher.quota_id or v in restrict_vars
|
||||||
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
if voucher and voucher.variation_id:
|
if voucher and voucher.variation_id:
|
||||||
item.available_variations = [v for v in item.available_variations
|
item.available_variations = [v for v in item.available_variations
|
||||||
if v.pk == voucher.variation_id]
|
if v.pk == voucher.variation_id]
|
||||||
|
|||||||
@@ -650,6 +650,15 @@ class VoucherTestCase(BaseQuotaTestCase):
|
|||||||
self.assertTrue(v.applies_to(self.var1.item, self.var1))
|
self.assertTrue(v.applies_to(self.var1.item, self.var1))
|
||||||
self.assertFalse(v.applies_to(self.var1.item, self.var2))
|
self.assertFalse(v.applies_to(self.var1.item, self.var2))
|
||||||
|
|
||||||
|
def test_voucher_applicability_variation_through_quota(self):
|
||||||
|
self.quota.variations.add(self.var1)
|
||||||
|
self.quota.items.add(self.var1.item)
|
||||||
|
v = Voucher.objects.create(quota=self.quota, event=self.event)
|
||||||
|
self.assertFalse(v.applies_to(self.item1))
|
||||||
|
self.assertTrue(v.applies_to(self.var1.item)) # semantics unclear
|
||||||
|
self.assertTrue(v.applies_to(self.var1.item, self.var1))
|
||||||
|
self.assertFalse(v.applies_to(self.var1.item, self.var2))
|
||||||
|
|
||||||
def test_voucher_no_item_with_quota(self):
|
def test_voucher_no_item_with_quota(self):
|
||||||
with self.assertRaises(ValidationError):
|
with self.assertRaises(ValidationError):
|
||||||
v = Voucher(quota=self.quota, item=self.item1, event=self.event)
|
v = Voucher(quota=self.quota, item=self.item1, event=self.event)
|
||||||
|
|||||||
@@ -242,6 +242,67 @@ class WidgetCartTest(CartTestMixin, TestCase):
|
|||||||
"cart_exists": False
|
"cart_exists": False
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def test_product_list_view_with_voucher_variation_through_quota(self):
|
||||||
|
self.event.vouchers.create(quota=self.quota_shirts, code="ABCDE")
|
||||||
|
self.quota_shirts.variations.remove(self.shirt_blue)
|
||||||
|
response = self.client.get('/%s/%s/widget/product_list?voucher=ABCDE' % (self.orga.slug, self.event.slug))
|
||||||
|
assert response['Access-Control-Allow-Origin'] == '*'
|
||||||
|
data = json.loads(response.content.decode())
|
||||||
|
assert data == {
|
||||||
|
"name": "30C3",
|
||||||
|
"currency": "EUR",
|
||||||
|
"show_variations_expanded": False,
|
||||||
|
"display_net_prices": False,
|
||||||
|
"vouchers_exist": True,
|
||||||
|
"waiting_list_enabled": False,
|
||||||
|
"error": None,
|
||||||
|
"items_by_category": [
|
||||||
|
{
|
||||||
|
"items": [
|
||||||
|
{
|
||||||
|
'id': self.shirt.pk,
|
||||||
|
'name': 'T-Shirt',
|
||||||
|
'picture': None,
|
||||||
|
'description': None,
|
||||||
|
'has_variations': 2,
|
||||||
|
'require_voucher': False,
|
||||||
|
'order_min': None,
|
||||||
|
'order_max': None,
|
||||||
|
'price': None,
|
||||||
|
'min_price': '14.00',
|
||||||
|
'max_price': '14.00',
|
||||||
|
'free_price': False,
|
||||||
|
'avail': None,
|
||||||
|
'original_price': None,
|
||||||
|
'variations': [
|
||||||
|
{
|
||||||
|
'id': self.shirt_red.pk,
|
||||||
|
'value': 'Red',
|
||||||
|
'order_max': 2,
|
||||||
|
'description': None,
|
||||||
|
'price': {
|
||||||
|
'gross': '14.00',
|
||||||
|
'net': '11.76',
|
||||||
|
'tax': '2.24',
|
||||||
|
'rate': '19.00',
|
||||||
|
'name': '',
|
||||||
|
'includes_mixed_tax_rate': False
|
||||||
|
},
|
||||||
|
'avail': [100, None]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": None,
|
||||||
|
"id": self.category.pk,
|
||||||
|
"name": "Everything"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"itemnum": 1,
|
||||||
|
"display_add_to_cart": True,
|
||||||
|
"cart_exists": False
|
||||||
|
}
|
||||||
|
|
||||||
def test_product_list_view_with_voucher_expired(self):
|
def test_product_list_view_with_voucher_expired(self):
|
||||||
self.event.vouchers.create(item=self.ticket, code="ABCDE", valid_until=now() - datetime.timedelta(days=1))
|
self.event.vouchers.create(item=self.ticket, code="ABCDE", valid_until=now() - datetime.timedelta(days=1))
|
||||||
response = self.client.get('/%s/%s/widget/product_list?voucher=ABCDE' % (self.orga.slug, self.event.slug))
|
response = self.client.get('/%s/%s/widget/product_list?voucher=ABCDE' % (self.orga.slug, self.event.slug))
|
||||||
|
|||||||
Reference in New Issue
Block a user