user3595632 user3595632 - 2 months ago 11
Python Question

Django: Which way is better way to find(search) a equal data object?

I am implementing searching functions in

Django
, which of these would be better?

def same_cart_item_in_cart(cart, new_cart_item):
already_exist_cart_item = cart.cartitem_set.filter(
Q(variation__product=new_cart_item.variation.product),
Q(variation=new_cart_item.variation),
Q(width=new_cart_item.width),
Q(height=new_cart_item.height),
).first()

return already_exist_cart_item # It can be None


Override
CartItem
's
__eq__
first.

class CartItem(TimeStampedModel):
cart = models.ForeignKey("Cart")
variation = models.ForeignKey(Variation)
# 벽화 너비
width = models.PositiveIntegerField(
default=1,
validators=[MinValueValidator(1)],
)
# 벽화 높이
height = models.PositiveIntegerField(
default=1,
validators=[MinValueValidator(1)],
)
quantity = models.PositiveIntegerField(
default=1,
validators=[MinValueValidator(1)],
)

class Meta:
ordering = ('-created',)

def __str__(self):
return str(self.variation.product) + ' - ' + str(self.variation)

def __eq__(self, other):
return (
self.variation.product == other.variation.product and
self.variation == other.variation and
self.width == other.width and
self.height == other.height
)


and then,

def same_cart_item_in_cart(cart, new_cart_item):
for cart_item in cart.cartitem_set.all():
if cart_item == new_cart_item:
return cart_item

return None

Answer

As i said in the comment <1> option is better.

And it you are trying to save new instance and check it before saving, Django made it for you. You can add unique_together to your Model Meta and you it will raise error if you would try to save partly same object.

UPDATE

It should optimize your code with using foregn key values directly

So your code would be

def same_cart_item_in_cart(cart, new_cart_item):
    already_exist_cart_item = cart.cartitem_set.filter(
        Q(variation_id=new_cart_item.variation_id),
        Q(width=new_cart_item.width),
        Q(height=new_cart_item.height),
    ).first()

    return already_exist_cart_item 

I removed Q(variation__product=...), if Variation instance is the same, you don't need to query on its fields. And changed Q(variation=...) to Q(variation_id=...)