我有一个名为Subtopic的模型。我的一个模板在一个对象上运行一个forloop,为一个表行的每个单元格返回一个不同的字段。
其中两个表格单元格查找一个字段,该字段是ManytoMany外键,对于同一个外部模型Resource。我希望每个都根据资源模型中的布尔字段的值显示不同的结果。
您在下面看到的内容目前正常,但不会尝试按布尔字段进行过滤。
models.py:
class ICTResourceManager(models.Manager):
def get_query_set(self):
return super(ICTResourceManager, self).get_query_set().filter('is_ict': True)
class NonICTResourceManager(models.Manager):
def get_query_set(self):
return super(NonICTResourceManager, self).get_query_set().filter('is_ict': False)
class Resource(models.Model):
subtopics = models.ManyToManyField(Subtopic)
external_site = models.ForeignKey(ExternalSite)
link_address = models.URLField(max_length=200, unique=True, verify_exists=False)
requires_login = models.BooleanField()
is_ict = models.BooleanField()
flags = models.ManyToManyField(Flag, blank=True)
comment = models.TextField()
def __unicode__(self):
return u'%s %s' % (self.external_site, self.link_address)
objects = models.Manager()
ict_objects = ICTResourceManager()
nonict_objects = NonICTResourceManager()
class Meta:
ordering = ['external_site', 'link_address']
views.py:
def view_ks5topic(request, modulecode, topicshortname):
listofsubtopics = Subtopic.objects.filter(topic__module__code__iexact = modulecode, topic__shortname__iexact = topicshortname)
themodule = Module.objects.get(code__iexact = modulecode)
thetopic = Topic.objects.get(module__code__iexact = modulecode, shortname__iexact = topicshortname)
return render_to_response('topic_page.html', locals())
我的模板:
{% for whatever in listofsubtopics %}
<tr>
<td>
{{ whatever.objective_html|safe }}
<p>
{% if request.user.is_authenticated %}
{% with 'objective' as column %}
{% include "edit_text.html" %}
{% endwith %}
{% else %}
{% endif %}
</td>
<td>
{% regroup whatever.resource_set.all by external_site.name as resource_list %}
{% for external_site in resource_list %}
<h4>{{ external_site.grouper }}</h4>
<ul>
{% for item in external_site.list %}
<li><a href="{{ item.link_address }}">{{ item.comment }}</a></li>
{% endfor %}
</ul>
{% endfor %}
</td>
</tr>
{% endfor %}
正如你所看到的,我已经为模型添加了额外的管理器来为我做过滤,但是当我替换模板中的相应行时,我只是得到了空白。我尝试过:for external_site.ict_objects in resource_list
和for item.ict_objects in resource_list
以及<a href="{{ item.ict_objects.link_address }}">
。如果在视图中我可能只用.filter('is_ict': True)
进行过滤,但是在forloop中我不知道在哪里进行过滤。
我还尝试在模板中编写regroup whatever.resource_set.filter('is_ict': True)
,但重新组合的语法似乎使用resource_set.all
而不是resource_set.all()
(我不知道为什么)所以滤镜文本没有在这里工作。
答案 0 :(得分:0)
原来可以使用自定义模板过滤器来完成。考虑到as is well documented模板语言不是一个完全成熟的python环境,在模板中过滤的原始努力是行不通的。对于任何知道替代方法的人来说,我原来的问题仍然是开放的,这种方法可以更直接地解决我最初提出的问题,但这是我如何做到的:
myapp_extras.py:
from django import template
register = template.Library()
def ict(value, arg):
"filters on whether the is_ict Boolean is true"
return value.filter(is_ict=arg)
register.filter('ict', ict)
我的模板,请注意第2行中使用自定义过滤器:
<td>
{% regroup whatever.resource_set.all|ict:1 by external_site.name as resource_list %}
{% for external_site in resource_list %}
<h4>{{ external_site.grouper }}</h4>
<ul>
{% for item in external_site.list %}
<li><a href="{{ item.link_address }}">{{ item.comment }}</a></li>
{% endfor %}
</ul>
{% endfor %}
</td>
在此之后,我能够从模型中删除其他自定义管理器。
另外一个问题是,当过滤布尔值is_ict字段时,我发现我必须使用filter(is_ict=1)
和filter(is_ict=0)
。这是引用True
或False
值的唯一方法吗?