Django showing error 'constraints' refers to the joined field
Asked Answered
H

1

8

I have two models Product and Cart. Product model has maximum_order_quantity. While updating quantity in cart, I'll have to check whether quantity is greater than maximum_order_quantityat database level. For that am comparing quantity with maximum_order_quantity in Cart Model But it throws an error when I try to migrate

cart.CartItems: (models.E041) 'constraints' refers to the joined field 'product__maximum_order_quantity'.

Below are my models

class Products(models.Model):
    category = models.ForeignKey(
        Category, on_delete=models.CASCADE, related_name="products"
    )
    product_name = models.CharField(max_length=50, unique=True)
    base_price = models.IntegerField()
    product_image = models.ImageField(
        upload_to="photos/products", null=True, blank=True
    )
    stock = models.IntegerField(validators=[MinValueValidator(0)])
    maximum_order_quantity = models.IntegerField(null=True, blank=True)
)

class CartItems(models.Model):
    cart = models.ForeignKey(Cart, on_delete=models.CASCADE)
    product = models.ForeignKey(Products, on_delete=models.CASCADE)
    quantity = models.IntegerField()

    class Meta:
        verbose_name_plural = "Cart Items"
        constraints = [
            models.CheckConstraint(
            check=models.Q(quantity__gt=models.F("product__maximum_order_quantity")),
            name="Quantity cannot be more than maximum order quantity"
            )
        ]

Error

SystemCheckError: System check identified some issues:

ERRORS:
cart.CartItems: (models.E041) 'constraints' refers to the joined field 'product__maximum_order_quantity'.
Hasp answered 5/3, 2023 at 4:17 Comment(0)
C
10

You cannot reference fields on related models in database-level constraints like CheckConstraint.

The error message you received is indicating that you cannot reference the maximum_order_quantity field of the Products model in the constraints attribute of the CartItems model.

The reason for this is that the maximum_order_quantity field is a property of the Products model, and in the CartItems model, you are referencing it through a foreign key relationship. Specifically, you are using the syntax product__maximum_order_quantity to access the maximum_order_quantity field of the related Products model.

However, the constraints attribute can only reference fields that belong to the same model. It cannot reference fields of related models.

Currently, you can override the clean() method as:

from django.core.exceptions import ValidationError

class CartItems(models.Model):
    cart = models.ForeignKey(Cart, on_delete=models.CASCADE)
    product = models.ForeignKey(Products, on_delete=models.CASCADE)
    quantity = models.IntegerField()

    def clean(self):
        if self.quantity > self.product.maximum_order_quantity:
            raise ValidationError('Quantity cannot be more than maximum order quantity')

Note: Models in Django don't require s to be added as suffix, since it is added by default. So it is better to change them as CartItem and Product from CartItems and Products respectively.

Caffey answered 5/3, 2023 at 7:23 Comment(4)
Thank you so much for the answer. I'll try it out. And could you explain me why referrencing field on related models in db level constraints donot work. And does this clean() method check on database level?Hasp
@Hasp Since models can be changed independently, and clean() method is used for validating.Caffey
Didn't understand it well. If could possible share me some resources regarding that and why referencing field on related models in db level constraints don't work.Hasp
@Hasp Added more info, see edited answer.Caffey

© 2022 - 2024 — McMap. All rights reserved.