Class: Arrow::Template::ForDirective

Inherits:
BracketingDirective show all
Includes:
Parser::Patterns
Defined in:
lib/arrow/template/for.rb

Overview

The Arrow::Template::ForDirective class, a derivative of Arrow::Template::BracketingDirective. This is the class which defines the behaviour of the ‘for’ template directive.

Syntax

  <?for <arglist> in <obj>?>...<?end for?>

This directive iterates over all the items in an Enumerable object (via the #entities method), rendering the contents once for each object. The specified #arglist is similar to Ruby’s argument lists: it supports defaults, as well as array (e.g., *rest) and hash arguments.

While the contents are rendering, a special attribute named iterator is set to an Arrow::Template::Iterator object, which can be used to get information about the iteration itself. This directive doesn’t add anything to the output directly, but relies on its subnodes for content.

This directive only works with Enumerable objects; for other objects with iterators or blocks, use the directive.

Examples

 <!-- Iterate over the headers in a request -->
 <?for name, value in request.headers_in ?>
   <strong><?attr name?>:</strong> <?attr value?><br/>
 <?end for?>

 <!-- Same thing, but this time in a table with alternating styles for each
      row. -->
 <table>
 <?for name, value in request.headers_in ?>
 <?if iterator.even? ?>
   <tr class="even-row">
 <?else?>
   <tr class="odd-row">
 <?end if?>
     <td><?attr name?></td> <td><?attr value?></td>
   </tr>
 <?end for?>
 </table>

 <!-- Pair up words with their lengths and sort them shortest first, then
      print them out with their lengths -->
 <?for word, length in tests.
       collect {|item| [item, item.length]}.
       sort_by {|item| item[1]} ?>
  <?attr word?>: <?attr length?>
 <?end for?>

Authors

  • Michael Granger

Please see the file LICENSE in the top-level directory for licensing details.

Constant Summary

IN =

The regexp for matching the ‘in’ part of the directive

WHITESPACE + /in/i + WHITESPACE

Constants included from Parser::Patterns

ALTERNATION, ARGDEFAULT, ARGUMENT, CAPTURE, COMMA, DBLQSTRING, DOT, EQUALS, IDENTIFIER, INFIX, LBRACKET, NUMBER, PATHNAME, QUOTEDSTRING, RBRACKET, REBINDOP, REGEXP, SLASHQSTRING, SYMBOL, TAGCLOSE, TAGMIDDLE, TAGOPEN, TICKQSTRING, VARIABLE, WHITESPACE

Constants inherited from BracketingDirective

SVNId, SVNRev

Constants inherited from AttributeDirective

SVNId, SVNRev

Constants inherited from Directive

SVNId, SVNRev

Constants inherited from Node

SVNId, SVNRev

Constants included from Arrow::HTMLUtilities

ARRAY_HTML_CONTAINER, HASH_HTML_CONTAINER, HASH_PAIR_HTML, IMMEDIATE_OBJECT_HTML_CONTAINER, IVAR_HTML_FRAGMENT, OBJECT_HTML_CONTAINER, THREAD_DUMP_KEY

Instance Attribute Summary

Instance Method Summary

Methods inherited from BracketingDirective

#add_to_template, #inspect, #is_rendering_node?, #render_contents, #to_a, #to_html

Methods inherited from AttributeDirective

allows_format?, #before_rendering, #build_rendering_proc, #call_methodchain, #inspect, #is_rendering_node?, #render, #render_contents, #to_html

Methods inherited from Directive

create, derivativeDirs, #inspect, #render, #to_html

Methods inherited from Node

#add_to_template, #css_class, #inspect, #is_rendering_node?, #render, #to_a, #to_html, #to_s

Methods included from Arrow::HTMLUtilities

#escape_html, #make_html_for_object, #make_object_html_wrapper

Methods inherited from Arrow::Object

deprecate_class_method, deprecate_method, inherited

Methods included from Arrow::Loggable

#log

Constructor Details

- (ForDirective) initialize(body, parser, state)

Create a new Arrow::Template::ForDirective object.



77
78
79
80
81
# File 'lib/arrow/template/for.rb', line 77

def initialize( body, parser, state )
  @args = []
  @pureargs = []
  super
end

Instance Attribute Details

- (Object) args (readonly)

The argument list for the iterator, with sigils and defaults, if any.



89
90
91
# File 'lib/arrow/template/for.rb', line 89

def args
  @args
end

- (Object) pureargs (readonly)

The argument list for the iterator, with any sigils and defaults stripped away.



93
94
95
# File 'lib/arrow/template/for.rb', line 93

def pureargs
  @pureargs
end

Instance Method Details

- (Object) parse_directive_contents(parser, state) (protected)

Parse the contents of the directive.



101
102
103
104
105
106
107
108
109
# File 'lib/arrow/template/for.rb', line 101

def parse_directive_contents( parser, state )
  @args, @pureargs = parser.scan_for_arglist( state )
  return nil unless @args

  state.scanner.skip( IN ) or
    raise Arrow::ParseError, "no 'in' for 'for'"

  super
end

- (Object) render_subnodes(attribute, template, scope) (protected)

Render the directive’s bracketed nodes once for each item in the iterated content.



114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
# File 'lib/arrow/template/for.rb', line 114

def render_subnodes( attribute, template, scope )
  res = []

  iterator = Arrow::Template::Iterator.new( attribute )
  iterator.each {|iter,*blockArgs|
    #self.log.debug "[FOR] Block args are: %p" % [ blockArgs ]

    # Make an attributes hash from the pure args of left side of the
    # 'for'.
    attributes = {}
    blockArgs.zip( self.pureargs ) {|pair|
      attributes[ pair[1] ] = pair[0]
    }
    attributes['iterator'] = iter

    # Process the nodes inside the 'for' block with the args being
    # overridden.
    #self.log.debug "  [FOR] calling into new scope with overridden " +
    #  "attributes: %p" % [ attributes ]
    template.with_overridden_attributes( scope, attributes ) {|template|
      res << template.render( @subnodes, scope )
    }
  }

  return *res
end