diff --git a/car_inventory/asgi.py b/car_inventory/asgi.py index 78e43762..941b6cbf 100644 --- a/car_inventory/asgi.py +++ b/car_inventory/asgi.py @@ -46,3 +46,19 @@ application = ProtocolTypeRouter( ), } ) + + +try: + from django.conf import settings + from django.contrib.sites.models import Site + + if not settings.DEBUG: + site = Site.objects.get(id=settings.SITE_ID) + if site.domain != settings.PRODUCTION_DOMAIN: + site.domain = settings.PRODUCTION_DOMAIN + site.name = settings.SITE_NAME + site.save() +except Exception as e: + # Log error but don't crash the app + if settings.DEBUG: + print(f"Site configuration error in WSGI: {e}") \ No newline at end of file diff --git a/inventory/management/commands/tenhal_plan.py b/inventory/management/commands/tenhal_plan.py index baa95ab7..e91d0b95 100644 --- a/inventory/management/commands/tenhal_plan.py +++ b/inventory/management/commands/tenhal_plan.py @@ -43,14 +43,14 @@ class Command(BaseCommand): ) # Assign quotas to plans - PlanQuota.objects.create(plan=basic_plan, quota=users_quota, value=99999) - PlanQuota.objects.create(plan=basic_plan, quota=cars_quota, value=99999) + PlanQuota.objects.create(plan=basic_plan, quota=users_quota, value=10000000) + PlanQuota.objects.create(plan=basic_plan, quota=cars_quota, value=10000000) - PlanQuota.objects.create(plan=pro_plan, quota=users_quota, value=99999) - PlanQuota.objects.create(plan=pro_plan, quota=cars_quota, value=99999) + PlanQuota.objects.create(plan=pro_plan, quota=users_quota, value=10000000) + PlanQuota.objects.create(plan=pro_plan, quota=cars_quota, value=10000000) - PlanQuota.objects.create(plan=enterprise_plan, quota=users_quota, value=99999) - PlanQuota.objects.create(plan=enterprise_plan, quota=cars_quota, value=99999) + PlanQuota.objects.create(plan=enterprise_plan, quota=users_quota, value=10000000) + PlanQuota.objects.create(plan=enterprise_plan, quota=cars_quota, value=10000000) # PlanQuota.objects.create(plan=pro_plan, quota=project_quota, value=50) # PlanQuota.objects.create(plan=pro_plan, quota=storage_quota, value=100) @@ -61,13 +61,13 @@ class Command(BaseCommand): enterprise_pricing = Pricing.objects.create(name="1 Year", period=365) PlanPricing.objects.create( - plan=basic_plan, pricing=basic_pricing, price=Decimal("2500.00") + plan=basic_plan, pricing=basic_pricing, price=Decimal("2997.00") ) PlanPricing.objects.create( - plan=pro_plan, pricing=pro_pricing, price=Decimal("4500.00") + plan=pro_plan, pricing=pro_pricing, price=Decimal("5395.00") ) PlanPricing.objects.create( - plan=enterprise_plan, pricing=enterprise_pricing, price=Decimal("8500.00") + plan=enterprise_plan, pricing=enterprise_pricing, price=Decimal("9590.00") ) # # Create quotas diff --git a/inventory/signals.py b/inventory/signals.py index 99b70213..0420e045 100644 --- a/inventory/signals.py +++ b/inventory/signals.py @@ -1001,15 +1001,25 @@ def car_created_notification(sender, instance, created, **kwargs): if created: accountants = ( models.CustomGroup.objects.filter( - dealer=instance.dealer, name__in=["Manager", "Accountant"] + dealer=instance.dealer, name__in=["Accountant"] ) .first() .group.user_set.all() .distinct() ) - for accountant in accountants: + managers = ( + models.CustomGroup.objects.filter( + dealer=instance.dealer, name__in=["Manager"] + ) + .first() + .group.user_set.all() + .distinct() + ) + + recipients = accountants.union(managers) + for recipient in recipients: models.Notification.objects.create( - user=accountant, + user=recipient, message=_( """ New Car {car_make}-{car_model}-{year}-{vin} has been added to the inventory. diff --git a/inventory/utils.py b/inventory/utils.py index 58db19d6..e1e0145e 100644 --- a/inventory/utils.py +++ b/inventory/utils.py @@ -1924,12 +1924,15 @@ def handle_payment(request, order): "last_name": last_name, "phone": phone, } - total = int(round(order.total())) * 100 + try: + total = int((order.total() + order.tax * order.total() / 100) * 100) + except (AttributeError, TypeError): + raise ValueError("Order total or tax is invalid") payload = json.dumps( { "amount": total, "currency": "SAR", - "description": f"payment issued for {'email'}", + "description": f"payment issued for {email}", "callback_url": callback_url, "source": { "type": "creditcard", diff --git a/inventory/views.py b/inventory/views.py index 29d145d1..eefb7339 100644 --- a/inventory/views.py +++ b/inventory/views.py @@ -52,7 +52,7 @@ from django.forms import CharField, HiddenInput, ValidationError from django.shortcuts import HttpResponse from django.db.models import Sum, F, Count -from django.db.models.functions import ExtractMonth +from django.db.models.functions import ExtractMonth,Round from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger from django.contrib.auth.models import User, Group from django.db.models import Value @@ -9736,8 +9736,12 @@ def ledger_unpost_all_journals(request, dealer_slug, entity_slug, pk): @permission_required("inventory.change_dealer", raise_exception=True) def pricing_page(request, dealer_slug): dealer=get_object_or_404(models.Dealer, slug=dealer_slug) + vat = models.VatRate.objects.filter(dealer=dealer).first() if not dealer.active_plan: - plan_list = PlanPricing.objects.all() + plan_list = PlanPricing.objects.annotate( + price_with_tax=Round(F('price') * vat.rate + F('price'), 2) + ).all() + form = forms.PaymentPlanForm() return render(request, "pricing_page.html", {"plan_list": plan_list, "form": form}) else: @@ -9786,7 +9790,6 @@ def payment_callback(request, dealer_slug): logger.info(f"Received payment callback for dealer_slug: {dealer_slug}, payment_id: {payment_id}, status: {payment_status}") order = Order.objects.filter(user=dealer.user, status=1).first() # Status 1 = NEW - print(order) if payment_status == "paid": logger.info(f"Payment successful for transaction ID {payment_id}. Processing order completion.") @@ -9807,10 +9810,11 @@ def payment_callback(request, dealer_slug): logger.debug(f"Billing info already exists for user {dealer.user}.") if not hasattr(order.user, 'userplan'): + print(order.get_plan_pricing().pricing.period) UserPlan.objects.create( user=order.user, plan=order.plan, - expire=datetime.now().date() + timedelta(days=order.get_plan_pricing().pricing.period + 30) + expire=datetime.now().date() + timedelta(days=order.get_plan_pricing().pricing.period) ) logger.info(f"Created new UserPlan for user {order.user} with plan {order.plan}.") else: diff --git a/templates/account/signup-wizard.html b/templates/account/signup-wizard.html index 09660e40..7c72c260 100644 --- a/templates/account/signup-wizard.html +++ b/templates/account/signup-wizard.html @@ -305,7 +305,7 @@ return true } function validate_sa_phone_number(phone_number) { - const phone_numberRegex = /^05[0-10]{7}$/; + const phone_numberRegex = /^05[0-9]{8}$/; return phone_numberRegex.test(phone_number) && phone_numberRegex !== ''; } function getAllFormData() { @@ -372,11 +372,7 @@ hideLoading(); const data = await response.json(); if (response.ok) { -<<<<<<< HEAD - notify("success","{% trans 'Account created successfully'%}"); -======= notify("success","Account created successfully"); ->>>>>>> d3dcb85fa378e156b77550e8ab833ad10ffad51f setTimeout(() => { window.location.href = "{% url 'account_login' %}"; }, 1000); diff --git a/templates/pricing_page.html b/templates/pricing_page.html index b235a7dc..96ff6cbb 100644 --- a/templates/pricing_page.html +++ b/templates/pricing_page.html @@ -100,7 +100,7 @@ id="plan_{{ forloop.counter }}" value="{{ pp.id }}" data-name="{{ pp.plan.name }}" - data-price="{{ pp.price }}" + data-price="{{ pp.price_with_tax }}" autocomplete="off" {% if forloop.first %}checked{% endif %}>