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

使用列表时遇'bytes' object has no attribute 'items'错误,需批量添加订单项

问题:批量创建OrderItem时触发bytes对象错误,且循环逻辑存疑

执行代码 items = [item for item in body.items()] 时出现错误:'bytes' object has no attribute 'items'。需求是批量添加多个OrderItem,不确定修复错误后当前循环能否正常实现需求。

请求数据

[
    {
        "service_id": 1,
        "quantity": 2,
        "price": 20
    },
    {
        "service_id": 2,
        "quantity": 3,
        "price": 20
    },
    {
        "service_id": 3,
        "quantity": 4,
        "price": 20
    }
]

现有Django REST接口代码

@api_view(['GET', 'POST'])
@csrf_exempt
# class CreteOrderView(View):
def create_order(request, *args, **kwargs):

    if request.method == 'POST':
        
        now = datetime.date.today()
        order = Order.objects.create(date=now)
        order.save()
        orderid = order.id
        order_id = orderid
        data = json.loads(request.body)
        price = request.session.get('price')
        quantity = request.session.get('quantity')
        print('quantity ' + str(quantity))
        service_id = request.session.get('service_id')
        body = request.body
        items = [item for item in body.items()]
        for item in items:
            orderitemcreate= OrderItem.objects.create(order_id_id=order_id,
                                                    service_id_id=service_id,
                                                    quantity=quantity,
                                                    price=price)
            orderitemcreate.save()
        return Response({"Order_id":str(order.id),
                        "Order_date":str(order.date),
                        "OrderItems_id" :str(orderitemcreate.id),
                        "service_id" :str(orderitemcreate.service_id),
                        "quantity" :str(orderitemcreate.quantity),
                        "price":str(orderitemcreate.price)})
        
    else:
        order_qs = models.Order.objects.all().values_list()
        OrderItem_qs = models.OrderItem.objects.all().values_list()
        return Response({"Order":str(order_qs),"OrderItem":str(OrderItem_qs)})

修复方案

1. 解决bytes对象错误

request.body 是字节类型,无法直接调用 .items() 方法。你已经通过 data = json.loads(request.body) 将字节数据解析成了列表,因此直接遍历 data 即可,无需再操作 body。删掉 body = request.body 和 items = [item for item in body.items()] 这两行代码。

2. 修正批量创建逻辑

当前循环完全没有使用请求体里的每个item数据,而是用session中的固定值创建OrderItem,会导致所有OrderItem的字段值完全一致,不符合批量创建不同条目需求。需要在循环中读取每个item的对应字段:

修改后的POST核心代码:

if request.method == 'POST':
    now = datetime.date.today()
    order = Order.objects.create(date=now)
    order_id = order.id
    data = json.loads(request.body)
    
    # 批量创建优化:先收集所有对象再批量插入
    order_items = []
    for item in data:
        order_item = OrderItem(
            order_id=order,  # 直接传入order对象,无需用order_id_id
            service_id_id=item['service_id'],
            quantity=item['quantity'],
            price=item['price']
        )
        order_items.append(order_item)
    
    OrderItem.objects.bulk_create(order_items)
    
    last_item = order_items[-1]
    return Response({
        "Order_id": str(order.id),
        "Order_date": str(order.date),
        "Last_OrderItem_id": str(last_item.id),
        "Total_OrderItems": len(order_items)
    })

额外优化建议

  • 删掉 order.save():Order.objects.create() 方法已经自动完成保存操作,无需重复调用。
  • 使用 bulk_create:相比循环调用 create,批量插入能大幅提升数据库操作性能。
  • 添加数据校验:建议使用Django REST Framework的序列化器对请求数据进行合法性校验,避免非法数据导致报错。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 04:18:14