【问题标题】:How are django templates parsed?django模板是如何解析的?
【发布时间】:2012-01-03 10:47:07
【问题描述】:

我一直在尝试更多地了解 Django 的模板引擎,因为它对我来说总是有点像一个黑盒子。 The documentation 很好地概述了所涉及的一般步骤,并指示模板已加载和解析,创建一个节点树,这些节点在上下文中呈现(以级联形式?)并附加在一起以给出结果。

我不明白的是解析方法,以及创建节点的标准是什么?解析后由什么构成特定节点,以及这如何影响自定义模板标签的创建(即是否有更好、更有效的方法来编写模板标签,从而减少节点?)。

【问题讨论】:

  • 我开始阅读django.template.base,但当我感觉到强大的时间弯曲魔法(比如早上 5 点)时就出去了。我会在早上投票并检查:)

标签: django django-templates


【解决方案1】:

了解更多有关该过程的一种方法是使用werkzeug debugger 运行django,并在模板中触发异常。这样一来,您就可以查看(并与之交互)整个堆栈。

【讨论】:

    【解决方案2】:

    从每个标签中创建一个节点。通过阅读how to write custom tags,您可以了解它是如何工作的。标签内的任何东西都是它的孩子。以下是 django 文档中的注释标签示例:

    def do_comment(parser, token):
        nodelist = parser.parse(('endcomment',))
        parser.delete_first_token()
        return CommentNode()
    

    如您所见,注释标记将解析所有内容,直到“结束注释”并将其丢弃。其他标签会将nodelist 传递给SometagNode() 并将其用于渲染。

    渲染是递归完成的。当在节点上调用 render() 时,它会在其子节点上运行渲染,依此类推。

    解析也是递归完成的,这就是为什么你可以获得嵌套标签,parser.parse() 将设法找到正确匹配的结束标签,因为当它解析并偶然发现一个标签时,它会调用 do_tag() 事物,其中turn 将再次调用parser.parse() 以找到最近的结束标记并将所有内容包装到一个节点中,返回一个节点,更高的 parser.parse() 将其放在节点列表中并继续搜索结束标记。

    节点中的上下文对象是一种字典结构的列表。额外的上下文被推送到现有上下文之上并传递给子节点并在节点渲染后弹出,这样它就不会影响上层范围。

    对于没有子标签的标签,parser.parse() 不被使用,因此节点实例返回时没有任何子标签。

    【讨论】:

      【解决方案3】:

      我认为您应该首先查看的是code.djangoproject.com 使用 django/template/base.py - 第一个(如 Yuji Tomita 之前所说)。或者下载源代码并使用您最喜欢的编辑器或 IDE 浏览它。

      【讨论】:

        【解决方案4】:

        我猜他们使用标记化和解析

        一个简单的描述方法是:

        标记化: 将代码拆分为以下类型:

        integer foo = "bar" + 15;
        

        这包括

        T_VARIABLETYPE  + T_VARIABLENAME  + T_EQUALS + T_STRING + T_PLUS + T_DIGIT + T_SEMI
        

        在此之后,您可以尝试使用解析器查找模式来解析

        解析:

        找到模式:

        T_VARIABLETYPE  + T_VARIABLENAME  + T_EQUALS + {A recursive thing} + T_SEMI
        

        这样就可以执行命令了

        如果你想尝试这个我可以推荐使用“ANTLR”http://www.antlr.org/ 它支持多种不同的语言,例如 Java 或 C#,甚至 PHP 和 JS

        【讨论】:

          猜你喜欢
          • 2013-03-31
          • 1970-01-01
          • 2011-07-04
          • 1970-01-01
          • 2014-07-20
          • 2015-05-05
          • 2014-02-11
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多