如何在Template Toolkit中删除变量?

时间:2011-09-29 10:06:56

标签: perl template-toolkit

查看Template Toolkit手册的Template::Manual::VMethods部分,我没有看到任何方法这样做。同时将undef分配给变量也不起作用 - variable.defined在事实之后返回true。

2 个答案:

答案 0 :(得分:2)

好吧,谷歌搜索"delete variable" site:mail.template-toolkit.org/pipermail/templates/带来了来自费利佩加斯珀的[Templates] Can I “DELETE some_var”?问题,并得到了Petr Danihlik的两个答案。彼得建议:

[% SET foo = 1 %]
[% IF foo.defined %] defined1 [% END %]
[% PERL %]
delete($stash->{foo});
[% END %]
[% IF foo.defined %] defined2 [% END %]

答案 1 :(得分:2)

我查看了Catalyst::View:TT code,以了解变量上下文。

以下子程序,我总结了一点点渲染工作:

sub render {
    my ( $self, $c, $template, $args ) = @_;
    # [...]
    my $output;    # Template rendering will end here
    # Variables interpolated by TT process() are passed inside an hashref
    # as copies.
    my $vars = {
        ( ref $args eq 'HASH' ? %$args : %{ $c->stash() } ),
        $self->template_vars( $c )
    };
    # [...]
    unless ( $self->template->process( $template, $vars, \$output ) ) { 
        # [ ... ]
    }
    # [ ... ]
    return $output;
}

使用process()中的变量副本调用TT $c->stash,那么为什么我们需要弄乱$c->stash来删除本地副本?也许我们没有。

此外,TT define() VMethod与其他方法一样,似乎是为列表构建的。当对它们调用VMethod时,标量会自动提升为单个元素列表:可能由于这个原因,IF测试总是返回true。

我使用带有DBIx::Class::ResultSet个对象引用的变量进行了一些测试,这似乎在测试变量时有效:

[%- resultset_rs = undef %]
[%- IF ( resultset_rs ) %]
    <h3>defined</h3>
[%- END %]

第一行删除变量,第二行进行适当的测试。

<强>更新

如果您可以在Catalyst视图中添加EVAL_PERL => 1标记,请在config()个论坛内,

__PACKAGE__->config({
    # ...
    EVAL_PERL => 1
});

然后您可以在模板中使用[% RAWPERL %]指令,这样您就可以直接访问Template::Context对象:然后您可以删除变量并.defined() VMethod做正确的事。

[%- RAWPERL %]
    delete $context->stash->{ 'resultset_rs' };
[%- END %]
[%- IF ( resultset_rs.defined ) %]
    <h3>defined: [% resultset_rs %]<h3>
[%- ELSE %]
    <h3>undefined: [% resultset_rs %]<h3>
[%- END %]