You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Django的views.py中遍历Session购物车数据并计算总价

购物车Session遍历异常与金额计算问题

我已将以下购物车数据存入Django Session,期望遍历数据并计算单个商品金额(数量×单价)及总金额:

dict_items([
    ('1', {'name': 'Talon Lott', 'image': '/media/images/products/1.png', 'reg_price': '958.0', 'dis_price': '844.0', 'qty': 1}),
    ('2', {'name': 'Lionel Owens', 'image': '/media/images/products/2.png', 'reg_price': '684.0', 'dis_price': '221.0', 'qty': '1'}),
    ('3', {'name': 'Brenna Chan', 'image': '/media/images/products/3.png', 'reg_price': '728.0', 'dis_price': '177.0', 'qty': 1}),
    ('4', {'name': 'Amos Osborne', 'image': '/media/images/products/4.png', 'reg_price': '453.0', 'dis_price': '547.0', 'qty': '1'})
])

但在views.py文件中遍历时仅能获取ID为1的商品:

{'name': 'Talon Lott', 'image': '/media/images/products/1.png', 'reg_price': '958.0', 'dis_price': '844.0', 'qty': 1}

以下是我的views.py代码(使用jQuery Ajax实现添加商品到购物车功能),请求解决遍历Session数据异常及金额计算问题:

# Add To Cart 
def add_to_cart(request):
    card_product = {}

    card_product[str(request.GET['id'])] ={
        'name': request.GET['name'],
        'image': request.GET['image'],
        'reg_price': request.GET['reg_price'],
        'dis_price': request.GET['dis_price'],
        'qty': request.GET['qty']
    }
    # print(card_product)
    # print(id, name, image, reg_price, dis_price, qty)
    if 'cartdata' in request.session:
        
        if str(request.GET['id']) in request.session['cartdata']:
            card_data = request.session['cartdata']
            card_data[str(request.GET['id'])]['qty'] = int(card_product[str(request.GET['id'])]['qty']) 
            card_data.update(card_data)
            request.session['cartdata'] = card_data
        else:
            card_data = request.session['cartdata']
            card_data.update(card_product)
            request.session['cartdata']= card_data

    else:
        request.session['cartdata'] = card_product

    return JsonResponse({
        'data':request.session['cartdata'],
        'totalitems':len(request.session['cartdata'])
        })
    

  
# Cart Page View

class CartListView(IndexView):
    template_name = 'cart/cart.html'

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        total_amounts = 0
        saving = 0

        if 'cartdata' in self.request.session:
            for pro_id, item in self.request.session['cartdata'].items():

                total_amounts += int(item['qty']) * float(item['dis_price'])
                saving += float(item['reg_price']) - float(item['dis_price'])
                print(item)

                context={
                    'total_amounts': total_amounts,
                    'saving': saving,
                    'cart_data': self.request.session['cartdata'],
                    'totalitems': len(self.request.session['cartdata'])
                }
        
                return context
        else:
            context={
                    'total_amounts': total_amounts,
                    'cart_data':0,
                    'totalitems': 0
                }
        
            return context

问题修复方案

1. 解决遍历仅获取第一个商品的问题

CartListView的get_context_data方法中,return context写在了for循环内部,导致循环第一次迭代就直接返回上下文,后续商品无法遍历。将返回语句移到循环外部即可:

class CartListView(IndexView):
    template_name = 'cart/cart.html'

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        total_amounts = 0
        saving = 0

        if 'cartdata' in self.request.session:
            cart_data = self.request.session['cartdata']
            for pro_id, item in cart_data.items():
                qty = int(item['qty'])
                dis_price = float(item['dis_price'])
                reg_price = float(item['reg_price'])
                
                # 累加单个商品金额到总金额
                total_amounts += qty * dis_price
                # 累加单个商品的总节省金额
                saving += qty * (reg_price - dis_price)
                print(item)

            # 循环结束后统一组装上下文
            context.update({
                'total_amounts': total_amounts,
                'saving': saving,
                'cart_data': cart_data,
                'totalitems': len(cart_data)
            })
        else:
            context.update({
                'total_amounts': total_amounts,
                'cart_data': {},  # 用空字典替代0,避免模板处理异常
                'totalitems': 0
            })
        
        return context

2. 修复add_to_cart中的冗余代码与类型问题

  • 删除冗余的card_data.update(card_data)操作
  • 统一将qty存储为整数,避免后续计算出现类型错误:
def add_to_cart(request):
    product_id = str(request.GET['id'])
    card_product = {
        product_id: {
            'name': request.GET['name'],
            'image': request.GET['image'],
            'reg_price': request.GET['reg_price'],
            'dis_price': request.GET['dis_price'],
            'qty': int(request.GET['qty'])  # 直接转整数存储
        }
    }

    if 'cartdata' in request.session:
        cart_data = request.session['cartdata']
        if product_id in cart_data:
            # 更新已有商品数量
            cart_data[product_id]['qty'] = card_product[product_id]['qty']
        else:
            # 添加新商品到购物车
            cart_data.update(card_product)
        request.session['cartdata'] = cart_data
    else:
        request.session['cartdata'] = card_product

    return JsonResponse({
        'data': request.session['cartdata'],
        'totalitems': len(request.session['cartdata'])
    })

3. 修正总节省金额计算逻辑

原代码仅计算单个商品的差价,未乘以数量,修正后计算所有商品的总节省金额,确保数据准确。


内容的提问来源于stack exchange,提问作者Humayun Ahmed

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.28 19:00:32