tilt 0.7 → 1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/COPYING CHANGED
@@ -1,4 +1,4 @@
1
- Copyright (c) 2009 Ryan Tomayko <http://tomayko.com/about>
1
+ Copyright (c) 2010 Ryan Tomayko <http://tomayko.com/about>
2
2
 
3
3
  Permission is hereby granted, free of charge, to any person obtaining a copy
4
4
  of this software and associated documentation files (the "Software"), to
data/README.md CHANGED
@@ -13,7 +13,8 @@ feature is relevant to the engine):
13
13
  * Ability to pass locals to template evaluation
14
14
  * Support for passing a block to template evaluation for "yield"
15
15
  * Backtraces with correct filenames and line numbers
16
- * Template compilation caching and reloading
16
+ * Template file caching and reloading
17
+ * Fast, method-based template source compilation
17
18
 
18
19
  The primary goal is to get all of the things listed above right for all
19
20
  template engines included in the distribution.
@@ -29,9 +30,10 @@ Support for these template engines is included with the package:
29
30
  Less CSS .less less
30
31
  Builder .builder builder
31
32
  Liquid .liquid liquid
32
- Mustache .mustache mustache
33
33
  RDiscount .markdown rdiscount
34
34
  RedCloth .textile redcloth
35
+ RDoc .rdoc rdoc
36
+ Radius .radius radius
35
37
 
36
38
  See [TEMPLATES.md][t] for detailed information on template engine
37
39
  options and supported features.
@@ -145,8 +147,49 @@ Or, use BlueCloth for markdown instead of RDiscount:
145
147
 
146
148
  Tilt.register 'markdown', Tilt::BlueClothTemplate
147
149
 
150
+ Template Compilation
151
+ --------------------
152
+
153
+ Tilt can compile generated Ruby source code produced by template engines and
154
+ reuse on subsequent template invocations. Benchmarks show this yields a 5x-10x
155
+ performance increase over evaluating the Ruby source on each invocation.
156
+
157
+ Template compilation is currently supported for these template engines:
158
+ StringTemplate, ERB, Erubis, Haml, and Builder.
159
+
160
+ To enable template compilation, the `Tilt::CompileSite` module must be mixed in
161
+ to the scope object passed to the template's `#render` method. This can be
162
+ accomplished by including (with `Module#include`) the module in the class used
163
+ for scope objects or by extending (with `Object#extend`) scope objects before
164
+ passing to `Template#render`:
165
+
166
+ require 'tilt'
167
+
168
+ template = Tilt::ERBTemplate.new('foo.erb')
169
+
170
+ # Slow. Uses Object#instance_eval to process template
171
+ class Scope
172
+ end
173
+ scope = Scope.new
174
+ template.render(scope)
175
+
176
+ # Fast. Uses compiled template and Object#send to process template
177
+ class Scope
178
+ include Tilt::CompileSite
179
+ end
180
+ scope = Scope.new
181
+ template.render(scope)
182
+
183
+ # Also fast, though a bit a slower due to having to extend each time
184
+ scope = Object.new
185
+ scope.extend Tilt::CompileSite
186
+ template.render(scope)
187
+
188
+ When the `Tilt::CompileSite` module is not present, template execution falls
189
+ back to evaluating the template from source on each invocation.
190
+
148
191
  LICENSE
149
192
  -------
150
193
 
