如何不转义替换文本?

How to not escape replacement text?

我有一个模板:

<blockquote>
    <p>{{ message|replace({"\r\n\r\n":'</p><p>', "\r\r":'</p><p>', "\n\n":'</p><p>'}) }}</p>
</blockquote>

有了这个输入

Woop-de-doo\r\nLa-dee-da\r\n\r\nFoo van der Bar\r\n\r\nMojo<script>alert('Test');</script>

它呈现如下:

Woop-de-doo La-dee-da</p><p>Foo van der Bar</p><p>Mojo<script>alert('Test');</script>

好吧,真遗憾,我希望我的替代品 HTML 能够呈现。如果你在最后打一个 |raw,它会起作用:

Woop-de-doo La-dee-da

Foo van der Bar

Mojo

除了它还运行来自输入文本的(潜在危险的)脚本,我显然不想发生这种情况。

如何让 Twig 按字面意思使用我的替换文本,但仍保持输入文本转义?

您尝试过使用 php 方法 nl2br 吗? http://php.net/manual/en/function.nl2br.php

您可以将其用作树枝过滤器

http://twig.sensiolabs.org/doc/filters/nl2br.html

{{ "I like Twig.\nYou will like it too."|nl2br }}

如果你特别想要你描述的转换并且你希望它做一个预转义然后在 html 中渲染你将不得不编写你自己的过滤器

为此让我们看看 nl2br 是如何实现的

https://github.com/twigphp/Twig/blob/11f9ebe8b6fb4d18d02591c4a042d1cab94b72eb/lib/Twig/Extension/Core.php#L172

 new Twig_SimpleFilter(
   'nl2br',
   'nl2br',
   array('pre_escape' => 'html', 'is_safe' => array('html'))
 )

所以现在为了编写您自己的扩展,您可以按照本教程进行操作

http://symfony.com/doc/current/cookbook/templating/twig_extension.html

class AppExtension extends \Twig_Extension
{
    public function getFilters()
    {
        return array(
            new \Twig_SimpleFilter(
                'doubleline2paragraph',
                array($this, 'doubleLine2Paragraph'),
                array('pre_escape' => 'html', 'is_safe' => array('html'))
            ),
        );
    }

    public function doubleLine2Paragraph($text)
    {
        // your transformation

        return $text;
    }

    public function getName()
    {
        return 'app_extension';
    }
}

然后注册它(如上文 link 中所述)以便您可以使用它

 {{ "your text" | doubleline2paragraph }}