From 2d5cd622c5174ec307bbaf7f2de29ec04ab22bf7 Mon Sep 17 00:00:00 2001 From: Christopher Neugebauer Date: Sat, 26 Mar 2016 19:47:01 +1100 Subject: [PATCH] Makes it invalid for a user to re-enter a voucher code they already have. --- registrasion/controllers/cart.py | 11 +++++++++-- registrasion/tests/test_voucher.py | 23 +++++++++++++++++++++-- 2 files changed, 30 insertions(+), 4 deletions(-) diff --git a/registrasion/controllers/cart.py b/registrasion/controllers/cart.py index ad680225..06eef3ef 100644 --- a/registrasion/controllers/cart.py +++ b/registrasion/controllers/cart.py @@ -125,18 +125,25 @@ class CartController(object): def apply_voucher(self, voucher_code): ''' Applies the voucher with the given code to this cart. ''' - # TODO: is it valid for a cart to re-add a voucher that they have? - # Is voucher exhausted? active_carts = rego.Cart.reserved_carts() # Try and find the voucher voucher = rego.Voucher.objects.get(code=voucher_code.upper()) + # It's invalid for a user to enter a voucher that's exhausted carts_with_voucher = active_carts.filter(vouchers=voucher) if len(carts_with_voucher) >= voucher.limit: raise ValidationError("This voucher is no longer available") + # It's not valid for users to re-enter a voucher they already have + user_carts_with_voucher = rego.Cart.objects.filter( + user=self.cart.user, + vouchers=voucher, + ) + if len(user_carts_with_voucher) > 0: + raise ValidationError("You have already entered this voucher.") + # If successful... self.cart.vouchers.add(voucher) self.end_batch() diff --git a/registrasion/tests/test_voucher.py b/registrasion/tests/test_voucher.py index f0d1be61..db59d094 100644 --- a/registrasion/tests/test_voucher.py +++ b/registrasion/tests/test_voucher.py @@ -7,6 +7,7 @@ from django.db import IntegrityError from registrasion import models as rego from registrasion.controllers.cart import CartController +from registrasion.controllers.invoice import InvoiceController from test_cart import RegistrationCartTestCase @@ -16,11 +17,11 @@ UTC = pytz.timezone('UTC') class VoucherTestCases(RegistrationCartTestCase): @classmethod - def new_voucher(self, code="VOUCHER"): + def new_voucher(self, code="VOUCHER", limit=1): voucher = rego.Voucher.objects.create( recipient="Voucher recipient", code=code, - limit=1 + limit=limit, ) voucher.save() return voucher @@ -107,3 +108,21 @@ class VoucherTestCases(RegistrationCartTestCase): voucher = self.new_voucher(code="VOUCHeR") current_cart = CartController.for_user(self.USER_1) current_cart.apply_voucher(voucher.code.lower()) + + def test_voucher_can_only_be_applied_once(self): + voucher = self.new_voucher(limit=2) + current_cart = CartController.for_user(self.USER_1) + current_cart.apply_voucher(voucher.code) + with self.assertRaises(ValidationError): + current_cart.apply_voucher(voucher.code) + + def test_voucher_can_only_be_applied_once_across_multiple_carts(self): + voucher = self.new_voucher(limit=2) + current_cart = CartController.for_user(self.USER_1) + current_cart.apply_voucher(voucher.code) + + inv = InvoiceController.for_cart(current_cart.cart) + inv.pay("Hello!", inv.invoice.value) + + with self.assertRaises(ValidationError): + current_cart.apply_voucher(voucher.code)