jinja2中的变量词法分析器突出显示

时间:2017-01-22 15:52:42

标签: python-3.x jinja2 pygments

我的jinja2模板收到一个代码块,其中可能包含任意数量的不同语言。我想将正确的词法分析器传递给模板并使用jinja2-highlight插件(pygments)进行相应的渲染。 我使用'命令'渲染我的模板。变量,它是一个字典,包含模板其余部分所需的所有数据。理想情况下,我想在这些方面做点什么

{% highlight "{{ command.lexer }}", lineno='table' %}{{ command.script }}{% endhighlight %}

我试过了:

{% highlight command.lexer, lineno='table' %}
{% highlight 'command.lexer', lineno='table' %}
{% highlight '{{ command.lexer }}', lineno='table' %}

甚至

{% set lexer = command.lexer %}
{% highlight 'lexer', lineno='table' %}
{% highlight '{{ lexer }}', lineno='table' %}

我似乎无法弄清楚jinja2和jinja2-highlight / pygments之间渲染规则的组合。

我真的不喜欢这样的事情:

{% if command.lexer == 'bash' %}
{% highlight 'bash', lineno='table' %}
{% elif command.lexer == 'perl' %}
{% highlight 'perl', lineno='table' %}
...
{% endif %}

这似乎与jinja2解析器类有关,但我有点卡住......感觉就像我忽略了一些微不足道的事情。

各种错误消息都看起来像:

jinja2.exceptions.TemplateSyntaxError: expected token 'end of statement block', got ','

2 个答案:

答案 0 :(得分:0)

不幸的是,使用当前的插件似乎不可能。没有递归jinja语法,插件解析的方式似乎没有很好地处理任何变量输入。我联系了作者,没有回复,浏览了插件的源代码后,似乎可能但是现在不值得花时间进行必要的修改,所以...

{% if command.lexer == 'bash' %}
{% highlight 'bash', lineno='table' %}
{% elif command.lexer == 'perl' %}
{% highlight 'perl', lineno='table' %}
...
{% endif %}

..它是。

答案 1 :(得分:0)

您是否尝试使用自定义过滤器,请参阅http://jinja.pocoo.org/docs/2.10/api/#custom-filters? (此提案不会使用 jinja2-highlight 扩展程序,但仅 pygments

filters.py文件中的

(必要时创建)

# highlight Filter
from pygments import highlight
from pygments import lexers
from pygments.formatters import HtmlFormatter

lexers_dict = dict()
html_formatter = HtmlFormatter()

def do_highlight(content, language):    
    lexers_dict.setdefault(language,lexers.get_lexer_by_name(language))

    return highlight(content, lexers_dict[language], html_formatter)


def init_app(app):
    """Initialize a Flask application with custom filters."""    
    app.jinja_env.filters['light'] = do_highlight

在模板文件(.html)

<div class="content">{{ command.script | light(command.lexer) | safe }}</div>
应用程序文件(app.py)中的

from my_app import filters
filters.init_app(app)