如何在 Django 模板中执行此操作

发布于 2024-11-02 19:21:25 字数 571 浏览 3 评论 0 原文

现在这将是一个有点奇怪的用例。也许有人有一些想法。

背景

我正在编写一个 AJAX 密集型网站。事实上,几乎没有任何整页重新加载。这意味着许多模板组合是在客户端完成的。目前我使用一些自己编写的 jQuery 脚本。为了使事情相当简单,我只使用变量占位符,如下所示:{{ somevar.someattr.someotherattr }}。我可能可以使用小胡子之类的东西来实现类似的行为。

另一方面,我有时喜欢能够在服务器端进行一些组合。我正在寻找一种方法来避免客户端和客户端上无意义的代码重复。服务器端。

想法

我希望能够以这样的方式呈现 Django 模板,使得输出中的某些间隙保持不变。更具体地说,如果模板渲染上下文中未提供给定变量,则占位符仍应读取 {{contents}}。我想知道使用过滤器和/或标签是否可以实现这种或类似的行为。

我可以只写 {{ somevar.someattr|default:"{{ somevar.someattr }}" }},但这不是很干燥。

Now this is going to be a little weird use-case. Maybe someone has some ideas.

Background

I'm writing a website that is very AJAX intensive. In fact there are hardly any full page reloads. This implies that a lot of template composition is done on the client side. For the moment I use some self written scripts in jQuery. To keep things reasonably simple I only use variable placeholders, like this: {{ somevar.someattr.someotherattr }}. I could probably use something like mustache to achieve a similar behaviour.

On the other hand, from time to time I like to be able to do some composition on the server side. I'm looking for a way to avoid pointless code duplication on the client & server side.

Idea

I'd like to be able to render Django templates in such a way, that certain gaps in the output would remain untouched. More specifically if a given variable is not supplied in the template rendering context, then the placeholder should still read {{ contents }}. I wonder whether this or a similar behaviour is possible to achieve using filters and/or tags.

I could just write {{ somevar.someattr|default:"{{ somevar.someattr }}" }}, however this isn't very DRY.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

晚雾 2024-11-09 19:21:25

我不知道 Django,但也许值得一看的是 javaScriptMVC: http://javascriptmvc.com/

I do not know Django but something that maybe worth a look at is javaScriptMVC: http://javascriptmvc.com/

野鹿林 2024-11-09 19:21:25

这就是我最后想到的:

代码:

from django import template

register = template.Library()

@register.filter(name='tmpl')
def tmpl_filter(value, arg=None):
    return value or ("{{ %s }}" % arg)

@register.tag(name='tmpl')
def tmpl_tag(parser, token):
    nodelist = parser.parse(('endtmpl',))
    parser.delete_first_token()
    return UpperNode(nodelist)

class UpperNode(template.Node):
    def __init__(self, nodelist):
        super(UpperNode, self).__init__()
        self.nodelist = nodelist
        nodes = self.get_nodes_by_type(template.VariableNode)
        for n in nodes:
            v = n.filter_expression.var
            if v.lookups:
                for i, f in enumerate(n.filter_expression.filters):
                    print f
                    if f[0] == tmpl_filter and len(f[1]) == 0:
                        n.filter_expression.filters[i] = \
                            (f[0], [(False, '.'.join(v.lookups))],)

    def render(self, context):
        return self.nodelist.render(context)

用法:

{% load placeholders %}
{% tmpl %}
    {{ var.for.template|tmpl }}
    {{ regular.var }}
    {% nestedtag %}
        {{ another.var.for.template|tmpl }}
    {% endnestedtag %}
{% endtmpl %}

这是一种黑客行为,但不会造成实际麻烦。我也认为它是线程安全的,但尚未在这方面进行测试。

That's what I came up with in the end:

Code:

from django import template

register = template.Library()

@register.filter(name='tmpl')
def tmpl_filter(value, arg=None):
    return value or ("{{ %s }}" % arg)

@register.tag(name='tmpl')
def tmpl_tag(parser, token):
    nodelist = parser.parse(('endtmpl',))
    parser.delete_first_token()
    return UpperNode(nodelist)

class UpperNode(template.Node):
    def __init__(self, nodelist):
        super(UpperNode, self).__init__()
        self.nodelist = nodelist
        nodes = self.get_nodes_by_type(template.VariableNode)
        for n in nodes:
            v = n.filter_expression.var
            if v.lookups:
                for i, f in enumerate(n.filter_expression.filters):
                    print f
                    if f[0] == tmpl_filter and len(f[1]) == 0:
                        n.filter_expression.filters[i] = \
                            (f[0], [(False, '.'.join(v.lookups))],)

    def render(self, context):
        return self.nodelist.render(context)

Usage:

{% load placeholders %}
{% tmpl %}
    {{ var.for.template|tmpl }}
    {{ regular.var }}
    {% nestedtag %}
        {{ another.var.for.template|tmpl }}
    {% endnestedtag %}
{% endtmpl %}

It's a hack, but not such a big one to cause actual trouble. Also I think it's thread-safe, however haven't tested it in that regard.

温馨耳语 2024-11-09 19:21:25

这就是我与 Django + ICanHaz.js 一起使用的内容。这样您就可以使用过滤器或标签:
http://tothinkornottothink.com/post/4282971041/using -jquery-templated-icanhaz-js-with-django

This is what I use with Django + ICanHaz.js. With this you can use filter or tags:
http://tothinkornottothink.com/post/4282971041/using-jquery-templating-icanhaz-js-with-django

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文