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

Django分类路径报错:Field 'id'预期数字却得到'economy'

解决Django中Category路径的ValueError问题

错误原因

你的Post模型里,category是关联到Category模型的外键,执行Post.objects.filter(category=cats)时,Django默认会把传入的cats字符串(比如'economy')当作Category的主键id(整数类型)去匹配,类型不匹配就触发了报错:Field 'id' expected a number but got 'economy'。

解决方案

方案一:直接匹配Category的title字段

修改views.py中的查询语句,明确指定匹配Category的title字段:

def CategoryView(request, cats):
    # 匹配Category的title字段,要忽略大小写就用category__title__iexact
    category_posts = Post.objects.filter(category__title=cats)
    return render(request, 'categories.html', {'cats':cats.title(), 'category_posts':category_posts})

如果数据库里的Category标题和URL传入的字符串存在大小写差异(比如库中是'Economy',URL里是'economy'),可以用category__title__iexact=cats实现忽略大小写的匹配。

方案二:使用Slug字段(推荐)

这是更规范的做法,能避免标题含特殊字符导致的路径问题:

  1. 给Category模型添加slug字段
    修改models.py的Category类:

    from django.utils.text import slugify
    
    class Category(models.Model):
        created_at = models.DateTimeField(auto_now_add=True, verbose_name="Created at")
        title = models.CharField(max_length=255, verbose_name="Title")
        slug = models.SlugField(unique=True, max_length=255, verbose_name="Slug")  # 添加该行
        parent = models.ForeignKey('self', related_name='children', on_delete=models.CASCADE, blank=True, null=True)
    
        class Meta:
            verbose_name = "Category"
            verbose_name_plural = "Categories"
            ordering = ['title']
    
        def __str__(self):
            return self.title
        
        # 自动从title生成slug
        def save(self, *args, **kwargs):
            if not self.slug:
                self.slug = slugify(self.title)
            super().save(*args, **kwargs)
    

    执行数据库迁移命令:

    python manage.py makemigrations
    python manage.py migrate
    
  2. 修改URL配置
    将urls.py中的动态路径改为<slug:cats>:

    path('category/<slug:cats>/', views.CategoryView, name ="category"),
    
  3. 更新视图查询逻辑
    修改views.py的查询语句匹配slug字段:

    def CategoryView(request, cats):
        category_posts = Post.objects.filter(category__slug=cats)
        # 获取Category对象,传递正确的标题到模板
        category = Category.objects.get(slug=cats)
        return render(request, 'categories.html', {'cats':category.title, 'category_posts':category_posts})
    

额外修复:模板语法错误

你的categories.html里有{% else %}但没有对应的{% if %},需要在{% for post in category_posts %}前添加{% if category_posts %}:

{% extends 'base.html' %}

{%block content%}

<h1> Category: {{ cats }} </h1>

{% if category_posts %}
{% for post in category_posts %}

<!-- 卡片内容部分 -->

{% endfor %}
{% else %}
    <h2>Sorry this page does not exist....</h2>
{% endif %}

{%endblock%}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.20 07:15:36