6

我正在尝试在使用 Django 1.4.3(使用 Python 2.7.2)的项目中使用 SO 答案中描述的模板标签: https ://stackoverflow.com/a/6217194/493211。

我是这样改编的:

from django import template


register = template.Library()

@register.filter
def template_exists(template_name):
    try:
        template.loader.get_template(template_name)
        return True
    except template.TemplateDoesNotExist:
        return False

这样我就可以在另一个模板中像这样使用它:

{% if 'profile/header.html'|template_exists %}        
  {% include 'profile/header.html' %}
{% else %}
  {% include 'common/header.html' %}
{% endif %}

这样,我可以避免使用诸如更改 INSTALLED_APPS 中的应用程序顺序之类的解决方案。

但是,它不起作用。如果模板存在,则在堆栈/控制台中引发异常,但不会传播到get_template(..)(从该语句内部),因此不会传播到我愚蠢的API。因此,在渲染过程中,这在我的脸上爆炸了。我将堆栈跟踪上传到pastebin

这是 Django 想要的行为吗?

我最终停止做愚蠢的事情。但我的问题仍然存在。

4

2 回答 2

2

自定义标签呢?这没有提供完整的功能,include但似乎满足了问题中的需求。:

@register.simple_tag(takes_context=True)
def include_fallback(context, *template_choices):
    t = django.template.loader.select_template(template_choices)
    return t.render(context)

然后在您的模板中:

{% include_fallback "profile/header.html" "common/header.html" %}
于 2013-02-06T21:57:59.627 回答
1

我找到了对我的问题的某种答案,因此我将其发布在这里以供将来参考。

如果我像这样使用我的 template_exists 过滤器

{% if 'profile/header.html'|template_exists %}        
  {% include 'profile/header.html' %}
{% else %}
  {% include 'common/header.html' %}
{% endif %}

如果profile/header.html不存在,则 TemplateDoesNotExist 在页面加载时会奇怪地传播,并且我收到服务器错误。但是,如果相反,我在模板中使用它:

{% with 'profile/header.html' as var_templ %}
  {% if var_templ|template_exists %}
    {% include var_templ %}
  {% else %}
    {% include 'common/header.html' %}
  {% endif %}
{% endwith %}

然后,它就像一个魅力!

显然,我可以使用

django.template.loader.select_template(['profile/header.html','common/header.html']) 

在视图中(来自this SO answer)。但是我正在使用一个 CBV,我想保持它相当通用,它是从主模板中调用的。而且我认为如果这个应用程序由于某种原因出现故障,让我的网站正常运行会很好。如果这对您来说似乎很愚蠢,请发表评论(或更好的答案)。

于 2013-02-06T15:31:55.880 回答