Skip to content

Commit

Permalink
Add discounts
Browse files Browse the repository at this point in the history
  • Loading branch information
KwikKill committed Nov 25, 2024
1 parent 3bd129c commit d1e2092
Show file tree
Hide file tree
Showing 4 changed files with 88 additions and 6 deletions.
14 changes: 13 additions & 1 deletion insalan/payment/admin.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
from django.http import HttpResponse
from django.utils.translation import gettext_lazy as _

from .models import Product, Transaction, Payment, TransactionStatus
from .models import Product, Transaction, Payment, TransactionStatus, Discount


class ProductAdmin(admin.ModelAdmin):
Expand Down Expand Up @@ -123,3 +123,15 @@ def has_delete_permission(self, _request, _obj=None):


admin.site.register(Transaction, TransactionAdmin)

class DiscountAdmin(admin.ModelAdmin):
"""
Admin handler for Discounts
"""

list_display = ("id", "discount", "user", "product", "used")
search_fields = ["id", "discount", "user", "product", "reason"]



admin.site.register(Discount, DiscountAdmin)
59 changes: 59 additions & 0 deletions insalan/payment/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,12 @@ def can_be_bought_now(self) -> bool:
"""Returns whether or not the product can be bought now"""
return self.available_from <= timezone.now() <= self.available_until

def __str__(self):
"""
Return the name of the product
"""
return str(self.name)


class Payment(models.Model):
"""
Expand Down Expand Up @@ -161,6 +167,11 @@ class Meta:
decimal_places=2,
verbose_name=_("Montant"),
)
discounts = models.ManyToManyField(
"Discount",
blank=True,
verbose_name=_("Réductions")
)

@staticmethod
def new(**data):
Expand Down Expand Up @@ -326,6 +337,10 @@ def validate_transaction(self):

self.payment_status = TransactionStatus.SUCCEEDED
self.last_modification_date = timezone.make_aware(datetime.now())
# For each discount, mark it as used
for discount in self.discounts.all():
discount.use()

self.save()
logger.info("Transaction %s succeeded", self.id)
self.run_success_hooks()
Expand Down Expand Up @@ -378,3 +393,47 @@ class Meta:
null=True,
)
count = models.IntegerField(default=1, editable=True, verbose_name=_("Quantité"))


class Discount(models.Model):
"""
A discount is a temporary reduction of the price of a product
A discount is tied to a user, a product and can be used only once
"""

class Meta:
"""Meta information"""

verbose_name = _("Réduction")
verbose_name_plural = _("Réductions")

id: int
user = models.ForeignKey(
User, null=True, on_delete=models.SET_NULL, verbose_name=_("Utilisateur")
)
product = models.ForeignKey(
Product, null=True, on_delete=models.SET_NULL, verbose_name=_("Produit")
)
discount = models.DecimalField(
null=False, max_digits=5, decimal_places=2, verbose_name=_("Réduction")
)
reason = models.CharField(max_length=200, verbose_name=_("Motif"))
creation_date = models.DateTimeField(
verbose_name=_("Date de création"),
editable=False,
default=timezone.now
)
used = models.BooleanField(default=False, verbose_name=_("Utilisé"))
used_date = models.DateTimeField(
verbose_name=_("Date d'utilisation"),
editable=False,
null=True,
blank=True
)

def use(self):
"""Use the discount"""
self.used = True
self.used_date = timezone.make_aware(datetime.now())
self.save()
15 changes: 13 additions & 2 deletions insalan/payment/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
import insalan.settings as app_settings
import insalan.payment.serializers as serializers

from .models import Transaction, TransactionStatus, Product, Payment
from .models import Transaction, TransactionStatus, Product, Payment, Discount
from .tokens import Token

logger = logging.getLogger(__name__)
Expand Down Expand Up @@ -424,10 +424,21 @@ def create(self, request):
{"err": _("Préconditions de paiement non remplies")},
status=status.HTTP_400_BAD_REQUEST,
)

amount = transaction_obj.amount

# If the user has a discount for some products, apply them
for product in transaction_obj.products.all():
discounts = Discount.objects.filter(user=payer, product=product)
if discounts.exists():
discount = discounts.first()
amount = transaction_obj.amount - discount.discount
# Add the discount to the transaction object
transaction_obj.discounts.add(discount)

# helloasso intent
helloasso_amount = int(
transaction_obj.amount * 100
amount * 100
) # helloasso reads prices in cents
intent_body = {
"totalAmount": helloasso_amount,
Expand Down
6 changes: 3 additions & 3 deletions insalan/tournament/models/tournament.py
Original file line number Diff line number Diff line change
Expand Up @@ -195,7 +195,7 @@ def save(self, *args, **kwargs):
if self.player_online_product is None:
prod = Product.objects.create(
price=self.player_price_online,
name=_(f"Place {self.name} Joueur en ligne"),
name=_(f"Place {self.name} Joueur en ligne - {self.event.name}"),
desc=_(f"Inscription au tournoi {self.name} joueur"),
category=ProductCategory.REGISTRATION_PLAYER,
associated_tournament=self,
Expand All @@ -212,7 +212,7 @@ def save(self, *args, **kwargs):
if self.manager_online_product is None:
prod = Product.objects.create(
price=self.manager_price_online,
name=_(f"Place {self.name} manager en ligne"),
name=_(f"Place {self.name} manager en ligne - {self.event.name}"),
desc=_(f"Inscription au tournoi {self.name} manager"),
category=ProductCategory.REGISTRATION_MANAGER,
associated_tournament=self,
Expand All @@ -229,7 +229,7 @@ def save(self, *args, **kwargs):
if self.substitute_online_product is None:
prod = Product.objects.create(
price=self.substitute_price_online,
name=_(f"Place {self.name} remplaçant en ligne"),
name=_(f"Place {self.name} remplaçant en ligne - {self.event.name}"),
desc=_(f"Inscription au tournoi {self.name} remplaçant"),
category=ProductCategory.REGISTRATION_SUBSTITUTE,
associated_tournament=self,
Expand Down

0 comments on commit d1e2092

Please sign in to comment.