151
- Tilt is Copyright (c) 2009 [Ryan Tomayko](http://tomayko.com/about) and
152
- distributed under the MIT license. See the COPYING file for more info.
194
+ Tilt is Copyright (c) 2010 [Ryan Tomayko](http://tomayko.com/about) and
195
+ distributed under the MIT license. See the `COPYING` file for more info.
data/Rakefile CHANGED
@@ -11,11 +11,17 @@ end
11
11
  desc 'Run tests (default)'
12
12
  Rake::TestTask.new(:test) do |t|
13
13
  t.test_files = FileList['test/*_test.rb']
14
- t.ruby_opts = ['-rubygems'] if defined? Gem
14
+ t.ruby_opts = ['-Itest']
15
+ t.ruby_opts << '-rubygems' if defined? Gem
15
16
  end
16
17
 
17
18
  # PACKAGING =================================================================
18
19
 
20
+ begin
21
+ require 'rubygems'
22
+ rescue LoadError
23
+ end
24
+
19
25
  if defined?(Gem)
20
26
  SPEC = eval(File.read('tilt.gemspec'))
21
27
 
@@ -72,26 +78,3 @@ file 'tilt.gemspec' => FileList['{lib,test}/**','Rakefile'] do |f|
72
78
  File.open(f.name, 'w') { |io| io.write(spec) }
73
79
  puts "updated #{f.name}"
74
80
  end
75
-
76
- # DOC =======================================================================
77
-
78
- # requires the hanna gem:
79
- # gem install mislav-hanna --source=http://gems.github.com
80
- desc 'Build API documentation (doc/api)'
81
- task 'rdoc' => 'rdoc/index.html'
82
- file 'rdoc/index.html' => FileList['lib/**/*.rb'] do |f|
83
- rm_rf 'rdoc'
84
- sh((<<-SH).gsub(/[\s\n]+/, ' ').strip)
85
- hanna
86
- --op doc/api
87
- --promiscuous
88
- --charset utf8
89
- --fmt html
90
- --inline-source
91
- --line-numbers
92
- --accessor option_accessor=RW
93
- --main Tilt
94
- --title 'Tilt API Documentation'
95
- #{f.prerequisites.join(' ')}
96
- SH
97
- end
data/TEMPLATES.md CHANGED
@@ -9,7 +9,6 @@ documentation on each supported template engine is provided below.
9
9
  * [Erubis](#erubis) - `Tilt::ErubisTemplate`
10
10
  * [Haml](#haml) - `Tilt::HamlTemplate`
11
11
  * [Liquid](#liquid) - `Tilt::LiquidTemplate`
12
- * [Mustache](#mustache) - `Tilt::MustachTemplate`
13
12
 
14
13
  Tilt includes support for CSS processors like [lesscss](http://lesscss.org)
15
14
  and [sass](http://sass-lang.com/), in addition, it also supports simple
@@ -94,15 +93,16 @@ the extensions as follows:
94
93
 
95
94
  ### Options
96
95
 
97
- #### `:trim => true`
98
-
99
- Delete spaces around '<% %>'. (But, spaces around '<%= %>' are preserved.)
96
+ #### `:engine_class => Erubis::Eruby`
100
97
 
101
- #### `:pattern => '<% %>'`
98
+ Allows you to specify a custom engine class to use instead of the
99
+ default which is `Erubis::Eruby`.
102
100
 
103
- Set pattern for embedded Ruby code.
101
+ #### `:escape_html => false`
104
102
 
105
- See the [ERB](#erb) template documentation for examples, usage, and options.
103
+ When `true`, `Erubis::EscapedEruby` will be used as the engine class
104
+ instead of the default. All content within `<%= %>` blocks will be
105
+ automatically html escaped.
106
106
 
107
107
  #### `:outvar => '_erbout'`
108
108
 
@@ -110,6 +110,16 @@ The name of the variable used to accumulate template output. This can be
110
110
  any valid Ruby expression but must be assignable. By default a local
111
111
  variable named `_erbout` is used.
112
112
 
113
+ #### `:pattern => '<% %>'`
114
+
115
+ Set pattern for embedded Ruby code.
116
+
117
+ See the [ERB](#erb) template documentation for examples, usage, and options.
118
+
119
+ #### `:trim => true`
120
+
121
+ Delete spaces around '<% %>'. (But, spaces around '<%= %>' are preserved.)
122
+
113
123
  ### See also
114
124
 
115
125
  * [Erubis Home](http://www.kuwata-lab.com/erubis/)
@@ -293,53 +303,6 @@ time when using this template engine within a threaded environment.
293
303
  * [Liquid Docs](http://liquid.rubyforge.org/)
294
304
  * GitHub: [tobi/liquid](http://github.com/tobi/liquid/)
295
305
 
296
- <a name='mustache'></a>
297
- Mustache (`mustache`)
298
- ---------------------
299
-
300
- Mustache is a framework-agnostic way to render logic-free views.
301
-
302
- __NOTE:__ It's suggested that your program `require 'mustache'` at load time
303
- when using this template engine in a threaded environment.
304
-
305
- ### Options
306
-
307
- #### `:path => Dir.pwd`
308
-
309
- The base path where mustache templates (`.html` files) are located. Defaults to
310
- the current working directory.
311
-
312
- #### `:template_extension => 'html'`
313
-
314
- The file extension used on mustache templates. Default is `'html'`.
315
-
316
- #### `:namespace => Object`
317
-
318
- The class or module where View classes are located. If you have
319
- `Hurl::App::Views`, namespace should be `Hurl:App`. This defaults to `Object`,
320
- causing `::Views` to be searched for classes.
321
-
322
- #### `:mustaches => nil` or `:view_path => nil`
323
-
324
- Where mustache views (`.rb` files) are located, or `nil` to disable auto-requiring
325
- of views based on template names. By default, the view file is assumed to be in
326
- the same directory as the template file.
327
-
328
- All other options are assumed to be attribute writer's on the Mustache
329
- class and are set when a template is compiled. They are:
330
-
331
- #### `:view => nil`
332
-
333
- The Mustache subclass that should be used a the view. When this option is
334
- specified, the template file will be determined from the view class, and the
335
- `:namespace` and `:mustaches` options are irrelevant.
336
-
337
- ### See also
338
-
339
- * [Mustache Docs](http://defunkt.github.com/mustache/)
340
- * GitHub: [defunkt/mustache](http://github.com/defunkt/mustache)
341
-
342
-
343
306
  <a name='markdown'></a>
344
307
  Markdown (`markdown`, `md`, `mkd`)
345
308
  ----------------------------------
@@ -421,3 +384,56 @@ engine in a threaded environment.
421
384
  ### See also
422
385
 
423
386
  * [RDoc](http://rdoc.sourceforge.net/doc/index.html)
387
+
388
+
389
+ <a name='radius'></a>
390
+ Radius (`radius`)
391
+ -----------------
392
+
393
+ Radius is the template language used by Radiant CMS. It is a tag
394
+ language designed to be valid XML/HTML.
395
+
396
+ ### Example
397
+
398
+ <html>
399
+ <body>
400
+ <h1><r:title /></h1>
401
+ <ul class="<r:type />">
402
+ <r:repeat times="3">
403
+ <li><r:hello />!</li>
404
+ </r:repeat>
405
+ </ul>
406
+ <r:yield />
407
+ </body>
408
+ </html>
409
+
410
+ ### Usage
411
+
412
+ To render a template such as the one above.
413
+
414
+ scope = OpenStruct.new
415
+ scope.title = "Radius Example"
416
+ scope.hello = "Hello, World!"
417
+
418
+ require 'radius'
419
+ template = Tilt::RadiusTemplate.new('example.radius', :tag_prefix=>'r')
420
+ template.render(scope, :type=>'hlist'){ "Jackpot!" }
421
+
422
+ The result will be:
423
+
424
+ <html>
425
+ <body>
426
+ <h1>Radius Example</h1>
427
+ <ul class="hlist">
428
+ <li>Hello, World!</li>
429
+ <li>Hello, World!</li>
430
+ <li>Hello, World!</li>
431
+ </ul>
432
+ Jackpot!
433
+ </body>
434
+ </html>
435
+
436
+ ### See also
437
+
438
+ * [Radius](http://radius.rubyforge.org/)
439
+ * [Radiant](http://radiantcms.org/)
data/bin/tilt CHANGED
@@ -3,17 +3,21 @@ require 'ostruct'
3
3
  require 'optparse'
4
4
  require 'tilt'
5
5
 
6
- usage = <<EOF
7
- Usage: tilt [OPTIONS] [FILE]
8
- Process template FILE and generate output. With no FILE or when FILE
9
- is '-', read template from stdin and use the --type option to determine
10
- the template's type.
6
+ usage = <<USAGE
7
+ Usage: tilt <options> <file>
8
+ Process template <file> and write output to stdout. With no <file> or
9
+ when <file> is '-', read template from stdin and use the --type option
10
+ to determine the template's type.
11
11
 
12
12
  Options
13
- -l, --list List supported template engines + file patterns and exit.
14
- -t, --type=PATTERN Use this template engine; required when FILE is stdin.
13
+ -l, --list List template engines + file patterns and exit
14
+ -t, --type=<pattern> Use this template engine; required if no <file>
15
+ -y, --layout=<file> Use <file> as a layout template
15
16
 
16
- -h, --help Show this help message.
17
+ -D<name>=<value> Define variable <name> as <value>
18
+ -o, --vars=<ruby> Evaluate <ruby> to Hash and use for variables
19
+
20
+ -h, --help Show this help message
17
21
 
18
22
  Convert markdown to HTML:
19
23
  $ tilt foo.markdown > foo.html
@@ -21,11 +25,18 @@ Convert markdown to HTML:
21
25
  Process ERB template:
22
26
  $ echo "Answer: <%= 2 + 2 %>" | tilt -t erb
23
27
  Answer: 4
24
- EOF
28
+
29
+ Define variables:
30
+ $ echo "Answer: <%= 2 + n %>" | tilt --locals="{:n=>40, :x=>0}"
31
+ Answer: 42
32
+ $ echo "Answer: <%= 2 + n %>" | tilt -Dn=40 -Dx=0
33
+ Answer: 42
34
+ USAGE
25
35
 
26
36
  script_name = File.basename($0)
27
37
  pattern = nil
28
38
  layout = nil
39
+ locals = {}
29
40
 
30
41
  ARGV.options do |o|
31
42
  o.program_name = script_name
@@ -44,18 +55,31 @@ ARGV.options do |o|
44
55
  end
45
56
 
46
57
  # the template type / pattern
47
- o.on("-t", "--type=PATTERN") do |val|
48
- fail "unknown template type: #{val}" if Tilt[val].nil?
58
+ o.on("-t", "--type=PATTERN", String) do |val|
59
+ abort "unknown template type: #{val}" if Tilt[val].nil?
49
60
  pattern = val
50
61
  end
51
62
 
52
63
  # pass template output into the specified layout template
53
- o.on("-y", "--layout=FILE") do |file|
64
+ o.on("-y", "--layout=FILE", String) do |file|
54
65
  paths = [file, "~/.tilt/#{file}", "/etc/tilt/#{file}"]
55
66
  layout = paths.
56
67
  map { |p| File.expand_path(p) }.
57
68
  find { |p| File.exist?(p) }
58
- fail "no such layout: #{file}" if layout.nil?
69
+ abort "no such layout: #{file}" if layout.nil?
70
+ end
71
+
72
+ # define a local variable
73
+ o.on("-D", "--define=PAIR", String) do |pair|
74
+ key, value = pair.split(/[=:]/, 2)
75
+ locals[key.to_sym] = value
76
+ end
77
+
78
+ # define local variables using a Ruby hash
79
+ o.on("--vars=RUBY") do |ruby|
80
+ hash = eval(ruby)
81
+ abort "vars must be a Hash, not #{hash.inspect}" if !hash.is_a?(Hash)
82
+ hash.each { |key, value| locals[key.to_sym] = value }
59
83
  end
60
84
 
61
85
  o.on_tail("-h", "--help") { puts usage; exit }
@@ -65,17 +89,22 @@ end
65
89
 
66
90
  file = ARGV.first || '-'
67
91
  pattern = file if pattern.nil?
92
+ abort "template type not given. see: #{$0} --help" if ['-', ''].include?(pattern)
93
+
94
+ engine = Tilt[pattern]
95
+ abort "template engine not found for: #{pattern}" if engine.nil?
96
+
68
97
  template =
69
- Tilt[pattern].new(file) {
98
+ engine.new(file) {
70
99
  if file == '-'
71
100
  $stdin.read
72
101
  else
73
102
  File.read(file)
74
103
  end
75
104
  }
76
- output = template.render
105
+ output = template.render(self, locals)
77
106
 
78
107
  # process layout
79
- output = Tilt.new(layout).render { output } if layout
108
+ output = Tilt.new(layout).render(self, locals) { output } if layout
80
109
 
81
110
  $stdout.write(output)