在Django模板中动态显示字段值 (object.x)
我现在正在开发一个应用程序,它使用自定义的注解查询集。目前我设置了两个网址,但我需要为用户希望汇总数据的每个字段设置一个网址。如果手动配置的话,就会违反“不要重复自己”的原则!这样的话,我大概会有8个网址,它们基本上做的都是同样的事情。
所以我做了以下几件事:
- 我创建了一个自定义模型管理器
- 我有一个视图
- 我配置了网址
以上所有内容都能正常工作。
简单来说,网址配置会把要注解的字段名称(对于懂SQL的人来说就是分组)传递给视图,视图会进行一些额外的处理,并根据传递的字段运行自定义模型管理器。
网址看起来是这样的:
url('^(?P<field>[\w-]+)/(?P<year>\d{4})/(?P<month>\d+)/(?P<day>\d+)/$','by_subtype', name='chart_link'),
field是数据库中实际运行查询集时使用的列。它是从视图传递到我的自定义管理器的。下面是管理器中的代码示例:
return self.filter(start_date_time__year=year).filter(start_date_time__month=month).filter(start_date_time__day=day).values(field).annotate(Count(field))
此外,我还将field的值作为上下文变量传递。这用于动态构建链接。不过,问题在于循环查询集并显示数据。
所以你典型的模板代码看起来是这样的:
{% for object in object_list %}
{{ object.sub_type }} : {{ object.sub_type__count|intcomma }}
{% endfor %}
基本上,你必须硬编码要显示的字段(比如object.x),有没有办法动态分配这个字段?也就是说,如果field = business,那么在模板中它应该自动处理:
{{ object.business }}
这能做到吗?还是我需要创建多个网址?或者有没有更好的方法来实现同样的结果,使用一个视图和网址动态处理查询。
你可以在github上找到代码,模板部分现在使用这个代码片段正常工作:http://www.djangosnippets.org/snippets/1412/。所以如果你之后遇到这个问题,想做类似的事情,可以看看github上的代码片段:http://gist.github.com/233262
2 个回答
如上所述,你可以通过自定义模板过滤器来实现这个功能。
举个例子:
@register.filter(name='get_attr')
def get_attr(obj, field_name):
if isinstance(obj, dict):
return obj.get(field_name)
return getattr(obj, field_name)
然后,在你的模板中使用它:
{{ obj|get_attr:'business' }}
听起来你想做的事情是这样的:
# in the views.py:
field = 'business'
{# in the template: #}
{{ object.field }}
并且希望在输出中显示 object.business
的值。不过,使用Django的模板语言,默认情况下是无法做到这一点的。
不过,有一些代码片段可以定义模板过滤器,帮助你实现这个功能:http://www.djangosnippets.org/snippets/1412/