NAME

Text::Xslate::PP::Booster - Text::Xslate code generator to build Perl code

SYNOPSIS

# If you want to check created codes, you can use it directly.
use Text::Xslate::PP;
use Text::Xslate::PP::Booster;

my $tx      = Text::Xslate->new();
my $booster = Text::Xslate::PP::Booster->new();

my $optext  = q{<: $value :>};
my $code    = $booster->opcode_to_perlcode_string( $tx->_compiler->compile( $optext ) );
my $coderef = $booster->opcode_to_perlcode( $tx->_compiler->compile( $optext ) );
# $coderef takes a Text::Xslate::PP::State object

DESCRIPTION

This module is a new Text::Xslate::PP runtime engine.

The old Text::Xslate::PP is very very slow, you know. Example:

> XSLATE=pp perl benchmark/others.pl
Text::Xslate/0.1019
Text::MicroTemplate/0.11
Text::ClearSilver/0.10.5.4
Template/2.22
...
         Rate xslate     tt     mt     cs
xslate  119/s     --   -58%   -84%   -95%
tt      285/s   139%     --   -61%   -88%
mt      725/s   507%   154%     --   -69%
cs     2311/s  1835%   711%   219%     --

All right, slower than template-toolkit! But now you get Text::Xslate::PP::Booster, which is as fast as Text::MicroTemplate:

> XSLATE=pp perl benchmark/others.pl
Text::Xslate/0.1024
...
         Rate     tt     mt xslate     cs
tt      288/s     --   -60%   -62%   -86%
mt      710/s   147%     --    -5%   -66%
xslate  749/s   160%     5%     --   -65%
cs     2112/s   634%   197%   182%     --

Text::Xslate::PP becomes to be faster!

APIs

new

Constructor.

$booster = Text::Xslate::PP::Booster->new();

opcode_to_perlcode

Takes a virtual machine code created by Text::Xslate::Compiler, and returns a code reference.

$coderef = $booster->opcode_to_perlcode( $ops );

The code reference takes Text::Xslate::PP::State object in Xslate runtime processes. Don't execute this code reference directly.

opcode_to_perlcode_string

Takes a virtual machine code created by Text::Xslate::Compiler, and returns a perl subroutine code text.

$str = $booster->opcode_to_perlcode_string( $ops );

ABOUT BOOST CODE

Text::Xslate::PP::Booster creates a code reference from a virtual machine code.

$tx->render_string( <<'CODE', {} );
: macro foo -> $arg {
    Hello <:= $arg :>!
: }
: foo($value)
CODE

Firstly the template data is converted to opcodes:

pushmark
fetch_s "value"
push
macro "foo"
macrocall
print
end
macro_begin "foo"
print_raw_s "    Hello "
fetch_lvar 0
print
print_raw_s "!\n"
macro_end

And the booster converted them into a perl subroutine code.

sub { no warnings 'recursion';
    my ( $st ) = $_[0];
    my ( $sv, $st2, $pad, %macro, $depth );
    my $output = '';
    my $vars   = $st->{ vars };

    $pad = [ [ ] ];

    # macro

    $macro{'foo'} = $st->{ booster_macro }->{'foo'} ||= sub {
        my ( $st, $pad ) = @_;
        my $vars = $st->{ vars };
        my $output = '';

        Carp::croak('Macro call is too deep (> 100) at "foo"') if ++$depth > 100;

        $output .= "        Hello ";

        $sv = $pad->[ -1 ]->[ 0 ];

        if ( Scalar::Util::blessed( $sv ) and $sv->isa('Text::Xslate::EscapedString') ) {
            $output .= $sv;
        }
        elsif ( defined $sv ) {
            $sv =~ s/($html_unsafe_chars)/$html_escape{$1}/xmsgeo;
            $output .= $sv;
        }
        else {
            warn_in_booster( $st, 'foo', 10, "Use of nil to be printed" );
        }

        $output .= "!\n";

        $depth--;
        pop( @$pad );

        $output;
    };


    # process start

    $output .= $macro{'foo'}->( $st, push_pad( $pad, [ $vars->{ "value" } ] ) );

    # process end

    $st->{ output } = $output;
}

So it makes the runtime speed much faster. Of course, its initial converting process takes a little cost of CPU and time.

SEE ALSO

Text::Xslate::PP

AUTHOR

Makamaka Hannyaharamitu <makamaka at cpan.org>

LICENSE AND COPYRIGHT

Copyright (c) 2010 by Makamaka Hannyaharamitu (makamaka).

This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself.