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

Django中如何将选中商品的input number数据正确传递至视图?

Django表单提交:关联选中商品ID与对应数量的解决方案

页面展示多个商品时,每个商品对应一个checkbox和input type='number'数量选择框,提交表单至create-order视图后,request.POST.getlist('quantity')会返回所有商品的数量,但仅需已勾选商品的对应数量,理想状态是形成如[(1,3),(2,4),(3,5)]的元组列表或{1:3,2:4,3:5}的字典,确保仅获取选中商品的数量。

当前表单代码:

<form action="{% url 'create-order' %}" method="POST">
    {% csrf_token %}
    <table class="table table-responsive table-borderless">
        <thead>
            <th>&nbsp;</th>
            <th>Quantity</th>
        </thead>
        <tbody>
            {% for item in items %}
            <tr class="align-middle alert border-bottom">
                <td>
                    <input type="checkbox" id="check" name="item" value="{{ item.id }}">
                </td>
                <td>
                    <input class="input" min="1" value=1 type="number" name="quantity">
                </td>
            </tr>
            {% endfor %}
        </tbody>
    </table>
    <div class="submitButton">
        <button type="submit" class="lgbtn green">Go to order</button>
    </div>
</form>

当前视图代码:

def create_order(request):
    quantities = request.POST.getlist('quantity')
    items = request.POST.getlist('item')
    return JsonResponse({
        'quantities': quantities, 
        'items': items
    })

问题示例:6个ID为1-6的商品,勾选1、2、3并设置数量为3、4、5,获取到items=[1,2,3](正常),但quantities=[3,4,5,1,1,1],无法直接对应选中商品的数量。


解决方案1:后端关联(推荐,安全性更高)

修改表单中数量输入框的name属性,将其与商品ID绑定,确保每个数量输入框的名称唯一且关联对应商品:

<!-- 仅修改数量输入框的name属性 -->
<input class="input" min="1" value=1 type="number" name="quantity_{{ item.id }}">

然后在视图中,根据选中的商品ID,针对性获取对应数量:

def create_order(request):
    selected_item_ids = request.POST.getlist('item')
    item_quantity = {}
    
    for item_id in selected_item_ids:
        # 获取对应商品的数量,默认值设为1
        quantity_str = request.POST.get(f'quantity_{item_id}', '1')
        try:
            # 转换为整数并验证合法性
            quantity = int(quantity_str)
            if quantity < 1:
                quantity = 1
        except ValueError:
            # 非法输入时默认设为1
            quantity = 1
        item_quantity[int(item_id)] = quantity
    
    # 转换为元组列表(可选)
    item_quantity_list = list(item_quantity.items())
    
    return JsonResponse({
        'item_quantity_dict': item_quantity,
        'item_quantity_list': item_quantity_list
    })

解决方案2:前端控制提交内容

通过JavaScript在表单提交前,禁用未勾选商品的数量输入框(禁用的输入框不会被提交):

<!-- 在表单结束前添加脚本 -->
<script>
document.querySelector('form').addEventListener('submit', function(e) {
    const checkboxes = document.querySelectorAll('input[name="item"]');
    checkboxes.forEach(checkbox => {
        const quantityInput = checkbox.closest('tr').querySelector('input[name="quantity"]');
        quantityInput.disabled = !checkbox.checked;
    });
});
</script>
</form>

此时视图中可以直接通过zip关联选中商品ID和对应数量:

def create_order(request):
    try:
        selected_item_ids = list(map(int, request.POST.getlist('item')))
        quantities = list(map(int, request.POST.getlist('quantity')))
        # 确保数量和商品ID长度一致(前端可能被篡改,需验证)
        if len(selected_item_ids) != len(quantities):
            raise ValueError("数量与选中商品不匹配")
        # 过滤非法数量
        valid_pairs = [(item_id, qty) for item_id, qty in zip(selected_item_ids, quantities) if qty >=1]
        item_quantity_dict = dict(valid_pairs)
    except (ValueError, TypeError):
        # 处理异常情况,返回空或默认值
        item_quantity_dict = {}
        valid_pairs = []
    
    return JsonResponse({
        'item_quantity_dict': item_quantity_dict,
        'item_quantity_list': valid_pairs
    })

注意:方案2依赖前端逻辑,存在被篡改的风险,建议配合后端验证使用,确保数据合法性。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.10 18:05:17