Home > Net >  Strange Error When Checking If Object Exists
Strange Error When Checking If Object Exists

Time:12-29

Thanks ahead of time for the help. I am trying to check if a cart object exists when a user visits the "myCart" page. If it does not, it should then create a new instance and use the user's id as a foreign key for reverse lookup. So I used the exists() method in an if statement. What's weird is that instead of executing the else block, it just throws me an error telling me the object doesn't exist. The test user doesn't have a cart object associated with it yet and that's obvious. What I don't understand is why it isn't triggering my else statement. Maybe I have been coding too long and need some sleep and that's why I'm missing it. Anyway if you guys could take a look for me I'd really appreciate it. :)

The Error: Weird Error

#the views.py file for this app:

def myCart(request):
    context = {}
    if request.user.is_authenticated:
        owner = request.user.id
        if Cart.objects.get(cart_owner=owner).exists():
            context['cart'] = cart
            return render(request, 'cart/myCart.html', context)
        else:
            cart = Cart(cart_owner=owner)
            context['cart'] = cart
        return render(request, 'cart/myCart.html', context)
    else:
        return HttpResponseRedirect(reverse("login"))



def update_cart(request):
    
    if request.user.is_authenticated:
        owner = request.user.id
        cart = Cart.objects.get(cart_owner=owner)


        productID = request.GET['id']
        product = Product.objects.get(pk=productID) 

        if not product in cart.products.all():
            cart.products.add(product)
        else:
            cart.products.remove(product)

        new_total = 0.00
        for item in cart.products.all():
            new_total  = float(item.priceNotax)

        cart.total = new_total
        cart.save()
        return HttpResponseRedirect(reverse("myCart"))

    else:
        return HttpResponseRedirect(reverse("login"))

The cart model:

class Cart(models.Model):
    cart_owner = models.ForeignKey(User, on_delete=models.CASCADE, null=True)
    products = models.ManyToManyField(Product, null=True, blank=True)
    total = models.DecimalField(max_digits=100, decimal_places=2, default=0.00)
    timestamp = models.DateTimeField(auto_now_add=False, auto_now=True)
    updated = models.DateTimeField(auto_now_add=False, auto_now=True)
    active = models.BooleanField(default=True)

    def __unicode__(self):
        return "Cart id: %s" %(self.id)

CodePudding user response:

By using .get(…), you retrieve the Cart, and if that is done successfully, .exists() will not work since a model object has no .exists() object.

You can work with .get_or_create(…) [Django-doc] to retrieve, or create a Cart object in case no such Cart exists:

from django.contrib.auth.decorators import login_required

@login_required
def myCart(request):
    context = {}
    context['cart'], __ = Cart.objects.get_or_create(cart_owner=request.user)
    return render(request, 'cart/myCart.html', context)

Note: It is normally better to make use of the settings.AUTH_USER_MODEL [Django-doc] to refer to the user model, than to use the User model [Django-doc] directly. For more information you can see the referencing the User model section of the documentation.


Note: You can limit views to a view to authenticated users with the @login_required decorator [Django-doc].

CodePudding user response:

.get() will throw an error if exactly 1 object was not found. Instead, replace it with .filter() and then you can check .exists()
Hence, change Cart.objects.get(cart_owner=owner).exists() to Cart.objects.filter(cart_owner=owner).exists()
Alternatively, you can use a try-except block which is technically a bit faster:

try:
    thepost = Content.objects.get(name="test")
except Content.DoesNotExist:
    thepost = None
  • Related