Django ManyToMany с двумя полями через промежуточную модель

Пишу код переноса товаров из корзины в заказы. Все работает корректно, но вот как в админке отображается мне не нравится.

Если конкретно, то вся заморочка в том, что я не могу в заказах просто воспользоваться ManyToMany связью с Товарами Product(), потому что в Корзине Basket() есть параметр Сколько шт. count Как это работает:

  • Достаем из БД корзину пользователя
  • Создаем объект Заказов Order()
  • Пробегаемся по Корзине Basket()
    • Каждый продукт из корзины сохраняем вместе с count в модели Purchase()
    • В объекте Заказов Order() есть M2M связь с Purchase(). Вот туда новую запись Purchase() и приклеиваем

views.py:

class OrdersLocation(View):
    """Заказы пользователя"""

    def post(self, request):
        """Оформить заказ всех продуктов из корзины"""
        # Получаем пользователя с его корзиной
        user = User.objects.filter(id=request.user.id).first()
        basket = Basket.objects.filter(user=user).all()

        # Делаем новый заказ
        purchases = []
        for wont in basket:
            p = Purchase(product=wont.product, count=wont.count)
            p.save()
            purchases.append(p)
        order = Order(user=user)
        order.save()
        for _ in purchases:
            order.products.add(_)
        order.save()

        # Очищаем корзину
        for wont in basket:
            wont.delete()
        return redirect('store:orders')

models.py:

class Basket(models.Model):
    """Корзина"""
    user = models.ForeignKey(User, related_name='Пользователь', default=0, editable=False, on_delete=models.CASCADE)
    product = models.ForeignKey(Product, related_name='Товар', default=0, on_delete=models.CASCADE)
    count = models.IntegerField('Сколько шт.', default=1, auto_created=True)
    ctime = models.DateTimeField('Запись создана', default=timezone.now)

    def __str__(self):
        return '{} заказал {} в количестве {} штук' \
               ''.format(self.user_id, self.product.caption, self.count)

    class Meta:
        verbose_name = 'Продукт'
        verbose_name_plural = 'Корзина'


class Purchase(models.Model):
    """Экземпляр заказа"""
    product = models.ForeignKey(Product, default=0, editable=False, on_delete=models.CASCADE)
    count = models.IntegerField('Сколько шт.', default=1, auto_created=True)
    ctime = models.DateTimeField('Запись создана', default=timezone.now)

    def __str__(self):
        return 'Заказ {} в количестве {} шт.' \
               ''.format(self.product.caption, self.count)

    class Meta:
        verbose_name = 'Заказанный продукт'
        verbose_name_plural = 'Заказанные продукты'


class Order(models.Model):
    """Заказы"""
    user = models.ForeignKey(User, default=0, editable=False, on_delete=models.CASCADE)
    products = models.ManyToManyField(Purchase, verbose_name='Заказанные продукты')
    status = models.CharField('Статус', max_length=13, choices=(
        ('Подтверждение', 'Подтверждение'),
        ('Отправка', 'В очереди на отправку'),
        ('Доставка', 'Доставка'),
        ('Доставлен', 'Заказ доставлен'),
        ('Отменено', 'Отменено'),
    ), null=True, default='Подтверждение')
    ctime = models.DateTimeField('Запись создана', default=timezone.now)

    def __str__(self):
        return 'Заказ {} №{}' \
               ''.format(self.user.username, self.id)

    class Meta:
        verbose_name = 'Заказ'
        verbose_name_plural = 'Заказы'

Результат ужасает

admin panel

Вопрос: как сделать так, чтобы администратор сайта мог менять состав заказа: добавлять/удалять товары и указывать через админ-панель количество экземпляров? Сейчас ситуация такова, что каждый раз создается запись Purchase() из товара и количества шт. и вот из них и выбирай. На лету нужную запись не создать, как быть?


Ответы (0 шт):