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

Django模板标签中调用ContentType.objects.get报DoesNotExist错误

Django模板标签ContentType查询不存在问题排查方案

核心故障点定位

视图层相同查询逻辑正常、模板标签触发DoesNotExist的核心差异在模板调用参数处理:你在模板中对传入的modelname加了|title过滤器,破坏了参数匹配规则。
Django框架django_content_type表中model字段存储的是全小写格式的模型名,和模型类Meta配置的model_name一致,默认是模型类名转全小写生成。而title过滤器会把传入字符串处理为首字母大写、其余字母小写的格式(例如传入srrpitem会输出Srrpitem),大小写不匹配自然无法命中查询。
视图层代码直接读取URL参数中的原始modelname值,没有做格式转换,和数据库存储值匹配,因此可以正常返回结果。

修复方案

直接移除模板调用时的|title过滤器,传入原始全小写格式的modelname即可:

{% get_object modelname primary %}

进阶排查&优化

如果移除过滤器后仍报错,按以下步骤处理:

  • 在模板标签函数中加临时日志,打印实际接收到的参数值,和数据库django_content_type表的存储值逐字对比,排查是否存在多余空格、特殊字符、传值错误问题:
    @register.simple_tag
    def get_object(modelname, id):
        # 临时调试用,确认参数值后可删除
        print(f"接收参数modelname: {repr(modelname)}, id: {repr(id)}")
        ctype = ContentType.objects.get(model=modelname)
        model = ctype.model_class()
        return model.objects.get(pk=id)
    
  • 如果项目中存在多个app下同名模型的情况,查询ContentType时建议同时传入app_label参数做过滤,避免命中错误记录
  • 增加异常兜底逻辑,避免单条数据查询失败导致整个页面崩溃,同时对传入的modelname统一转小写做兼容:
    from django import template
    from django.contrib.contenttypes.models import ContentType
    from django.core.exceptions import ObjectDoesNotExist
    
    register = template.Library()
    
    @register.simple_tag
    def get_object(modelname, id):
        try:
            ctype = ContentType.objects.get(model=modelname.lower())
            model = ctype.model_class()
            return model.objects.get(pk=id)
        except ObjectDoesNotExist:
            return None
    

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.29 15:01:07