【问题标题】:Can an object tell Twig not to escape output when it is {{ printed }}对象可以告诉 Twig 在 {{ 打印 }} 时不要转义输出吗
【发布时间】:2016-09-10 21:03:17
【问题描述】:

我遇到了这样一种情况,即发送到我的 Twig 模板的一些变量是普通的旧变量,所以我希望它们是 html 转义的(这是默认行为)。但是发送到我的模板的其他变量实际上是带有 __toString() 渲染器的对象......其中一些对象发送原始 HTML(例如,来自 TinyMCE 或 CKEditor 等所见即所得编辑器)。

理想情况下,我希望我的模板设计者不必对对象使用 |raw 过滤器,而是让对象以某种方式告诉 Twig 它们已经被转义。

换句话说,我试图模仿设置is_safe 的 Twig 函数的行为,但不需要模板设计者使用函数。

例如我可以在其定义中使用 is_safe 参数编写一个 Twig 函数,并且可以在我的模板中使用它:

{{ figure_out_what_to_do(something) }}

figure_out_what_to_do 知道检查“某物”对象以确定它是否需要转义)。但对我来说,这并不比记住在“某物”的每次输出后加上|raw 更好。因此,我希望能够做到这一点:

{{ something }}

...让 Twig 识别出 something 是一个对象,因此询问它是否需要转义。

我猜答案是“不”,但我想我会问一下,以防更了解 Twig 内部结构的人对我有任何指点。

谢谢。

【问题讨论】:

    标签: twig


    【解决方案1】:

    __toString() 方法中,您可以执行以下操作而不是返回 html 输出:return new Twig_Markup($html, 'UTF-8'); 从而将其标记为安全且不可转义

    【讨论】:

    • 这正是我想要的——谢谢! (希望这已经在某个地方的文档中)。仅供参考,我不能在__toString() 中使用它,因为 PHP 只允许从中返回实际的字符串(而不是对象)。但我可以使用其他一些方法来解决这个问题(比如拥有一个带有魔术__get 方法的包装器对象,twig 会调用它,它可以决定是返回字符串还是返回 Twig_Markup 对象)。
    • @JordanLev,你搞定了吗?如果是这样,你能告诉,如何?
    【解决方案2】:

    您可以扩展\Twig_Markup,而不是在__toString() 中返回一个新的\Twig_Markup 对象(这会导致致命错误,因为它必须返回一个字符串):

    class Something extends \Twig_Markup {
      public function __toString() {
        return $this->safeValue;
      }
      public function count() {
        return mb_strlen($this->safeValue);
      }
    }
    

    在决定是否转义字符串时,Twig 会查看对象以查看它是否是 \Twig_Markup 的实例。这是\Twig_Markup的来源:

    
    /*
     * This file is part of Twig.
     *
     * (c) Fabien Potencier
     *
     * For the full copyright and license information, please view the LICENSE
     * file that was distributed with this source code.
     */
    
    namespace Twig;
    
    /**
     * Marks a content as safe.
     *
     * @author Fabien Potencier <fabien@symfony.com>
     */
    class Markup implements \Countable
    {
        protected $content;
        protected $charset;
    
        public function __construct($content, $charset)
        {
            $this->content = (string) $content;
            $this->charset = $charset;
        }
    
        public function __toString()
        {
            return $this->content;
        }
    
        public function count()
        {
            return \function_exists('mb_get_info') ? mb_strlen($this->content, $this->charset) : \strlen($this->content);
        }
    }
    
    class_alias('Twig\Markup', 'Twig_Markup');
    

    正如您在源代码中看到的,\Twig_Markup 实现了\Countable。这就是为什么我在示例中覆盖了 public function count() 的实现。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2019-03-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-25
      • 1970-01-01
      相关资源
      最近更新 更多