last commit
This commit is contained in:
parent
491670200c
commit
e30005021d
7 changed files with 106 additions and 50 deletions
|
|
@ -2,11 +2,11 @@ from functools import update_wrapper
|
|||
|
||||
from django.contrib import admin
|
||||
|
||||
from .models import Promotion, Plan, Event, Recipient
|
||||
|
||||
from .models import Promotion, Plan, Event, Recipient, EventSaver
|
||||
|
||||
admin.site.register(Plan)
|
||||
admin.site.register(Promotion)
|
||||
admin.site.register(Event)
|
||||
admin.site.register(EventSaver)
|
||||
admin.site.register(Recipient)
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,32 @@
|
|||
# Generated by Django 5.1.7 on 2025-10-14 16:49
|
||||
|
||||
import uuid
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('promotions', '0010_remove_plan_max_amount_remove_plan_min_amount_and_more'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.CreateModel(
|
||||
name='EventSaver',
|
||||
fields=[
|
||||
('uuid', models.UUIDField(db_index=True, default=uuid.uuid4, editable=False, primary_key=True, serialize=False, unique=True)),
|
||||
('created_at', models.DateTimeField(auto_now_add=True, db_index=True)),
|
||||
('updated_at', models.DateTimeField(auto_now=True, db_index=True)),
|
||||
('title', models.CharField(max_length=255, verbose_name='title')),
|
||||
('event_label', models.CharField(db_index=True, max_length=255, unique=True, verbose_name='label')),
|
||||
('save_once', models.BooleanField(default=False, verbose_name='save once')),
|
||||
],
|
||||
options={
|
||||
'abstract': False,
|
||||
},
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name='recipient',
|
||||
name='wallet_uuid',
|
||||
),
|
||||
]
|
||||
|
|
@ -5,14 +5,47 @@ from django.utils import timezone
|
|||
|
||||
from oauth2_provider.settings import oauth2_settings
|
||||
|
||||
|
||||
from apps.promotions import handlers
|
||||
|
||||
from apps.promotions.handlers import PromotionTypeChoices, BasePromotionHandler
|
||||
|
||||
|
||||
from apps.users.models import User
|
||||
from utils.models import BaseModel
|
||||
|
||||
from django.utils.translation import gettext_lazy as _
|
||||
|
||||
|
||||
class EventSaverQuerySet(models.QuerySet):
|
||||
pass
|
||||
|
||||
|
||||
class EventSaver(BaseModel):
|
||||
title = models.CharField(_('title'), max_length=255)
|
||||
event_label = models.CharField(_('label'), max_length=255, unique=True, db_index=True)
|
||||
save_once = models.BooleanField(_('save once'), default=False)
|
||||
|
||||
objects = EventSaverQuerySet.as_manager()
|
||||
|
||||
def save_event(self, **kwargs):
|
||||
user = kwargs.get('user')
|
||||
application = kwargs.get('application')
|
||||
label = kwargs.get('label')
|
||||
data = kwargs.get('data')
|
||||
|
||||
if self.save_once:
|
||||
event, created = Event.objects.get_or_create(user=user, application=application, label=label, defaults={"data": data})
|
||||
if created:
|
||||
return event
|
||||
else:
|
||||
raise Exception(_('already saved'))
|
||||
|
||||
else:
|
||||
event = Event.objects.create(user=user, application=application, label=label, defaults={"date": date})
|
||||
return event
|
||||
|
||||
|
||||
class EventQuerySet(models.QuerySet):
|
||||
pass
|
||||
|
||||
|
|
@ -63,20 +96,6 @@ class Plan(BaseModel):
|
|||
def __str__(self):
|
||||
return self.title
|
||||
|
||||
# @property
|
||||
# def handler(self):
|
||||
# if self.promotion_type == PromotionTypeChoices.PERCENTAGE.name:
|
||||
# return handlers.PercentageHandler(self)
|
||||
#
|
||||
# elif self.promotion_type == PromotionTypeChoices.REFERRAL.name:
|
||||
# return handlers.ReferralHandler(self)
|
||||
#
|
||||
# elif self.promotion_type == PromotionTypeChoices.OTHERS.name:
|
||||
# return handlers.OtherHandler(self)
|
||||
#
|
||||
# else:
|
||||
# raise NotImplementedError()
|
||||
|
||||
def process_event(self, event=None):
|
||||
self.promote(event=event)
|
||||
|
||||
|
|
@ -155,7 +174,6 @@ class Recipient(BaseModel):
|
|||
raise
|
||||
|
||||
|
||||
|
||||
class PromotionQuerySet(models.QuerySet):
|
||||
def used(self, user):
|
||||
return self.filter(user=user, state__in=[Promotion.StateChoices.CREATED])
|
||||
|
|
|
|||
|
|
@ -30,13 +30,14 @@ class EventSerializer(serializers.ModelSerializer):
|
|||
)
|
||||
read_only_fields = ('user', 'application')
|
||||
|
||||
|
||||
class PlanSerializer(serializers.ModelSerializer):
|
||||
base_amount = serializers.IntegerField(required=True)
|
||||
promotion_amount = serializers.IntegerField(read_only=True)
|
||||
|
||||
class Meta:
|
||||
model = Plan
|
||||
fields = (
|
||||
fields = ("label"
|
||||
"title",
|
||||
"description",
|
||||
"base_amount",
|
||||
|
|
@ -58,4 +59,3 @@ class PlanPromotSerializer(serializers.ModelSerializer):
|
|||
"application",
|
||||
)
|
||||
read_only_fields = ('user', 'application')
|
||||
|
||||
|
|
|
|||
|
|
@ -1,11 +1,12 @@
|
|||
from drf_spectacular.utils import extend_schema
|
||||
from rest_framework import mixins
|
||||
from rest_framework.decorators import action
|
||||
from rest_framework import exceptions
|
||||
from rest_framework.viewsets import GenericViewSet
|
||||
|
||||
from apps.gooyal_oauth2.rest_framework import IsAuthenticatedOrTokenMatchesOASRequirements
|
||||
from apps.gooyal_oauth2.utils import get_application
|
||||
from .models import Plan, Promotion
|
||||
from .models import Plan, Promotion, EventSaver
|
||||
from .serializers import PlanSerializer, PromotionSerializer, EventSerializer
|
||||
from .tasks import analyze_event_task
|
||||
from ..users.models import User
|
||||
|
|
@ -74,14 +75,20 @@ class ApplicationEventViewSet(
|
|||
"POST": [["promotions.application.event:submit"]],
|
||||
}
|
||||
|
||||
def perform_create(self, serializer):
|
||||
def perform_create(self, serializer: EventSerializer):
|
||||
if hasattr(self.request, 'user'):
|
||||
user = self.request.user
|
||||
else:
|
||||
user = None
|
||||
|
||||
application = get_application(self.request)
|
||||
event = serializer.save(user=user, application=application)
|
||||
# EventSaver.objects.first(event_label=serializer.validated_data['event_label'], valid_application__contains=application.uuid)
|
||||
event_saver: EventSaver = EventSaver.objects.filter(event_label=serializer.validated_data['label']).first()
|
||||
try:
|
||||
event = event_saver.save_event(user=user, application=application, **serializer.validated_data)
|
||||
except Exception as e:
|
||||
raise exceptions.ValidationError(str(e))
|
||||
|
||||
analyze_event_task.delay(event.uuid)
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -188,7 +188,7 @@ REST_FRAMEWORK = {
|
|||
# 'otp_min': '1/min',
|
||||
# 'otp_day': '20/day',
|
||||
},
|
||||
'EXCEPTION_HANDLER': 'utils.exceptions.ExceptionHandler',
|
||||
'EXCEPTION_HANDLER': 'utils.exceptions.exception_handler',
|
||||
}
|
||||
|
||||
AUTHENTICATION_BACKENDS = (
|
||||
|
|
|
|||
|
|
@ -5,10 +5,8 @@ from rest_framework.views import exception_handler as drf_exception_handler
|
|||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
class ExceptionHandler:
|
||||
|
||||
@classmethod
|
||||
def __call__(cls, exc, context):
|
||||
def exception_handler(exc, context):
|
||||
# پاسخ پیشفرض DRF را دریافت میکنیم
|
||||
response = drf_exception_handler(exc, context)
|
||||
|
||||
|
|
@ -33,6 +31,7 @@ class ExceptionHandler:
|
|||
# در فایل middleware.py
|
||||
from django.http import JsonResponse
|
||||
|
||||
|
||||
class ErrorMiddleware:
|
||||
def __init__(self, get_response):
|
||||
self.get_response = get_response
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue