From d6ad2d3c6ee63fc8493b47e4f4b82e1804bfac5f Mon Sep 17 00:00:00 2001 From: Jesse Luehrs Date: Fri, 5 Oct 2012 11:48:54 -0500 Subject: support {{@index}} --- lib/Text/Xslate/Syntax/Handlebars.pm | 41 ++++++++++++++++++++++++++++++------ t/blocks.t | 14 ++++++++++++ 2 files changed, 48 insertions(+), 7 deletions(-) diff --git a/lib/Text/Xslate/Syntax/Handlebars.pm b/lib/Text/Xslate/Syntax/Handlebars.pm index 85dc0a0..ee4639c 100644 --- a/lib/Text/Xslate/Syntax/Handlebars.pm +++ b/lib/Text/Xslate/Syntax/Handlebars.pm @@ -14,7 +14,7 @@ my $nl = qr/\x0d?\x0a/; my $bracket_string = qr/\[ [^\]]* \]/xms; my $STRING = qr/(?: $Text::Xslate::Util::STRING | $bracket_string )/xms; -my $single_char = '[.#^/>&;]'; +my $single_char = '[.#^/>&;@]'; my $OPERATOR_TOKEN = sprintf( "(?:%s|$single_char)", join('|', map{ quotemeta } qw(..)) @@ -242,6 +242,8 @@ sub init_symbols { $self->prefix('&', 0)->set_nud($self->can('nud_mark_raw')); $self->prefix('..', 0)->set_nud($self->can('nud_uplevel')); + + $self->prefix('@', 0)->set_nud($self->can('nud_iterator')); } # copied from Text::Xslate::Parser, but using different definitions of @@ -491,7 +493,7 @@ sub std_block { ), )); - my $loop_var = $self->symbol('(variable)')->clone(id => '(block)'); + my $loop_var = $self->symbol('(block)')->clone(arity => 'variable'); my $body_block = [ $symbol->clone( @@ -503,11 +505,7 @@ sub std_block { '(new_vars_for)', $self->vars, $name->clone, - $self->symbol('(iterator)')->clone( - arity => 'iterator', - id => '$~(block)', - first => $loop_var, - ), + $self->iterator_index, ), ]) ), @@ -573,6 +571,25 @@ sub std_partial { ); } +sub nud_iterator { + my $self = shift; + my ($symbol) = @_; + + my $token = $self->token; + if ($token->arity ne 'variable') { + $self->_unexpected('iterator variable', $token); + } + + $self->advance; + + if ($token->id eq 'index') { + return $self->iterator_index; + } + else { + $self->_error("Unknown iterator variable " . $token->id); + } +} + sub undefined_name { my $self = shift; my ($name) = @_; @@ -675,6 +692,16 @@ sub vars { return $self->symbol('(vars)')->clone(arity => 'vars'); } +sub iterator_index { + my $self = shift; + + return $self->symbol('(iterator)')->clone( + arity => 'iterator', + id => '$~(block)', + first => $self->symbol('(block)'), + ), +} + sub _field_to_string { my $self = shift; my ($symbol) = @_; diff --git a/t/blocks.t b/t/blocks.t index 7cc68fe..8b44e9d 100644 --- a/t/blocks.t +++ b/t/blocks.t @@ -47,4 +47,18 @@ render_ok( "nested array of hashes block variable" ); +render_ok( + '{{#goodbyes}}{{@index}}. {{text}}! {{/goodbyes}}cruel {{world}}!', + { + goodbyes => [ + { text => 'goodbye' }, + { text => 'Goodbye' }, + { text => 'GOODBYE' }, + ], + world => 'world', + }, + '0. goodbye! 1. Goodbye! 2. GOODBYE! cruel world!', + "\@index variable" +); + done_testing; -- cgit v1.2.3