检查自定义 Twig 函数是否存在,然后调用它

2023-12-10

我测试是否存在自定义 Twig 函数:

{% if methodExist('sg_datatables_render') %}
    {{ sg_datatables_render(datatable) }}
 {% else %}
    {{ datatable_render((datatable)) }}
{% endif %}

methodExist是一个简单的Twig_Function:

 /**
 * @param $name
 * @return bool
 */
public function methodExist($name){

    if($this->container->get('twig')->getFunction($name)){
        return true;
    }else{
        return false;
    }
}

但我得到一个例外:

Unknown "sg_datatables_render" function. Did you mean "datatable_render"?
500 Internal Server Error - Twig_Error_Syntax

我试图复制这个,事实上,{{ sg_datatables_render(datatable) }}似乎总是会导致Twig_Error_Syntax异常时sg_datatables_render尚未注册为 Twig 函数。

然后我尝试了这样的事情。它很难看,但我想知道它是否有效。这个想法是,将创建一个不存在的函数来避免抛出异常:

$twig->addFunction(new Twig_Function('methodExist', function(Twig_Environment $twig, $name) {
    $hasFunction = $twig->getFunction($name) !== false;

    if (!$hasFunction) {
        // The callback function defaults to null so I have omitted it here
        return $twig->addFunction(new Twig_Function($name));
    }

    return $hasFunction;
}, ['needs_environment' => true]));

但这没有用。我还尝试向新函数添加一个简单的回调函数,但没有成功。

我用过滤器尝试了同样的技巧,即:

{% if filterExists('sg_datatables_render') %}
    {{ datatable|sg_datatables_render }}
 {% else %}
    {{ datatable|datatable_render }}
{% endif %}

它也不起作用。


解决方案一:{{ renderDatatable(datatable) }}

像这样的东西确实有效(耶!):

$twig->addFunction(new Twig_Function('renderDatatable', function(Twig_Environment $twig, $datatable) {
    $sgFunction = $twig->getFunction('sg_datatables_render');

    if ($sgFunction !== false) {
        return $sgFunction->getCallable()($datatable);
    }

    return $twig->getFunction('datatable_render')->getCallable()($datatable);
}, ['needs_environment' => true]));

然后在树枝中:

{{ renderDatatable(datatable) }}

The renderDatatable函数特定于渲染数据表,即它不是像您的那样的通用/多用途函数methodExist是,但它有效。您当然可以尝试自己创建一个更通用的实现。


解决方案2:{{ fn('sg_datatables_render', datatable) }}

这是一个更通用的方法。创建一个额外的 Twig 函数来配合methodExist:

$twig->addFunction(new Twig_Function('fn', function(Twig_Environment $twig, $name, ...$args) {
     $fn = $twig->getFunction($name);

     if ($fn === false) {
         return null;
     }

     // You could add some kind of error handling here
     return $fn->getCallable()(...$args);
 }, ['needs_environment' => true]));

然后你可以将原始代码修改为:

{% if methodExist('sg_datatables_render') %}
    {{ fn('sg_datatables_render', datatable) }}
 {% else %}
    {{ datatable_render((datatable)) }}
{% endif %}

或者甚至使用三元运算符:

{{ methodExist('sg_datatables_render') ? fn('sg_datatables_render', datatable) : datatable_render(datatable) }}

PS

这是我的写法methodExist功能:

$twig->addFunction(new Twig_Function('methodExists', function(Twig_Environment $twig, $name) {
     return $twig->getFunction($name) !== false;
 }, ['needs_environment' => true]));
  1. I added s到函数名称的末尾,因为该函数检查方法/函数是否存在s.
  2. I added ['needs_environment' => true]所以我可以用$twig代替$this->container->get('twig')。 (感谢 yceruto 的建议。)
  3. getFunction回报false如果该函数不存在(请参阅文档),所以我将函数体简化为单行返回语句。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

检查自定义 Twig 函数是否存在,然后调用它 的相关文章

随机推荐