diff --git a/inventory/models.py b/inventory/models.py index 761de267..9616f067 100644 --- a/inventory/models.py +++ b/inventory/models.py @@ -1306,7 +1306,7 @@ class Dealer(models.Model, LocalizedNameMixin): ) arabic_name = models.CharField(max_length=255, verbose_name=_("Arabic Name")) name = models.CharField(max_length=255, verbose_name=_("English Name")) - phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator]) + phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator()]) address = models.CharField( max_length=200, blank=True, null=True, verbose_name=_("Address") ) @@ -1432,7 +1432,7 @@ class Staff(models.Model): last_name = models.CharField(max_length=255, verbose_name=_("Last Name")) arabic_name = models.CharField(max_length=255, verbose_name=_("Arabic Name")) - phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator]) + phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator()]) staff_type = models.CharField( choices=StaffTypes.choices, max_length=255, verbose_name=_("Staff Type") ) @@ -1826,7 +1826,7 @@ class Organization(models.Model, LocalizedNameMixin): ) vrn = models.CharField(max_length=15, verbose_name=_("VAT Registration Number")) email = models.EmailField(verbose_name=_("Email")) - phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator]) + phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator()]) address = models.CharField( max_length=200, blank=True, null=True, verbose_name=_("Address") ) @@ -1960,7 +1960,7 @@ class Representative(models.Model, LocalizedNameMixin): id_number = models.CharField( max_length=10, unique=True, verbose_name=_("ID Number") ) - phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator]) + phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator()]) email = models.EmailField(max_length=255, verbose_name=_("Email Address")) address = models.CharField( max_length=200, blank=True, null=True, verbose_name=_("Address") @@ -2668,7 +2668,7 @@ class Vendor(models.Model, LocalizedNameMixin): arabic_name = models.CharField(max_length=255, verbose_name=_("Arabic Name")) name = models.CharField(max_length=255, verbose_name=_("English Name")) contact_person = models.CharField(max_length=100, verbose_name=_("Contact Person")) - phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator]) + phone_number = models.CharField(max_length=255, verbose_name=_("Phone Number"),validators=[SaudiPhoneNumberValidator()]) email = models.EmailField(max_length=255, verbose_name=_("Email Address")) address = models.CharField(max_length=200, verbose_name=_("Address")) logo = models.ImageField( diff --git a/inventory/utils.py b/inventory/utils.py index 660ea13a..1886d8fc 100644 --- a/inventory/utils.py +++ b/inventory/utils.py @@ -1571,13 +1571,13 @@ def _post_sale_and_cogs(invoice, dealer): # calc = CarFinanceCalculator(invoice) data = get_finance_data(invoice,dealer) car = data.get("car") - cash_acc = entity.get_all_accounts().filter(role_default=True, role=roles.ASSET_CA_CASH).first() - ar_acc = entity.get_all_accounts().filter(role_default=True, role=roles.ASSET_CA_RECEIVABLES).first() - vat_acc = entity.get_all_accounts().filter(role_default=True, role=roles.LIABILITY_CL_TAXES_PAYABLE).first() - car_rev = entity.get_all_accounts().filter(role_default=True, role=roles.INCOME_OPERATIONAL).first() - add_rev = entity.get_all_accounts().filter(role_default=True, role=roles.INCOME_OPERATIONAL).first() - cogs_acc = entity.get_all_accounts().filter(role_default=True, role=roles.COGS).first() - inv_acc = entity.get_all_accounts().filter(role_default=True, role=roles.ASSET_CA_INVENTORY).first() + cash_acc = entity.get_default_coa_accounts().filter(role_default=True, role=roles.ASSET_CA_CASH).first() + ar_acc = entity.get_default_coa_accounts().filter(role_default=True, role=roles.ASSET_CA_RECEIVABLES).first() + vat_acc = entity.get_default_coa_accounts().filter(role_default=True, role=roles.LIABILITY_CL_TAXES_PAYABLE).first() + car_rev = entity.get_default_coa_accounts().filter(role_default=True, role=roles.INCOME_OPERATIONAL).first() + add_rev = entity.get_default_coa_accounts().filter(code="4020").first() + cogs_acc = entity.get_default_coa_accounts().filter(role_default=True, role=roles.COGS).first() + inv_acc = entity.get_default_coa_accounts().filter(role_default=True, role=roles.ASSET_CA_INVENTORY).first() # for car_data in data['cars']: # car = invoice.get_itemtxs_data()[0].filter( @@ -1588,7 +1588,7 @@ def _post_sale_and_cogs(invoice, dealer): net_car_price = Decimal(data['discounted_price']) net_additionals_price = Decimal(data['additional_services']['total']) vat_amount = Decimal(data['vat_amount']) - grand_total = net_car_price + net_additionals_price + vat_amount + grand_total = net_car_price + car.get_additional_services_amount_ + vat_amount cost_total = Decimal(car.cost_price) discount_amount =Decimal(data['discount_amount']) @@ -1608,7 +1608,8 @@ def _post_sale_and_cogs(invoice, dealer): journal_entry=je_sale, account=cash_acc, amount=grand_total, - tx_type='debit' + tx_type='debit', + description='Debit to Cash on Hand' ) # # Cr A/R (clear the receivable) @@ -1624,7 +1625,8 @@ def _post_sale_and_cogs(invoice, dealer): journal_entry=je_sale, account=vat_acc, amount=vat_amount, - tx_type='credit' + tx_type='credit', + description="Credit to Tax Payable" ) # Cr Sales – Car @@ -1632,16 +1634,26 @@ def _post_sale_and_cogs(invoice, dealer): journal_entry=je_sale, account=car_rev, amount=net_car_price, - tx_type='credit' + tx_type='credit', + description=" Credit to Car Sales" ) - if net_additionals_price > 0: + if car.get_additional_services_amount > 0: # Cr Sales – Additional Services TransactionModel.objects.create( journal_entry=je_sale, account=add_rev, - amount=net_additionals_price, - tx_type='credit' + amount=car.get_additional_services_amount, + tx_type='credit', + description="Credit to After-Sales Services" + ) + TransactionModel.objects.create( + journal_entry=je_sale, + + account=vat_acc, + amount=car.get_additional_services_vat, + tx_type='credit', + description="Credit to Tax Payable (Additional Services)" ) # ------------------------------------------------------------------ @@ -1660,7 +1672,7 @@ def _post_sale_and_cogs(invoice, dealer): journal_entry=je_cogs, account=cogs_acc, amount=cost_total, - tx_type='debit' + tx_type='debit', ) # Cr Inventory diff --git a/inventory/validators.py b/inventory/validators.py index 4c7a0191..a3a9c8aa 100644 --- a/inventory/validators.py +++ b/inventory/validators.py @@ -1,10 +1,14 @@ from django.core.validators import RegexValidator from django.utils.translation import gettext_lazy as _ - +import re class SaudiPhoneNumberValidator(RegexValidator): def __init__(self, *args, **kwargs): super().__init__( regex=r"^(\+9665|05)[0-9]{8}$", message=_("Enter a valid Saudi phone number (05XXXXXXXX or +9665XXXXXXXX)"), - ) \ No newline at end of file + ) + def __call__(self, value): + # Remove any whitespace, dashes, or other separators + cleaned_value = re.sub(r'[\s\-\(\)\.]', '', str(value)) + super().__call__(cleaned_value) \ No newline at end of file diff --git a/scripts/set_plans.py b/scripts/set_plans.py index a5593359..11ef1bf5 100644 --- a/scripts/set_plans.py +++ b/scripts/set_plans.py @@ -4,6 +4,13 @@ from decimal import Decimal def run(): # Create quotas first + free_quota = Quota.objects.create( + codename="free_quota", + name="Free Features", + description="Free plan features", + is_boolean=True, + url="pricing", + ) basic_quota = Quota.objects.create( codename="basic_quota", name="Basic Features", @@ -27,7 +34,19 @@ def run(): is_boolean=True, url="pricing", ) - + # Create the plans + free_plan = Plan.objects.create( + name="Free", + description="Free plan with limited features", + price=Decimal("0.00"), # 0 + period=7, # 1 week + default=True, + available=True, + visible=True, + order=1, + ) + free_plan.quotas.add(free_quota) + # Create the plans basic_plan = Plan.objects.create( name="Basic", diff --git a/templates/dealers/dealer_detail.html b/templates/dealers/dealer_detail.html index 704b2d97..88cd9a90 100644 --- a/templates/dealers/dealer_detail.html +++ b/templates/dealers/dealer_detail.html @@ -138,11 +138,11 @@ {% endcomment %}
{% if not dealer.user.userplan %} - {{ _("Subscribe Now") }} + {{ _("Subscribe Now") }} {% elif dealer.user.userplan.is_expired %} - {{ _("Renew") }} + {{ _("Renew") }} {% elif dealer.user.userplan.plan.name != "Enterprise" %} - {{ _("Upgrade Plan") }} + {{ _("Upgrade Plan") }} {% endif %}
diff --git a/templates/inventory/inventory_stats.html b/templates/inventory/inventory_stats.html index 21f9c38d..b05648bd 100644 --- a/templates/inventory/inventory_stats.html +++ b/templates/inventory/inventory_stats.html @@ -39,7 +39,7 @@ {% if inventory.total_cars > 0 %}
-
+

    {% trans "Powered By Tenhal" %}