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

Django多对多字段赋值报错:期望ID数字却收到分类名称

解决方案

问题本质

product.categories.set() 方法要求传入关联对象的ID(数字类型)或模型实例,但前端传递的是分类的标题字符串(比如'face picture from actor'),导致Django无法将字符串解析为分类ID,触发ValueError。你的models.py中ManyToManyField的定义是正确的,问题出在前后端数据传递不匹配。


方法1:修改前端传递分类ID(推荐)

在manager_room.js的下拉选择框中,将option的value属性设置为分类的id而非title:

{categoryList.map(category => (
  <option key={category.id} value={category.id}>
    {category.title}
  </option>
))}

后端无需修改,product.categories.set(data.getlist('category'))可以直接接收ID列表并完成关联。


方法2:后端适配接收的标题字符串

如果前端无法修改传递的数据,后端需要先根据标题查询对应的ProductCategory实例,再传递给set()方法:

# product_views.py 中的处理逻辑
from django.shortcuts import get_list_or_404

# 获取前端传递的分类标题列表
category_titles = data.getlist('category')
# 根据标题查询对应的分类实例
categories = get_list_or_404(ProductCategory, title__in=category_titles)
# 关联分类
product.categories.set(categories)

注意:如果存在多个分类标题重复的情况,需要先确保ProductCategory的title字段是唯一的(可以在models中添加unique=True约束),避免查询出错。


方法3:通过序列化器自动处理(DRF场景)

如果使用Django REST Framework的序列化器,可以在序列化器中配置SlugRelatedField,自动将标题转换为实例:

# product_serializers.py
from rest_framework import serializers
from .models import Product, ProductCategory

class ProductSerializer(serializers.ModelSerializer):
    categories = serializers.SlugRelatedField(
        many=True,
        queryset=ProductCategory.objects.all(),
        slug_field='title'
    )

    class Meta:
        model = Product
        fields = ['id', 'name', 'categories', ...]

在视图中使用序列化器处理数据时,会自动将前端传递的标题字符串转换为对应的分类实例,无需手动调用set()方法。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.02 21:05:55