users models.py:
from django.contrib.auth.models import AbstractUser
from phonenumber_field.modelfields import PhoneNumberField
from django.db import models
class CustomUser(AbstractUser):
USER_CHOICES = (
('s', 'Сотрудник'),
('p', 'Подрядчик'),
('k', 'Клиент'),
)
user_type = models.CharField('Тип сотрудника', choices=USER_CHOICES, null=False, blank=False, max_length=1)
balance = models.DecimalField('Баланс', max_digits=10, decimal_places=2, default=0.0)
description = models.TextField('Описание', null=False, blank=False)
phone = PhoneNumberField("Телефон", null=False, blank=False, unique=True)
first_name = models.CharField('Имя', max_length=30, null=False, blank=False)
last_name = models.CharField('Фамилия', max_length=30, null=False, blank=False)
financial_accounting = models.BooleanField('Вести учёт финансов', default=False)
def save(self, *args, **kwargs):
from payments.models import Payment, Invoice
payments_sum = sum([sum([payment.total for payment in invoice.payments.filter(approved=True)]) for invoice in Invoice.objects.filter(receiver=self.id)])
self.balance = payments_sum
super().save(*args, **kwargs)
def __str__(self):
return self.username
class Meta:
verbose_name = 'Сотрудник'
verbose_name_plural = 'Сотрудники'
payments models.py:
class Invoice(models.Model):
payments = models.ManyToManyField('Payment', related_name='invoices', verbose_name='Платежи', blank=True)
comment = models.TextField('Комментарий к счёту')
payment_type = models.ForeignKey('PaymentType', on_delete=models.CASCADE, related_name='invoices', verbose_name="Тип начисления")
subtype = models.ForeignKey('SubType', on_delete=models.CASCADE, related_name='invoices', verbose_name="Назначение начисления")
payer = models.ForeignKey(CustomUser, on_delete=models.CASCADE, related_name='invoices', verbose_name="Плательщик")
receiver = models.ForeignKey(CustomUser, on_delete=models.CASCADE, related_name='received_invoices', verbose_name="Получатель")
project = models.ForeignKey(Project, on_delete=models.CASCADE, related_name='invoices', verbose_name="Выбор проекта")
approved = models.BooleanField('Счёт оплачен', default=False)
class Meta:
verbose_name = 'Счёт на оплату'
verbose_name_plural = 'Счета на оплату'
def __str__(self):
return f'Счёт {self.id}'
class Payment(models.Model):
id = models.CharField(primary_key=True, max_length=10, unique=True, blank=True)
project = models.ForeignKey(Project, on_delete=models.CASCADE, related_name='payments', verbose_name="Проект")
date = models.DateField("Дата начисления", default=date.today)
subtype = models.ForeignKey('SubType', on_delete=models.CASCADE, related_name='payments', verbose_name="Назначение платежа")
total = models.DecimalField('Сумма платежа', max_digits=10, decimal_places=2, default=0.0)
approved = models.BooleanField('Подтверждение платежа', default=False)
def save(self, *args, **kwargs):
if not self.id:
last_id = Payment.objects.order_by('-id').first()
if last_id:
last_number = int(last_id.id)
self.id = str(last_number + 1)
else:
self.id = "10001"
super().save(*args, **kwargs)
class Meta:
verbose_name = 'Платёж'
verbose_name_plural = 'Платежи'
def __str__(self):
return f'Платёж {self.id}'
Сейчас поле balance у юзера заполняется, только когда я сохраняю его в админке. Т.е. я меняю payment'ы, и чтобы изменения отобразились на балансе, мне нужно обязательно нажать на сохранение. Как сделать, чтобы это всё происходило как-нибудь автоматически?