Звоните из ссылки на код в Template Toolkit - PullRequest
0 голосов
/ 27 августа 2018

У меня есть простая функция высшего порядка, которая создает форматер сообщений.

use strict;
use warnings;

sub make_formatter {
    my $level = shift;
    return sub {
        my $message = shift;
        return "[$level] $message";
    }
}

Я использую его из Perl так:

my $component_formatter = make_formatter('ComponentError');
print $component_formatter->('Hello') . "\n";

Я хочу использовать make_formatterиз шаблона Template Toolkit.Я попытался сделать следующее:

use Template;
use Template::Constants;

my $template = Template->new({
#   DEBUG => Template::Constants::DEBUG_ALL,
    VARIABLES => {
        make_formatter => make_formatter,
    }
});

my $template_str = "
[% my_formatter = make_formatter('MyFormatter') %]
<h1>[% my_formatter('Sample message') %]</h1>
";

$template->process(\$template_str);

Вывод этого сценария:

$ perl test.pl 
Use of uninitialized value $level in concatenation (.) or string at test.pl line 10.


<h1>[] MyFormatter</h1>

Можно ли вызвать my_formatter, используя только синтаксис Template Toolkit?Вызов внешнего Perl-кода, который по умолчанию не вызывается из Template Toolkit, не возможен.

1 Ответ

0 голосов
/ 28 августа 2018

Прежде всего позвольте мне отметить, что настоятельно рекомендуется помещать use strict; use warnings; в начало вашего скрипта.

Если вы сделаете это для своего фрагмента, генерирующего шаблон $, вы получите ошибку Bareword "make_formatter" not allowed while "strict subs" in use, который должен помочь вам определить, что это бесполезная запись.

Теперь, если вы вместо этого вызовете make_formatter(), это выдаст <h1>[] MyFormatter</h1>.Это имеет смысл: ваша функция вернула подпрограмму, которая вызывается с помощью 'MyFormatter' в вашем шаблоне (а $ level равен undef, как вы вызывали make_formatter без ввода).

Как указал г-н Хегланд,

my $template = Template->new({
VARIABLES => {
    make_formatter => \&make_formatter,
}
});

приводит к выводу, который, как я понимаю, вам нужен:

<h1>[MyFormatter] Sample message</h1>

\ & make_formatter дает вам ссылку на подпрограмму, которую в perl обычно можно вызывать с помощью: my $ref = \&make_formatter; $ref->( 'Input' );

Это можно затем вызвать в первой строке вашего шаблона, возвращая другой код ref, который затем вызывается во второй строке.

Надеюсь, это поможет!

...