Django:如何使用自定义模板标签动态获取字段值?
我正在写一个通用的模板标签,目的是根据用户在模板文件中的输入动态返回模型的字段值。这个想法来源于《实用Django项目(第二版)》这本书,但书中的版本是获取一组对象,而我只想获取单个对象的值。我想获取网站设置(比如标题、标语等),并动态传递到模板中,这样我就不需要重复写代码来获取每个字段的值。
以下是我目前的进展。
为模型定义了一个admin.py(这里不包括,因为不重要)
定义了一个模型:
from django.db import models
from django.contrib.sites.models import Site
class Naming(models.Model):
title = models.CharField(max_length=250)
site_id = models.ForeignKey(Site)
tagline = models.CharField(max_length=250)
description = models.TextField(blank=True)
def __unicode__(self):
return self.title
定义了一个模板标签文件,注释的那一行是我卡住的地方
from django.db.models import get_model
from django.contrib.sites.models import Site
from django import template
def do_site_att(parser, token):
bits = token.split_contents()
if len(bits) != 5:
raise template.TemplateSyntaxError("'get_site_att' tag takes exactly four arguments")
model_args = bits[1].split('.')
if len(model_args) != 2:
raise template.TemplateSyntaxError("First argument to 'get_site_att' must be an 'application name'.'model name' string.")
model = get_model(*model_args)
if model is None:
raise template.TemplateSyntaxError("'get_site_att' tag got an invalid model: %s." % bits[1])
return ContentNode(model, bits[2], bits[4])
class ContentNode(template.Node):
def __init__(self, model, field, varname):
self.model = model
self.field = field
self.varname = varname
def render(self, context):
current_site = Site.objects.get_current()
try:
var = self.model.objects.get(site_id=current_site.id)
context[self.varname] = var.title #I get stuck here because it not accepts input like var.field (I have extract the field value above)
except:
context[self.varname] = "Value not found"
return ''
register = template.Library()
register.tag('get_site_att', do_site_att)
在base.html中的模板查询:
{% load general_tags %}
{% get_site_att general.Naming title as title %}
<h1 id="branding">{{title}}</h1>
{% get_site_att general.Naming tagline as tagline %}
<h2 id="tagline">{{tagline}}</h2>
我尝试了所有我能想到的方法,但就是无法让它工作。任何帮助都非常感谢。谢谢。
2 个回答
4
在Python中,如果你想获取一个属性,而这个属性的名字存储在另一个变量里,通常的做法是使用 getattr
这个函数。
context[self.varname] = getattr(var, self.field)
4
我找到了这个问题的解决办法:
在被注释掉的那几行代码中,使用以下代码:
var = self.model.objects.get(site_id__exact=current_site.id)
context[self.varname] = var.__dict__[self.field]#this will get the field's value dynamically, which is what I was looking for