erubis-bmp 2.7.0.bmp

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.
Files changed (78) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGES.txt +828 -0
  3. data/MIT-LICENSE +20 -0
  4. data/README.txt +10 -0
  5. data/benchmark/bench.rb +313 -0
  6. data/benchmark/bench_context.yaml +141 -0
  7. data/benchmark/mybench2.rb +266 -0
  8. data/benchmark/pibench.rb +163 -0
  9. data/benchmark/templates/_footer.html +4 -0
  10. data/benchmark/templates/_header.html +52 -0
  11. data/benchmark/templates/bench_erb.rhtml +29 -0
  12. data/benchmark/templates/bench_erubis.rhtml +29 -0
  13. data/benchmark/templates/bench_eruby.rhtml +29 -0
  14. data/bin/erubis +10 -0
  15. data/contrib/erubis-run.rb +132 -0
  16. data/doc/Rookbook.yaml +106 -0
  17. data/doc/docstyle.css +209 -0
  18. data/doc/users-guide.html +3551 -0
  19. data/doc/users-guide.txt +3631 -0
  20. data/examples/basic/Makefile +58 -0
  21. data/examples/basic/example.ec +42 -0
  22. data/examples/basic/example.ecpp +33 -0
  23. data/examples/basic/example.ejava +45 -0
  24. data/examples/basic/example.ejs +16 -0
  25. data/examples/basic/example.eperl +16 -0
  26. data/examples/basic/example.ephp +17 -0
  27. data/examples/basic/example.eruby +15 -0
  28. data/examples/basic/example.escheme +26 -0
  29. data/examples/pi-xhtml/ExamplePage.xhtml +80 -0
  30. data/examples/pi-xhtml/Makefile +17 -0
  31. data/examples/pi-xhtml/my/User.java +19 -0
  32. data/examples/pi-xhtml/my/Util.java +54 -0
  33. data/examples/pi/Makefile +54 -0
  34. data/examples/pi/example.ec +42 -0
  35. data/examples/pi/example.ejava +45 -0
  36. data/examples/pi/example.ejs +16 -0
  37. data/examples/pi/example.eperl +16 -0
  38. data/examples/pi/example.ephp +17 -0
  39. data/examples/pi/example.eruby +15 -0
  40. data/examples/pi/example.escheme +26 -0
  41. data/lib/erubis.rb +73 -0
  42. data/lib/erubis/context.rb +83 -0
  43. data/lib/erubis/converter.rb +357 -0
  44. data/lib/erubis/engine.rb +120 -0
  45. data/lib/erubis/engine/ec.rb +117 -0
  46. data/lib/erubis/engine/ecpp.rb +113 -0
  47. data/lib/erubis/engine/ejava.rb +110 -0
  48. data/lib/erubis/engine/ejavascript.rb +119 -0
  49. data/lib/erubis/engine/enhanced.rb +126 -0
  50. data/lib/erubis/engine/eperl.rb +95 -0
  51. data/lib/erubis/engine/ephp.rb +99 -0
  52. data/lib/erubis/engine/eruby.rb +125 -0
  53. data/lib/erubis/engine/escheme.rb +114 -0
  54. data/lib/erubis/engine/optimized.rb +127 -0
  55. data/lib/erubis/enhancer.rb +723 -0
  56. data/lib/erubis/error.rb +23 -0
  57. data/lib/erubis/evaluator.rb +88 -0
  58. data/lib/erubis/generator.rb +85 -0
  59. data/lib/erubis/helper.rb +47 -0
  60. data/lib/erubis/helpers/rails_form_helper.rb +197 -0
  61. data/lib/erubis/helpers/rails_helper.rb +353 -0
  62. data/lib/erubis/local-setting.rb +9 -0
  63. data/lib/erubis/main.rb +516 -0
  64. data/lib/erubis/preprocessing.rb +58 -0
  65. data/lib/erubis/tiny.rb +144 -0
  66. data/lib/erubis/util.rb +22 -0
  67. data/setup.rb +1331 -0
  68. data/test/Rookbook.yaml +42 -0
  69. data/test/assert-text-equal.rb +44 -0
  70. data/test/test-engines.rb +425 -0
  71. data/test/test-enhancers.rb +646 -0
  72. data/test/test-erubis.rb +887 -0
  73. data/test/test-index-cgi.rb +191 -0
  74. data/test/test-main.rb +752 -0
  75. data/test/test-users-guide.rb +73 -0
  76. data/test/test.rb +45 -0
  77. data/test/testutil.rb +111 -0
  78. metadata +121 -0
@@ -0,0 +1,3631 @@
1
+ .=title: Erubis Users' Guide
2
+ .#.?version: $Release$
3
+ .#.?release: $Release$
4
+ .#.?lastupdate: $Date$
5
+ .?stylesheet: docstyle.css
6
+
7
+ release: $Release$
8
+
9
+
10
+
11
+ .$ Preface | preface*
12
+
13
+ Erubis is an implementation of eRuby.
14
+ It has the following features.
15
+ .* Very fast, almost three times faster than ERB and about ten percent faster than eruby (implemented in C)
16
+ .* File caching of converted Ruby script support
17
+ .* Auto escaping support
18
+ .* Auto trimming spaces around '<% %>'
19
+ .* Embedded pattern changeable (default '<% %>')
20
+ .* Enable to handle Processing Instructions (PI) as embedded pattern (ex. '<?rb ... ?>')
21
+ .* Multi-language support (Ruby/PHP/C/Java/Scheme/Perl/Javascript)
22
+ .* Context object available and easy to combine eRuby template with YAML datafile
23
+ .* Print statement available
24
+ .* Easy to expand and customize in subclass
25
+ .* {{<Ruby on Rails support|#rails>}}
26
+ .* mod_ruby support|#topcs-modruby
27
+ .#.* {{<Very fast|#topics-benchmark>}}, almost three times faster than ERB and about ten percent faster than eruby (implemented in C)
28
+ .#.* {{<File caching of converted Ruby script support|#topics-caching>}}
29
+ .#.* {{<Auto escaping support|#tut-escape>}}
30
+ .#.* {{<Auto trimming spaces around '<% %>'|#tut-trim>}}
31
+ .#.* {{<Embedded pattern changeable|#tut-pattern>}} (default '<% %>')
32
+ .#.* {{<Enable to handle Processing Instructions (PI) as embedded pattern|#tut-pi>}} (ex. '<?rb ... ?>')
33
+ .#.* {{<Multi-language support|#lang>}} (Ruby/PHP/C/Java/Scheme/Perl/Javascript)
34
+ .#.* {{<Context object available|#tut-context>}} and {{<easy to combine eRuby template with YAML datafile|#tut-datafile>}}
35
+ .#.* {{<Print statement available|#printenabled-enhancer>}}
36
+ .#.* {{<Easy to expand and customize in subclass|#enhancer>}}
37
+ .#.* {{<Ruby on Rails support|#topics-rails>}}
38
+ .#.* {{<mod_ruby support|#topcs-modruby>}}
39
+
40
+ Erubis is implemented in pure Ruby. It requires Ruby 1.8 or higher.
41
+ Erubis now supports Ruby 1.9.
42
+
43
+
44
+
45
+ .$$ Table of Contents | toc*
46
+
47
+ .<<< users-guide.toc
48
+
49
+
50
+
51
+ .$ Installation | install
52
+
53
+ .* If you have installed RubyGems, just type {{,gem install --remote erubis,}}.
54
+ .====================
55
+ $ sudo gem install --remote erubis
56
+ .====================
57
+
58
+ .* Else install {{<abstract|http://rubyforge.org/projects/erubis/>}} at first,
59
+ and download erubis_X.X.X.tar.bz2 and install it by setup.rb.
60
+ .====================
61
+ $ tar xjf abstract_X.X.X.tar.bz2
62
+ $ cd abstract_X.X.X/
63
+ $ sudo ruby setup.rb
64
+ $ cd ..
65
+ $ tar xjf erubis_X.X.X.tar.bz2
66
+ $ cd erubis_X.X.X/
67
+ $ sudo ruby setup.rb
68
+ .====================
69
+
70
+ .#.* Or if you can be root user, download erubis_X.X.X.tar.bz2 and install by setup.rb.
71
+ .# .====================
72
+ .# $ tar xjf erubis-X.X.X.tar.bz2
73
+ .# $ cd erubis_X.X.X/
74
+ .# $ ruby setup.rb
75
+ .# .#$ ruby setup.rb config
76
+ .# .#$ ruby setup.rb setup
77
+ .# .#$ sudo ruby setup.rb install
78
+ .# .====================
79
+ .#
80
+ .#.* Else you should copy 'lib/erubis.rb', 'lib/erubis/', and 'bin/erubis' into proper directory manually.
81
+ .# .====================
82
+ .# $ tar xjf erubis-X.X.X.tar.bz2
83
+ .# $ cd erubis_X.X.X/
84
+ .# $ cp -r lib/erubis.rb lib/erubis /usr/local/lib/ruby/site_ruby/1.8
85
+ .# $ cp bin/erubis /usr/local/bin
86
+ .# .====================
87
+
88
+ .* (Optional) 'contrib/inline-require' enables you to merge 'lib/**/*.rb' into 'bin/erubis'.
89
+ .====================
90
+ $ tar xjf erubis_X.X.X.tar.bz2
91
+ $ cd erubis_X.X.X/
92
+ $ unset RUBYLIB
93
+ $ contrib/inline-require -I lib bin/erubis > contrib/erubis
94
+ .====================
95
+
96
+
97
+
98
+ .$ Tutorial | tutorial
99
+
100
+
101
+
102
+ .$$ Basic Example | tut-basic
103
+
104
+ Here is a basic example of Erubis.
105
+
106
+ .? example1.eruby
107
+ .-------------------- example1.eruby
108
+ <ul>
109
+ {{*<% for item in list %>*}}
110
+ <li>{{*<%= item %>*}}</li>
111
+ {{*<% end %>*}}
112
+ {{*<%# here is ignored because starting with '#' %>*}}
113
+ </ul>
114
+ .--------------------
115
+
116
+ .? example1.rb
117
+ .-------------------- example1.rb
118
+ require 'erubis'
119
+ input = File.read('example1.eruby')
120
+ eruby = {{*Erubis::Eruby.new(input)*}} # create Eruby object
121
+
122
+ puts "---------- script source ---"
123
+ puts {{*eruby.src*}} # print script source
124
+
125
+ puts "---------- result ----------"
126
+ list = ['aaa', 'bbb', 'ccc']
127
+ puts {{*eruby.result(binding())*}} # get result
128
+ ## or puts eruby.result({{*:list=>list*}}) # or pass Hash instead of Binding
129
+
130
+ ## # or
131
+ ## eruby = Erubis::Eruby.new
132
+ ## input = File.read('example1.eruby')
133
+ ## src = eruby.convert(input)
134
+ ## eval src
135
+ .--------------------
136
+
137
+ .? output
138
+ .==================== example1.result
139
+ $ ruby example1.rb
140
+ .#.<<<:! (cd guide.d; ruby example1.rb)
141
+ ---------- script source ---
142
+ _buf = ''; _buf << '<ul>
143
+ '; for item in list
144
+ _buf << ' <li>'; _buf << ( item ).to_s; _buf << '</li>
145
+ '; end
146
+
147
+ _buf << '</ul>
148
+ ';
149
+ _buf.to_s
150
+ ---------- result ----------
151
+ <ul>
152
+ <li>aaa</li>
153
+ <li>bbb</li>
154
+ <li>ccc</li>
155
+ </ul>
156
+ .====================
157
+
158
+ Erubis has command 'erubis'. Command-line option '-x' shows the compiled source code of eRuby script.
159
+
160
+ .? example of command-line option '-x'
161
+ .==================== example1_x.result
162
+ $ erubis {{*-x*}} example1.eruby
163
+ .#.<<<:! (cd guide.d; erubis -x example1.eruby)
164
+ _buf = ''; _buf << '<ul>
165
+ '; for item in list
166
+ _buf << ' <li>'; _buf << ( item ).to_s; _buf << '</li>
167
+ '; end
168
+
169
+ _buf << '</ul>
170
+ ';
171
+ _buf.to_s
172
+ .====================
173
+
174
+
175
+
176
+ .$$ Trimming Spaces | tut-trim
177
+
178
+ Erubis deletes spaces around '<% %>' automatically, while it leaves spaces around '<%= %>'.
179
+
180
+ .? example2.eruby
181
+ .-------------------- example2.eruby.comment_filter
182
+ <ul>
183
+ <% for item in list %> # trimmed
184
+ <li>
185
+ <%= item %> # not trimmed
186
+ </li>
187
+ <% end %> # trimmed
188
+ </ul>
189
+ .--------------------
190
+
191
+ .? compiled source code
192
+ .==================== example2_x.result
193
+ $ erubis -x example2.eruby
194
+ .#.<<<:! (ruby -pi.bak -e 'sub! /\s*\#.*$/, ""' guide.d/example2.eruby; erubis -x guide.d/example2.eruby)
195
+ _buf = ''; _buf << '<ul>
196
+ '; for item in list
197
+ _buf << ' <li>
198
+ '; _buf << ( item ).to_s; _buf << '
199
+ '; _buf << ' </li>
200
+ '; end
201
+ _buf << '</ul>
202
+ ';
203
+ _buf.to_s
204
+ .====================
205
+
206
+ If you want leave spaces around '<% %>', add command-line property '--trim=false'.
207
+
208
+ .? compiled source code with command-line property '--trim=false'
209
+ .==================== example2_trim.result
210
+ $ erubis -x {{*--trim=false*}} example2.eruby
211
+ .#.<<<:! erubis -x --trim=false guide.d/example2.eruby
212
+ _buf = ''; _buf << '<ul>
213
+ '; _buf << ' '; for item in list ; _buf << '
214
+ '; _buf << ' <li>
215
+ '; _buf << ( item ).to_s; _buf << '
216
+ '; _buf << ' </li>
217
+ '; _buf << ' '; end ; _buf << '
218
+ '; _buf << '</ul>
219
+ ';
220
+ _buf.to_s
221
+ .====================
222
+
223
+ Or add option {{,:trim=>false,}} to Erubis::Eruby.new().
224
+
225
+ .? example2.rb
226
+ .-------------------- example2.rb
227
+ require 'erubis'
228
+ input = File.read('example2.eruby')
229
+ eruby = Erubis::Eruby.new(input{{*, :trim=>false*}})
230
+
231
+ puts "----- script source ---"
232
+ puts eruby.src # print script source
233
+
234
+ puts "----- result ----------"
235
+ list = ['aaa', 'bbb', 'ccc']
236
+ puts eruby.result(binding()) # get result
237
+ .--------------------
238
+
239
+ .? output
240
+ .==================== example2.result
241
+ $ ruby example2.rb
242
+ .#.<<<:! (cd guide.d; ruby example2.rb)
243
+ ----- script source ---
244
+ _buf = ''; _buf << '<ul>
245
+ '; {{*_buf << ' ';*}} for item in list ; _buf << '
246
+ '; _buf << ' <li>
247
+ '; _buf << ( item ).to_s; _buf << '
248
+ '; _buf << ' </li>
249
+ '; {{*_buf << ' ';*}} end ; _buf << '
250
+ '; _buf << '</ul>
251
+ ';
252
+ _buf.to_s
253
+ ----- result ----------
254
+ <ul>
255
+
256
+ <li>
257
+ aaa
258
+ </li>
259
+
260
+ <li>
261
+ bbb
262
+ </li>
263
+
264
+ <li>
265
+ ccc
266
+ </li>
267
+
268
+ </ul>
269
+ .====================
270
+
271
+
272
+
273
+ .$$ Escape | tut-escape
274
+
275
+ Erubis has ability to escape (sanitize) expression.
276
+ Erubis::Eruby class act as the following:
277
+ .* {{,<%= {{/expr/}} %>,}} - not escaped.
278
+ .* {{,<%== {{/expr/}} %>,}} - escaped.
279
+ .* {{,<%=== {{/expr/}} %>,}} - out to $stderr.
280
+ .* {{,<%==== {{/expr/}} %>,}} - ignored.
281
+
282
+ Erubis::EscapedEruby{{(Erubis::EscapedEruby class includes Erubis::EscapeEnhancer which swtches the action of '<%= %>' and '<%== %>'.)}} class handle '<%= %>' as escaped and '<%== %>' as not escaped.
283
+ It means that using Erubis::EscapedEruby you can escape expression by default.
284
+ Also Erubis::XmlEruby class (which is equivalent to Erubis::EscapedEruby) is provided for compatibility with Erubis 1.1.
285
+
286
+ .? example3.eruby
287
+ .-------------------- example3.eruby
288
+ <% for item in list %>
289
+ <p>{{*<%=*}} item {{*%>*}}</p>
290
+ <p>{{*<%==*}} item {{*%>*}}</p>
291
+ <p>{{*<%===*}} item {{*%>*}}</p>
292
+
293
+ <% end %>
294
+ .--------------------
295
+
296
+ .? example3.rb
297
+ .-------------------- example3.rb
298
+ require 'erubis'
299
+ input = File.read('example3.eruby')
300
+ eruby = Erubis::{{*EscapedEruby*}}.new(input) # or Erubis::XmlEruby
301
+
302
+ puts "----- script source ---"
303
+ puts eruby.src # print script source
304
+
305
+ puts "----- result ----------"
306
+ {{*list = ['<aaa>', 'b&b', '"ccc"']*}}
307
+ puts eruby.result(binding()) # get result
308
+ .--------------------
309
+
310
+ .? output
311
+ .==================== example3.result.split_filter
312
+ $ ruby example3.rb 2> stderr.log
313
+ .#.<<<:! (cd guide.d; ruby example3.rb 2> stderr.log) | ruby -pe 'sub! /_buf << [E(].*?;|\$stderr.*?;/, "{{*\\&*}}"'
314
+ ----- script source ---
315
+ _buf = ''; for item in list
316
+ _buf << ' <p>'; {{*_buf << Erubis::XmlHelper.escape_xml( item )*}}; _buf << '</p>
317
+ <p>'; {{*_buf << ( item ).to_s*}}; _buf << '</p>
318
+ <p>'; {{*$stderr.puts("*** debug: item=#{(item).inspect}")*}}; _buf << '</p>
319
+
320
+ '; end
321
+ _buf.to_s
322
+ ----- result ----------
323
+ <p>{{*&lt;aaa&gt;*}}</p>
324
+ <p><aaa></p>
325
+ <p></p>
326
+
327
+ <p>{{*b&amp;b*}}</p>
328
+ <p>b&b</p>
329
+ <p></p>
330
+
331
+ <p>{{*&quot;ccc&quot;*}}</p>
332
+ <p>"ccc"</p>
333
+ <p></p>
334
+
335
+ $ cat stderr.log
336
+ .#.<<<: guide.d/stderr.log
337
+ *** debug: item="<aaa>"
338
+ *** debug: item="b&b"
339
+ *** debug: item="\"ccc\""
340
+ .====================
341
+
342
+ The command-line option '-e' will do the same action as Erubis::EscapedEruby.
343
+ This option is available for any language.
344
+ .#{{(Command-line option '-e' is equivarent to '-E Escape'.)}}
345
+
346
+ .==================== example3_e.result
347
+ $ erubis -l ruby {{*-e*}} example3.eruby
348
+ .#.<<<:! (cd guide.d; erubis -e -l ruby example3.eruby)
349
+ _buf = ''; for item in list
350
+ _buf << ' <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
351
+ <p>'; _buf << ( item ).to_s; _buf << '</p>
352
+ <p>'; $stderr.puts("*** debug: item=#{(item).inspect}"); _buf << '</p>
353
+
354
+ '; end
355
+ _buf.to_s
356
+ .====================
357
+
358
+ Escaping function (default 'Erubis::XmlHelper.escape_xml()') can be changed by command-line property '--escapefunc=xxx' or by overriding Erubis::Eruby#escaped_expr() in subclass.
359
+
360
+ .? example to override Erubis::Eruby#escaped_expr()
361
+ .--------------------
362
+ class CGIEruby < Erubis::Eruby
363
+ def {{*escaped_expr(code)*}}
364
+ return "CGI.escapeHTML((#{code.strip}).to_s)"
365
+ #return "h(#{code.strip})"
366
+ end
367
+ end
368
+
369
+ class LatexEruby < Erubi::Eruby
370
+ def {{*escaped_expr(code)*}}
371
+ return "(#{code}).gsub(/[%\\]/,'\\\\\&')"
372
+ end
373
+ end
374
+ .--------------------
375
+
376
+
377
+
378
+ .$$ Embedded Pattern | tut-pattern
379
+
380
+ You can change embedded pattern '{{,<% %>,}}' to another by command-line option '-p' or option '{{,:pattern=>...,}}' of Erubis::Eruby.new().
381
+
382
+ .? example4.eruby
383
+ .-------------------- example4.eruby
384
+ {{*<!--%*}} for item in list {{*%-->*}}
385
+ <p>{{*<!--%=*}} item {{*%-->*}}</p>
386
+ {{*<!--%*}} end {{*%-->*}}
387
+ .--------------------
388
+
389
+ .? compiled source code with command-line option '-p'
390
+ .==================== example4_x.result
391
+ $ erubis -x {{*-p '<!--% %-->'*}} example4.eruby
392
+ .#.<<<:! erubis -x -p '<!--% %-->' guide.d/example4.eruby
393
+ _buf = ''; for item in list
394
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
395
+ '; end
396
+ _buf.to_s
397
+ .====================
398
+
399
+ .? example4.rb
400
+ .-------------------- example4.rb
401
+ require 'erubis'
402
+ input = File.read('example4.eruby')
403
+ eruby = Erubis::Eruby.new(input{{*, :pattern=>'<!--% %-->'*}})
404
+ # or '<(?:!--)?% %(?:--)?>'
405
+
406
+ puts "---------- script source ---"
407
+ puts eruby.src # print script source
408
+
409
+ puts "---------- result ----------"
410
+ list = ['aaa', 'bbb', 'ccc']
411
+ puts eruby.result(binding()) # get result
412
+ .--------------------
413
+
414
+ .? output
415
+ .==================== example4.result
416
+ $ ruby example4.rb
417
+ .#.<<<:! (cd guide.d; ruby example4.rb)
418
+ ---------- script source ---
419
+ _buf = ''; for item in list
420
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
421
+ '; end
422
+ _buf.to_s
423
+ ---------- result ----------
424
+ <p>aaa</p>
425
+ <p>bbb</p>
426
+ <p>ccc</p>
427
+ .====================
428
+
429
+ It is able to specify regular expression with :pattern option.
430
+ Notice that you must use '{{,(?: ),}}' instead of '{{,( ),}}' for grouping.
431
+ For example, '{{,<(!--)?% %(--)?>,}}' will not work while '{{,<(?:!--)?% %(?:--)?>,}}' will work.
432
+
433
+
434
+
435
+ .$$ Context Object | tut-context
436
+
437
+ Context object is a set of data which are used in eRuby script.
438
+ Using context object makes clear which data to be used.
439
+ In Erubis, Hash object and Erubis::Context object are available as context object.
440
+
441
+ Context data can be accessible via instance variables in eRuby script.
442
+
443
+ .? example5.eruby
444
+ .-------------------- example5.eruby
445
+ <span><%= {{*@val*}} %></span>
446
+ <ul>
447
+ <% for item in {{*@list*}} %>
448
+ <li><%= item %></li>
449
+ <% end %>
450
+ </ul>
451
+ .--------------------
452
+
453
+ .? example5.rb
454
+ .-------------------- example5.rb
455
+ require 'erubis'
456
+ input = File.read('example5.eruby')
457
+ eruby = Erubis::Eruby.new(input) # create Eruby object
458
+
459
+ ## create context object
460
+ ## (key means var name, which may be string or symbol.)
461
+ {{*context = {
462
+ :val => 'Erubis Example',
463
+ 'list' => ['aaa', 'bbb', 'ccc'],
464
+ }*}}
465
+ ## or
466
+ # context = Erubis::Context.new()
467
+ # context['val'] = 'Erubis Example'
468
+ # context[:list] = ['aaa', 'bbb', 'ccc'],
469
+
470
+ puts {{*eruby.evaluate(context)*}} # get result
471
+ .--------------------
472
+
473
+ .? output
474
+ .==================== example5.result
475
+ $ ruby example5.rb
476
+ .#.<<<:! (cd guide.d; ruby example5.rb)
477
+ <span>Erubis Example</span>
478
+ <ul>
479
+ <li>aaa</li>
480
+ <li>bbb</li>
481
+ <li>ccc</li>
482
+ </ul>
483
+ .====================
484
+
485
+ The difference between Erubis#result(binding) and Erubis#evaluate(context) is that the former invokes 'eval @src, binding' and the latter invokes 'context.instance_eval @src'.
486
+ This means that data is passed into eRuby script via local variables when Eruby::binding() is called, or passed via instance variables when Eruby::evaluate() is called.
487
+
488
+ Here is the definition of Erubis#result() and Erubis#evaluate().
489
+
490
+ .? definition of result(binding) and evaluate(context)
491
+ .--------------------
492
+ def result(_binding=TOPLEVEL_BINDING)
493
+ if _binding.is_a?(Hash)
494
+ # load hash data as local variable
495
+ _h = _binding
496
+ _binding = binding()
497
+ eval _h.collect{|k,v| "#{k} = _h[#{k.inspect}];"}.join, _binding
498
+ end
499
+ return {{*eval(@src, _binding)*}}
500
+ end
501
+
502
+ def evaluate(_context=Erubis::Context.new)
503
+ if _context.is_a?(Hash)
504
+ # convert hash object to Context object
505
+ _hash = _context
506
+ _context = Erubis::Context.new
507
+ _hash.each {|k, v| _context[k] = v }
508
+ end
509
+ return {{*_context.instance_eval(@src)*}}
510
+ end
511
+ .--------------------
512
+
513
+ instance_eval() is defined at Object class so it is able to use any object as a context object as well as Hash or Erubis::Context.
514
+
515
+ .? example6.rb
516
+ .-------------------- example6.rb
517
+ class MyData
518
+ attr_accessor :val, :list
519
+ end
520
+
521
+ ## any object can be a context object
522
+ {{*mydata = MyData.new*}}
523
+ {{*mydata.val = 'Erubis Example'*}}
524
+ {{*mydata.list = ['aaa', 'bbb', 'ccc']*}}
525
+
526
+ require 'erubis'
527
+ eruby = Erubis::Eruby.new(File.read('example5.eruby'))
528
+ puts eruby.evaluate({{*mydata*}})
529
+ .--------------------
530
+
531
+ .? output
532
+ .==================== example6.result
533
+ $ ruby example6.rb
534
+ .#.<<<:! (cd guide.d; ruby example6.rb)
535
+ <span>Erubis Example</span>
536
+ <ul>
537
+ <li>aaa</li>
538
+ <li>bbb</li>
539
+ <li>ccc</li>
540
+ </ul>
541
+ .====================
542
+
543
+
544
+ It is recommended to use 'Erubis::Eruby#evaluate(context)' rather than 'Erubis::Eruby#result(binding())' because the latter has some problems.
545
+ See {{<evaluate(context) v.s. result(binding)|#topics-context-vs-binding>}} section for details.
546
+
547
+
548
+
549
+ .$$ Context Data File | tut-datafile
550
+
551
+ Command-line option '-f' specifies context data file.
552
+ Erubis load context data file and use it as context data.
553
+ Context data file can be YAML file ('*.yaml' or '*.yml') or Ruby script ('*.rb').
554
+ .#It is very useful to import YAML document data into Hash context object.
555
+ .#You can specify YAML file as context data file with command-line option '-f'.
556
+
557
+ .? example7.eruby
558
+ .-------------------- example7.eruby
559
+ <h1><%= {{*@title*}} %></h1>
560
+ <ul>
561
+ <% for user in {{*@users*}} %>
562
+ <li>
563
+ <a href="mailto:<%= user['mail']%>"><%= user['name'] %></a>
564
+ </li>
565
+ <% end %>
566
+ </ul>
567
+ .--------------------
568
+
569
+ .? context.yaml
570
+ .-------------------- context.yaml
571
+ {{*title:*}} Users List
572
+ {{*users:*}}
573
+ - name: foo
574
+ mail: foo@mail.com
575
+ - name: bar
576
+ mail: bar@mail.net
577
+ - name: baz
578
+ mail: baz@mail.org
579
+ .--------------------
580
+
581
+ .? context.rb
582
+ .-------------------- context.rb
583
+ @title = 'Users List'
584
+ @users = [
585
+ { 'name'=>'foo', 'mail'=>'foo@mail.com' },
586
+ { 'name'=>'bar', 'mail'=>'bar@mail.net' },
587
+ { 'name'=>'baz', 'mail'=>'baz@mail.org' },
588
+ ]
589
+ .--------------------
590
+
591
+ .#.? example7.rb
592
+ .#.-------------------- example7.rb
593
+ .#require 'erubis'
594
+ .#input = File.read('example7.eruby')
595
+ .#eruby = Erubis::Eruby.new(input) # create Eruby object
596
+ .#
597
+ .### load YAML document as context object
598
+ .#{{*require 'yaml'*}}
599
+ .#{{*context = YAML.load_file('example7.yaml')*}}
600
+ .#
601
+ .#puts {{*eruby.evaluate(context)*}} # get result
602
+ .#.--------------------
603
+ .#
604
+ .#.? output
605
+ .#.====================
606
+ .#$ ruby example7.rb
607
+ .#.<<<:! (cd guide.d; ruby example7.rb)
608
+ .#.====================
609
+ .#
610
+ .#It is able to specify YAML data file with the command-line option '-f'.
611
+ .#You don't have to write ruby script such as 'example7.rb'.
612
+
613
+ .? example of command-line option '-f'
614
+ .==================== example7.result.split_filter
615
+ $ erubis {{*-f context.yaml*}} example7.eruby
616
+ .#.<<<:! (cd guide.d; erubis -f context.yaml example7.eruby)
617
+ <h1>Users List</h1>
618
+ <ul>
619
+ <li>
620
+ <a href="mailto:foo@mail.com">foo</a>
621
+ </li>
622
+ <li>
623
+ <a href="mailto:bar@mail.net">bar</a>
624
+ </li>
625
+ <li>
626
+ <a href="mailto:baz@mail.org">baz</a>
627
+ </li>
628
+ </ul>
629
+ $ erubis {{*-f context.rb*}} example7.eruby
630
+ .#.<<<:! (cd guide.d; erubis -f context.rb example7.eruby)
631
+ <h1>Users List</h1>
632
+ <ul>
633
+ <li>
634
+ <a href="mailto:foo@mail.com">foo</a>
635
+ </li>
636
+ <li>
637
+ <a href="mailto:bar@mail.net">bar</a>
638
+ </li>
639
+ <li>
640
+ <a href="mailto:baz@mail.org">baz</a>
641
+ </li>
642
+ </ul>
643
+ .====================
644
+
645
+ Command-line option '-S' converts keys of mapping in YAML data file from string into symbol.
646
+ Command-line option '-B' invokes 'Erubis::Eruby#result(binding())' instead of 'Erubis::Eruby#evaluate(context)'.
647
+
648
+
649
+
650
+ .$$ Context Data String | tut-datastr
651
+
652
+ Command-line option '-c {{/str/}}' enables you to specify context data in command-line.
653
+ {{/str/}} can be YAML flow-style or Ruby code.
654
+
655
+ .? example8.eruby
656
+ .-------------------- example8.eruby
657
+ <h1><%= @title %></h1>
658
+ <ul>
659
+ <% for item in @list %>
660
+ <li><%= item %></li>
661
+ <% end %>
662
+ </ul>
663
+ .--------------------
664
+
665
+ .? example of YAML flow style
666
+ .==================== example8_yaml.result
667
+ $ erubis {{*-c '{title: Example, list: [AAA, BBB, CCC]}'*}} example8.eruby
668
+ .#.<<<:! (cd guide.d; erubis -c '{title: Example, list: [AAA, BBB, CCC]}' example8.eruby)
669
+ <h1>Example</h1>
670
+ <ul>
671
+ <li>AAA</li>
672
+ <li>BBB</li>
673
+ <li>CCC</li>
674
+ </ul>
675
+ .====================
676
+
677
+ .? example of Ruby code
678
+ .==================== example8_ruby.result
679
+ $ erubis {{*-c '@title="Example"; @list=%w[AAA BBB CCC]'*}} example8.eruby
680
+ .#.<<<:! (cd guide.d; erubis -c '@title="Example"; @list=%w[AAA BBB CCC]' example8.eruby)
681
+ <h1>Example</h1>
682
+ <ul>
683
+ <li>AAA</li>
684
+ <li>BBB</li>
685
+ <li>CCC</li>
686
+ </ul>
687
+ .====================
688
+
689
+
690
+ .$$ Preamble and Postamble | tut-preamble
691
+
692
+ The first line ('_buf = '';') in the compiled source code is called preamble
693
+ and the last line ('_buf.to_s') is called postamble.
694
+
695
+ Command-line option '-b' skips the output of preamble and postamble.
696
+
697
+ .? example9.eruby
698
+ .-------------------- example9.eruby
699
+ <% for item in @list %>
700
+ <b><%= item %></b>
701
+ <% end %>
702
+ .--------------------
703
+
704
+ .? compiled source code with and without command-line option '-b'
705
+ .==================== example9.result.split_filter
706
+ $ erubis -x example9.eruby
707
+ .#.<<<:! erubis -x guide.d/example9.eruby | ruby -pe 'sub! /^_buf.*?(;|$)/, "{{*\\&*}}"'
708
+ {{*_buf = '';*}} for item in @list
709
+ _buf << ' <b>'; _buf << ( item ).to_s; _buf << '</b>
710
+ '; end
711
+ {{*_buf.to_s*}}
712
+ $ erubis -x {{*-b*}} example9.eruby
713
+ .#.<<<:! erubis -x -b guide.d/example9.eruby
714
+ for item in @list
715
+ _buf << ' <b>'; _buf << ( item ).to_s; _buf << '</b>
716
+ '; end
717
+ .====================
718
+
719
+ Erubis::Eruby.new option '{{,:preamble=>false,}}' and '{{,:postamble=>false,}}' also suppress output of preamble or postamle.
720
+
721
+ .? example9.rb
722
+ .-------------------- example9.rb
723
+ require 'erubis'
724
+ input = File.read('example9.eruby')
725
+ eruby1 = Erubis::Eruby.new(input)
726
+ eruby2 = Erubis::Eruby.new(input, {{*:preamble=>false, :postamble=>false*}})
727
+
728
+ puts eruby1.src # print preamble and postamble
729
+ puts "--------------"
730
+ puts eruby2.src # don't print preamble and postamble
731
+ .--------------------
732
+
733
+ .? output
734
+ .==================== example9.result
735
+ $ ruby example9.rb
736
+ .#.<<<:! (cd guide.d; ruby example9.rb)
737
+ _buf = ''; for item in @list
738
+ _buf << ' <b>'; _buf << ( item ).to_s; _buf << '</b>
739
+ '; end
740
+ _buf.to_s
741
+ --------------
742
+ for item in @list
743
+ _buf << ' <b>'; _buf << ( item ).to_s; _buf << '</b>
744
+ '; end
745
+ .====================
746
+
747
+ .#The command-line option '-b' specify both :preamble and :postamble to false.
748
+
749
+
750
+
751
+ .$$ Processing Instruction (PI) Converter | tut-pi
752
+
753
+ Erubis can parse Processing Instructions (PI) as embedded pattern.
754
+
755
+ .* '{{,<?rb {{/.../}} ?>,}}' represents Ruby statement.
756
+ .* '{{,@{{{/.../}}}@,}}' represents escaped expression value.
757
+ .* '{{,@!{{{/.../}}}@,}}' represents normal expression value.
758
+ .* '{{,@!!{{{/.../}}}@,}}' prints expression value to standard output.
759
+ .* (experimental) '{{,<%= {{/.../}} %>,}}' is also available to print expression value.
760
+
761
+ This is more useful than basic embedded pattern ('{{,<% ... >,}}') because PI doesn't break XML or HTML at all.
762
+ For example the following XHTML file is well-formed and HTML validator got no errors on this example.
763
+
764
+ .? example10.xhtml
765
+ .-------------------- example10.xhtml
766
+ <?xml version="1.0" ?>
767
+ {{*<?rb
768
+ lang = 'en'
769
+ list = ['<aaa>', 'b&b', '"ccc"']
770
+ ?>*}}
771
+ <html lang="{{*@!{lang}@*}}">
772
+ <body>
773
+ <ul>
774
+ {{*<?rb for item in list ?>*}}
775
+ <li>{{*@{item}@*}}</li>
776
+ {{*<?rb end ?>*}}
777
+ </ul>
778
+ </body>
779
+ </html>
780
+ .--------------------
781
+
782
+ If the command-line property '--pi={{/name/}}' is specified, erubis command parses input with PI converter.
783
+ If {{/name/}} is omitted then the following name is used according to '-l {{/lang/}}'.
784
+
785
+ .? mapping of '-l' option and PI name
786
+ .+--------------------
787
+ '-l' option ., PI name
788
+ .--------------------
789
+ -l ruby ., <?rb ... ?>
790
+ -l php ., <?php ... ?>
791
+ -l perl ., <?perl ... ?>
792
+ -l java ., <?java ... ?>
793
+ -l javascript ., <?js ... ?>
794
+ -l scheme ., <?scheme ... ?>
795
+ .+--------------------
796
+
797
+ .? output
798
+ .==================== example10_x.result
799
+ $ erubis -x {{*--pi*}} example10.xhtml
800
+ .#.<<<:! (cd guide.d; erubis -x --pi example10.xhtml)
801
+ _buf = ''; _buf << '<?xml version="1.0" ?>
802
+ ';
803
+ lang = 'en'
804
+ list = ['<aaa>', 'b&b', '"ccc"']
805
+
806
+ _buf << '<html lang="'; _buf << (lang).to_s; _buf << '">
807
+ <body>
808
+ <ul>
809
+ '; for item in list
810
+ _buf << ' <li>'; _buf << Erubis::XmlHelper.escape_xml(item); _buf << '</li>
811
+ '; end
812
+ _buf << ' </ul>
813
+ </body>
814
+ </html>
815
+ ';
816
+ _buf.to_s
817
+ .====================
818
+
819
+ Expression character can be changeable by command-line property '--embchar={{/char/}}. Default is '{{,@,}}'.
820
+
821
+ Use Erubis::PI::Eruby instead of Erubis::Eruby if you want to use PI as embedded pattern.
822
+
823
+ .? example10.rb
824
+ .-------------------- example10.rb
825
+ require 'erubis'
826
+ input = File.read('example10.xhtml')
827
+ eruby = Erubis::PI::Eruby.new(input)
828
+ print eruby.src
829
+ .--------------------
830
+
831
+ .? output
832
+ .==================== example10.result
833
+ $ ruby example10.rb
834
+ .#.<<<:! (cd guide.d; ruby example10.rb)
835
+ _buf = ''; _buf << '<?xml version="1.0" ?>
836
+ ';
837
+ lang = 'en'
838
+ list = ['<aaa>', 'b&b', '"ccc"']
839
+
840
+ _buf << '<html lang="'; _buf << (lang).to_s; _buf << '">
841
+ <body>
842
+ <ul>
843
+ '; for item in list
844
+ _buf << ' <li>'; _buf << Erubis::XmlHelper.escape_xml(item); _buf << '</li>
845
+ '; end
846
+ _buf << ' </ul>
847
+ </body>
848
+ </html>
849
+ ';
850
+ _buf.to_s
851
+ .====================
852
+
853
+
854
+ {{*(experimental)*}} Erubis supports '<%= ... %>' pattern with PI pattern.
855
+ .#It is useful if you are Rails user to write helper methods which contains '}' character.
856
+
857
+ .? example of Rails view template
858
+ .--------------------
859
+ <table>
860
+ <tr>
861
+ <?rb for item in @list ?>
862
+ <td>@{item.id}@</td>
863
+ <td>@{item.name}@</td>
864
+ <td>
865
+ {{*<%=*}} link_to 'Destroy', {:action=>'destroy', :id=>item.id},
866
+ :confirm=>'Are you OK?' {{*%>*}}
867
+ </td>
868
+ <?rb end ?>
869
+ </tr>
870
+ </table>
871
+ .--------------------
872
+
873
+
874
+
875
+ .$$ Retrieve Ruby Code | tut-notext
876
+
877
+ Similar to '-x', ommand-line option '-X' shows converted Ruby source code.
878
+ The difference between '-x' and 'X' is that the former converts text part but the latter ignores it.
879
+ It means that you can retrieve Ruby code from eRuby script by '-X' option.
880
+
881
+ .#Command 'notext' is a utility to extract only program code from eRuby/PHP/ePerl script.
882
+ .#It is an application of NoTextEnhancer.
883
+
884
+ For example, see the following eRuby script.
885
+ This is some complex, so it is difficult to grasp the program code.
886
+
887
+ .? example11.rhtml
888
+ .-------------------- example11.rhtml
889
+ <?xml version="1.0" encoding="UTF-8"?>
890
+ <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
891
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
892
+ <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
893
+ <body>
894
+ <h3>List</h3>
895
+ <% if @list.nil? || @list.empty? %>
896
+ <p>not found.</p>
897
+ <% else %>
898
+ <table>
899
+ <tbody>
900
+ <% @list.each_with_index do |item, i| %>
901
+ <tr bgcolor="<%= i % 2 == 0 ? '#FCC' : '#CCF' %>">
902
+ <td><%= item %></td>
903
+ </tr>
904
+ <% end %>
905
+ </tbody>
906
+ </table>
907
+ <% end %>
908
+ </body>
909
+ </html>
910
+ .--------------------
911
+
912
+ Command-line option '-X' extracts only the ruby code from eRuby script.
913
+
914
+ .? result
915
+ .==================== example11.result
916
+ $ erubis {{*-X*}} example11.rhtml
917
+ _buf = '';
918
+
919
+
920
+
921
+
922
+
923
+ if @list.nil? || @list.empty?
924
+
925
+ else
926
+
927
+
928
+ @list.each_with_index do |item, i|
929
+ _buf << ( i % 2 == 0 ? '#FCC' : '#CCF' ).to_s;
930
+ _buf << ( item ).to_s;
931
+
932
+ end
933
+
934
+
935
+ end
936
+
937
+
938
+ _buf.to_s
939
+ .====================
940
+
941
+ Command-line option '-C' ({{*c*}}mpact) deletes empty lines.
942
+
943
+ .? result
944
+ .==================== example11_C.result
945
+ $ erubis {{*-XC*}} example11.rhtml
946
+ _buf = '';
947
+ if @list.nil? || @list.empty?
948
+ else
949
+ @list.each_with_index do |item, i|
950
+ _buf << ( i % 2 == 0 ? '#FCC' : '#CCF' ).to_s;
951
+ _buf << ( item ).to_s;
952
+ end
953
+ end
954
+ _buf.to_s
955
+ .====================
956
+
957
+ Option '-U' ({{*u*}}nique) converts empty lines into a line.
958
+
959
+ .? result
960
+ .==================== example11_U.result
961
+ $ erubis {{*-XU*}} example11.rhtml
962
+ _buf = '';
963
+
964
+ if @list.nil? || @list.empty?
965
+
966
+ else
967
+
968
+ @list.each_with_index do |item, i|
969
+ _buf << ( i % 2 == 0 ? '#FCC' : '#CCF' ).to_s;
970
+ _buf << ( item ).to_s;
971
+
972
+ end
973
+
974
+ end
975
+
976
+ _buf.to_s
977
+ .====================
978
+
979
+ Option '-N' ({{*n*}}umber) adds line number.
980
+ It is available with '-C' or '-U'.
981
+
982
+ .? result
983
+ .==================== example11_N.result
984
+ $ erubis {{*-XNU*}} example11.rhtml
985
+ 1: _buf = '';
986
+
987
+ 7: if @list.nil? || @list.empty?
988
+
989
+ 9: else
990
+
991
+ 12: @list.each_with_index do |item, i|
992
+ 13: _buf << ( i % 2 == 0 ? '#FCC' : '#CCF' ).to_s;
993
+ 14: _buf << ( item ).to_s;
994
+
995
+ 16: end
996
+
997
+ 19: end
998
+
999
+ 22: _buf.to_s
1000
+ .====================
1001
+
1002
+ Command-line option '-X' is available with PHP script.
1003
+ .#Language is automatically detected by suffix of filename.
1004
+ .#And you can specify language with option '-l' ({{*l*}}anguage).
1005
+
1006
+ .? example11.php
1007
+ .-------------------- example11.php
1008
+ <?xml version="1.0"?>
1009
+ <html>
1010
+ <body>
1011
+ <h3>List</h3>
1012
+ <?php if (!$list) { ?>
1013
+ <p>not found.</p>
1014
+ <?php } else { ?>
1015
+ <table>
1016
+ <tbody>
1017
+ <?php $i = 0; ?>
1018
+ <?php foreach ($list as $item) { ?>
1019
+ <tr bgcolor="<?php echo ++$i % 2 == 1 ? '#FCC' : '#CCF'; ?>">
1020
+ <td><?php echo $item; ?></td>
1021
+ </tr>
1022
+ <?php } ?>
1023
+ </tbody>
1024
+ </table>
1025
+ <?php } ?>
1026
+ </body>
1027
+ </html>
1028
+ .--------------------
1029
+
1030
+ .? result
1031
+ .==================== example11_php.result
1032
+ $ erubis -XNU {{*-l php*}} {{*--pi=php*}} --trim=false example11.php
1033
+
1034
+ 5: <?php if (!$list) { ?>
1035
+
1036
+ 7: <?php } else { ?>
1037
+
1038
+ 10: <?php $i = 0; ?>
1039
+ 11: <?php foreach ($list as $item) { ?>
1040
+ 12: <?php echo ++$i % 2 == 1 ? '#FCC' : '#CCF'; ?>
1041
+ 13: <?php echo $item; ?>
1042
+
1043
+ 15: <?php } ?>
1044
+
1045
+ 18: <?php } ?>
1046
+
1047
+ .====================
1048
+
1049
+ .#
1050
+ .#.? example11.eperl
1051
+ .#.-------------------- example11.eperl
1052
+ .#<?xml version="1.0"?>
1053
+ .#<html>
1054
+ .# <body>
1055
+ .# <h3>List</h3>
1056
+ .# <? if (!@list) { !>
1057
+ .# <p>not found.</p>
1058
+ .# <? } else { !>
1059
+ .# <table>
1060
+ .# <tbody>
1061
+ .# <? $i = 0; !>
1062
+ .# <? foreach ($item in @list) { !>
1063
+ .# <tr bgcolor="<?= ++$i % 2 == 1 ? '#FCC' : '#CCF' !>">
1064
+ .# <td><?= $item !></td>
1065
+ .# </tr>
1066
+ .# <? } !>
1067
+ .# </tbody>
1068
+ .# </table>
1069
+ .# <? } !>
1070
+ .# </body>
1071
+ .#</html>
1072
+ .#.chomp
1073
+ .#.--------------------
1074
+ .#
1075
+ .#.? result
1076
+ .#.==================== example11_eperl.result
1077
+ .#$ erubis -XNU -l perl example11.eperl
1078
+ .# 1: use HTML::Entities;
1079
+ .#
1080
+ .# 5: if (!@list) {
1081
+ .#
1082
+ .# 7: } else {
1083
+ .#
1084
+ .# 10: $i = 0;
1085
+ .# 11: foreach ($item in @list) {
1086
+ .# 12: print(++$i % 2 == 1 ? '#FCC' : '#CCF');
1087
+ .# 13: print($item);
1088
+ .#
1089
+ .# 15: }
1090
+ .#
1091
+ .# 18: }
1092
+ .#
1093
+ .#.====================
1094
+ .#
1095
+
1096
+
1097
+
1098
+ .$ Enhancer | enhancer
1099
+
1100
+ Enhancer is a module to add a certain feature into Erubis::Eruby class.
1101
+ Enhancer may be language-independent or only for Erubis::Eruby class.
1102
+
1103
+ To use enhancers, define subclass and include them.
1104
+ The folloing is an example to use {{<EscapeEnhancer|#escape-enhancer>}}, {{<PercentLineEnhancer|#percentline-enhancer>}}, and {{<BiPatternEnhancer|#bipattern-enhancer>}}.
1105
+
1106
+ .--------------------
1107
+ class MyEruby < Erubis::Eruby
1108
+ include EscapeEnhancer
1109
+ include PercentLineEnhancer
1110
+ include BiPatternEnhancer
1111
+ end
1112
+ .--------------------
1113
+
1114
+ You can specify enhancers in command-line with option '-E'.
1115
+ The following is an example to use some enhancers in command-line.
1116
+ .====================
1117
+ $ erubis -xE Escape,PercentLine,BiPattern example.eruby
1118
+ .====================
1119
+
1120
+ The following is the list of enhancers.
1121
+
1122
+ .: {{<EscapeEnhander|#escape-enhancer>}} (language-independent)
1123
+ Switch '<%= %>' to escaped and '<%== %>' to unescaped.
1124
+ .: {{<StdoutEnhancer|#stdout-enhancer>}} (only for Eruby)
1125
+ Use $stdout instead of array buffer.
1126
+ .: {{<PrintOutEnhancer|#printout-enhancer>}} (only for Eruby)
1127
+ Use "print(...)" statement insead of "_buf << ...".
1128
+ .: {{<PrintEnabledEnhancer|#printenabled-enhancer>}} (only for Eruby)
1129
+ Enable to use print() in '<% ... %>'.
1130
+ .: {{<ArrayEnhancer|#array-enhancer>}} (only for Eruby)
1131
+ Return array of string instead of returning string.
1132
+ .: {{<ArrayBufferEnhancer|#arraybuffer-enhancer>}} (only for Eruby)
1133
+ Use array buffer. It is a little slower than StringBufferEnhancer.
1134
+ .: {{<StringBufferEnhancer|#stringbuffer-enhancer>}} (only for Eruby)
1135
+ Use string buffer. This is included in Erubis::Eruby by default.
1136
+ .: {{<ErboutEnhancer|#erbout-enhancer>}} (only for Eruby)
1137
+ Set '_erbout = _buf = "";' to be compatible with ERB.
1138
+ .: {{<NoTextEnhancer|#notext-enhancer>}} (language-independent)
1139
+ Print embedded code only and ignore normal text.
1140
+ .: {{<NoCodeEnhancer|#nocode-enhancer>}} (language-independent)
1141
+ Print normal text only and ignore code.
1142
+ .: {{<SimplifyEnhancer|#simplify-enhancer>}} (language-independent)
1143
+ Make compile faster but don't trim spaces around '<% %>'.
1144
+ .: {{<BiPatternEnhancer|#bipattern-enhancer>}} (language-independent)
1145
+ [experimental] Enable to use another embedded pattern with '<% %>'.
1146
+ .: {{<PercentLineEnhancer|#percentline-enhancer>}} (language-independent)
1147
+ Regard lines starting with '%' as Ruby code. This is for compatibility with eruby and ERB.
1148
+ .: {{<HeaderFooterEnhancer|#headerfooter-enhancer>}} (language-independent)
1149
+ [experimental] Enable you to add header and footer in eRuby script.
1150
+ .: {{<InterpolationEnhancer|#interpolation-enhancer>}} (only for Eruby)
1151
+ [experimental] convert '<p><%= text %></p>' into '_buf << %Q`<p>#{text}</p>`'.
1152
+ .: {{<DeleteIndentEnhancer|#deleteindent-enhancer>}} (language-independent)
1153
+ [experimental] delete indentation of HTML file and eliminate page size.
1154
+
1155
+
1156
+ If you required 'erubis/engine/enhanced', Eruby subclasses which include each enhancers are defined.
1157
+ For example, class BiPatternEruby includes BiPatternEnhancer.
1158
+
1159
+ .#The following eRuby script ('example.rhtml') is used in the sections.
1160
+ .#
1161
+ .#.? example.rhtml
1162
+ .#.-------------------- example.rhtml
1163
+ .#<% for item in list %>
1164
+ .# <b><%= item %></b>
1165
+ .# <b><%== item %></b>
1166
+ .#<% end %>
1167
+ .#.--------------------
1168
+
1169
+
1170
+
1171
+ .$$ EscapeEnhancer | escape-enhancer
1172
+
1173
+ EscapeEnhancer switches '<%= ... %>' to escaped and '<%== ... %>' to unescaped.
1174
+
1175
+ .? example.eruby
1176
+ .-------------------- example.eruby
1177
+ <div>
1178
+ <% for item in list %>
1179
+ <p><%= item %></p>
1180
+ <p><%== item %></p>
1181
+ <% end %>
1182
+ </div>
1183
+ .--------------------
1184
+
1185
+ .#.? escape-example.rb
1186
+ .#.-------------------- escape-example.rb
1187
+ .#require 'erubis'
1188
+ .#class EscapedEruby < Erubis::Eruby
1189
+ .# include Erubis::EscapeEnhancer
1190
+ .#end
1191
+ .#eruby = EscapedEruby.new(File.read('example.eruby'))
1192
+ .#print eruby.src
1193
+ .#.--------------------
1194
+ .#
1195
+ .#.? compiled source code
1196
+ .#.====================
1197
+ .#$ ruby escape-example.rb
1198
+ .#.<<<:! (cd guide.d; ruby escape-example.rb)
1199
+ .#.====================
1200
+
1201
+ .? compiled source code
1202
+ .==================== escape_example.result
1203
+ $ erubis -xE Escape example.eruby
1204
+ .#.<<<:! erubis -xE Escape guide.d/example.eruby | ruby -pe 'sub! /_buf << [E(].*?;/, "{{*\\&*}}"'
1205
+ _buf = ''; _buf << '<div>
1206
+ '; for item in list
1207
+ _buf << ' <p>'; {{*_buf << Erubis::XmlHelper.escape_xml( item );*}} _buf << '</p>
1208
+ <p>'; {{*_buf << ( item ).to_s;*}} _buf << '</p>
1209
+ '; end
1210
+ _buf << '</div>
1211
+ ';
1212
+ _buf.to_s
1213
+ .====================
1214
+
1215
+ EscapeEnhancer is language-independent.
1216
+
1217
+
1218
+
1219
+ .$$ StdoutEnhancer | stdout-enhancer
1220
+
1221
+ StdoutEnhancer use $sdtdout instead of array buffer.
1222
+ Therefore, you can use 'print' statement in embedded ruby code.
1223
+
1224
+ .#.? stdout-example.rb
1225
+ .#.-------------------- stdout-example.rb
1226
+ .#require 'erubis'
1227
+ .#class StdoutEruby < Erubis::Eruby
1228
+ .# include Erubis::StdoutEnhancer
1229
+ .#end
1230
+ .#eruby = StdoutEruby.new(File.read('example.eruby'))
1231
+ .#print eruby.src
1232
+ .#.--------------------
1233
+ .#
1234
+ .#.? compiled source code
1235
+ .#.====================
1236
+ .#$ ruby stdout-example.rb
1237
+ .#.<<<:! (cd guide.d; ruby stdout-example.rb)
1238
+ .#.====================
1239
+
1240
+ .? compiled source code
1241
+ .==================== stdout_exmple.result
1242
+ $ erubis -xE Stdout example.eruby
1243
+ .#.<<<:! erubis -xE Stdout guide.d/example.eruby | ruby -pe 'sub! /^_buf = .*;/, "{{*\\&*}}"'
1244
+ {{*_buf = $stdout;*}} _buf << '<div>
1245
+ '; for item in list
1246
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
1247
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1248
+ '; end
1249
+ _buf << '</div>
1250
+ ';
1251
+ {{*''*}}
1252
+ .====================
1253
+
1254
+ StdoutEnhancer is only for Eruby.
1255
+
1256
+
1257
+
1258
+ .$$ PrintOutEnhancer | printout-enhancer
1259
+
1260
+ PrintOutEnhancer makes compiled source code to use 'print(...)' instead of '_buf << ...'.
1261
+
1262
+ .#.? printstatement-example.rb
1263
+ .#.-------------------- printstatement-example.rb
1264
+ .#require 'erubis'
1265
+ .#class PrintOutEruby < Erubis::Eruby
1266
+ .# include Erubis::PrintOutEnhancer
1267
+ .#end
1268
+ .#eruby = PrintOutEruby.new(File.read('example.eruby'))
1269
+ .#print eruby.src
1270
+ .#.--------------------
1271
+ .#
1272
+ .#.? compiled source code
1273
+ .#.====================
1274
+ .#$ ruby printstatement-example.rb
1275
+ .#.<<<:! (cd guide.d; ruby printstatement-example.rb)
1276
+ .#.====================
1277
+
1278
+ .? compiled source code
1279
+ .==================== printstatement_example.result
1280
+ $ erubis -xE PrintOut example.eruby
1281
+ .#.<<<:! erubis -xE PrintOut guide.d/example.eruby | ruby -pe 'gsub! /print/, "{{*\\&*}}"'
1282
+ {{*print*}} '<div>
1283
+ '; for item in list
1284
+ {{*print*}} ' <p>'; {{*print*}}(( item ).to_s); {{*print*}} '</p>
1285
+ <p>'; {{*print*}} Erubis::XmlHelper.escape_xml( item ); {{*print*}} '</p>
1286
+ '; end
1287
+ {{*print*}} '</div>
1288
+ ';
1289
+ .====================
1290
+
1291
+ PrintOutEnhancer is only for Eruby.
1292
+
1293
+
1294
+
1295
+ .$$ PrintEnabledEnhancer | printenabled-enhancer
1296
+
1297
+ PrintEnabledEnhancer enables you to use print() method in '<% ... %>'.
1298
+
1299
+ .? printenabled-example.eruby
1300
+ .-------------------- printenabled-example.eruby
1301
+ <% for item in @list %>
1302
+ <b>{{*<% print item %>*}}</b>
1303
+ <% end %>
1304
+ .--------------------
1305
+
1306
+ .? printenabled-example.rb
1307
+ .-------------------- printenabled-example.rb
1308
+ require 'erubis'
1309
+ class PrintEnabledEruby < Erubis::Eruby
1310
+ include Erubis::PrintEnabledEnhancer
1311
+ end
1312
+ input = File.read('printenabled-example.eruby')
1313
+ eruby = PrintEnabledEruby.new(input)
1314
+ list = ['aaa', 'bbb', 'ccc']
1315
+ print eruby.evaluate(:list=>list)
1316
+ .--------------------
1317
+
1318
+ .? output result
1319
+ .==================== printenable_example.result
1320
+ $ ruby printenabled-example.rb
1321
+ .#.<<<:! (cd guide.d; ruby printenabled-example.rb)
1322
+ <b>aaa</b>
1323
+ <b>bbb</b>
1324
+ <b>ccc</b>
1325
+ .====================
1326
+
1327
+ Notice to use Eruby#evaluate() and not to use Eruby#result(),
1328
+ because print() method in '<% ... %>' invokes not Kernel#print() but PrintEnabledEnhancer#print().
1329
+
1330
+ PrintEnabledEnhancer is only for Eruby.
1331
+
1332
+
1333
+
1334
+ .$$ ArrayEnhancer | array-enhancer
1335
+
1336
+ ArrayEnhancer makes Eruby to return an array of strings.
1337
+
1338
+ .#.? array-example.rb
1339
+ .#.-------------------- array-example.rb
1340
+ .#require 'erubis'
1341
+ .#class ArrayEruby < Erubis::Eruby
1342
+ .# include Erubis::ArrayEnhancer
1343
+ .#end
1344
+ .#eruby = ArrayEruby.new(File.read('example.eruby'))
1345
+ .#print eruby.src
1346
+ .#.--------------------
1347
+ .#
1348
+ .#.? compiled source code
1349
+ .#.====================
1350
+ .#$ ruby array-example.rb
1351
+ .#.<<<:! (cd guide.d; ruby array-example.rb)
1352
+ .#.====================
1353
+
1354
+ .? compiled source code
1355
+ .==================== array_example.result
1356
+ $ erubis -xE Array example.eruby
1357
+ .#.<<<:! erubis -xE Array guide.d/example.eruby | ruby -pe 'sub! /^_buf( = \[\];)?/, "{{*\\&*}}"'
1358
+ {{*_buf = [];*}} _buf << '<div>
1359
+ '; for item in list
1360
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
1361
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1362
+ '; end
1363
+ _buf << '</div>
1364
+ ';
1365
+ {{*_buf*}}
1366
+ .====================
1367
+
1368
+ ArrayEnhancer is only for Eruby.
1369
+
1370
+
1371
+
1372
+ .$$ ArrayBufferEnhancer | arraybuffer-enhancer
1373
+
1374
+ ArrayBufferEnhancer makes Eruby to use array buffer.
1375
+ Array buffer is a litte slower than String buffer.
1376
+
1377
+ ArrayBufferEnhancer is only for Eruby.
1378
+
1379
+ .? compiled source code
1380
+ .==================== arraybuffer_example.result
1381
+ $ erubis -xE ArrayBuffer example.eruby
1382
+ .#.<<<:! erubis -xE ArrayBuffer guide.d/example.eruby | ruby -pe 'sub!(/^_buf( = .*?;|\.join)?/,"{{*\\&*}}")'
1383
+ {{*_buf = [];*}} _buf << '<div>
1384
+ '; for item in list
1385
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
1386
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1387
+ '; end
1388
+ _buf << '</div>
1389
+ ';
1390
+ {{*_buf.join*}}
1391
+ .====================
1392
+
1393
+
1394
+
1395
+ .$$ StringBufferEnhancer | stringbuffer-enhancer
1396
+
1397
+ StringBufferEnhancer makes Eruby to use string buffer.
1398
+ String buffer is a little faster than array buffer.
1399
+ Erubis::Eruby includes this enhancer by default.
1400
+
1401
+
1402
+ .#.? stringbuffer-example.rb
1403
+ .#.-------------------- stringbuffer-example.rb
1404
+ .#require 'erubis'
1405
+ .#class StringBufferEruby < Erubis::Eruby
1406
+ .# include Erubis::StringBufferEnhancer
1407
+ .#end
1408
+ .#eruby = StringBufferEruby.new(File.read('example.eruby'))
1409
+ .#print eruby.src
1410
+ .#.--------------------
1411
+ .#
1412
+ .#.? compiled source code
1413
+ .#.====================
1414
+ .#$ ruby stringbuffer-example.rb
1415
+ .#.<<<:! (cd guide.d; ruby stringbuffer-example.rb)
1416
+ .#.====================
1417
+
1418
+ .? compiled source code
1419
+ .==================== stringbuffer_example.result
1420
+ $ erubis -xE StringBuffer example.eruby
1421
+ .#.<<<:! erubis -xE StringBuffer guide.d/example.eruby | ruby -pe 'sub!(/^_buf( = .*?;)?/,"{{*\\&*}}")'
1422
+ {{*_buf = '';*}} _buf << '<div>
1423
+ '; for item in list
1424
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
1425
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1426
+ '; end
1427
+ _buf << '</div>
1428
+ ';
1429
+ {{*_buf.to_s*}}
1430
+ .====================
1431
+
1432
+
1433
+ StringBufferEnhancer is only for Eruby.
1434
+
1435
+
1436
+
1437
+ .$$ ErboutEnhancer | erbout-enhancer
1438
+
1439
+ ErboutEnhancer makes Eruby to be compatible with ERB.
1440
+ This is useful especially for Ruby on Rails.
1441
+
1442
+ .#.? erbout-example.rb
1443
+ .#.-------------------- erbout-example.rb
1444
+ .#require 'erubis'
1445
+ .#class ErboutEruby < Erubis::Eruby
1446
+ .# include Erubis::ErboutEnhancer
1447
+ .#end
1448
+ .#eruby = ErboutEruby.new(File.read('example.eruby'))
1449
+ .#print eruby.src
1450
+ .#.--------------------
1451
+ .#
1452
+ .#.? compiled source code
1453
+ .#.====================
1454
+ .#$ ruby erbout-example.rb
1455
+ .#.<<<:! (cd guide.d; ruby erbout-example.rb)
1456
+ .#.====================
1457
+
1458
+ .? compiled source code
1459
+ .====================
1460
+ $ erubis -xE Erbout example.eruby
1461
+ .#.<<<:! erubis -xE Erbout guide.d/example.eruby | ruby -pe 'sub! /^_erbout = _buf = .*?;/,"{{*\\&*}}"'
1462
+ {{*_erbout = _buf = '';*}} _buf << '<div>
1463
+ '; for item in list
1464
+ _buf << ' <p>'; _buf << ( item ).to_s; _buf << '</p>
1465
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1466
+ '; end
1467
+ _buf << '</div>
1468
+ ';
1469
+ _buf.to_s
1470
+ .====================
1471
+
1472
+
1473
+ ErboutEnhancer is only for Eruby.
1474
+
1475
+
1476
+
1477
+ .$$ NoTextEnhancer | notext-enhancer
1478
+
1479
+ NoTextEnhancer suppress output of text and prints only embedded code.
1480
+ This is useful especially when debugging a complex eRuby script.
1481
+
1482
+ .? notext-example.eruby
1483
+ .-------------------- notext-example.eruby
1484
+ <h3>List</h3>
1485
+ <% if !@list || @list.empty? %>
1486
+ <p>not found.</p>
1487
+ <% else %>
1488
+ <table>
1489
+ <tbody>
1490
+ <% @list.each_with_index do |item, i| %>
1491
+ <tr bgcolor="<%= i%2 == 0 ? '#FFCCCC' : '#CCCCFF' %>">
1492
+ <td><%= item %></td>
1493
+ </tr>
1494
+ <% end %>
1495
+ </tbody>
1496
+ </table>
1497
+ <% end %>
1498
+ .--------------------
1499
+
1500
+ .? output example of NoTextEnhancer
1501
+ .==================== notext_example.result
1502
+ $ erubis -xE NoText notext-example.eruby
1503
+ .#.<<<:! (cd guide.d; erubis -xE NoText notext-example.eruby)
1504
+ _buf = '';
1505
+ if !@list || @list.empty?
1506
+
1507
+ else
1508
+
1509
+
1510
+ @list.each_with_index do |item, i|
1511
+ _buf << ( i%2 == 0 ? '#FFCCCC' : '#CCCCFF' ).to_s;
1512
+ _buf << ( item ).to_s;
1513
+
1514
+ end
1515
+
1516
+
1517
+ end
1518
+ _buf.to_s
1519
+ .====================
1520
+
1521
+ NoTextEnhancer is language-independent. It is useful even if you are PHP user, see {{<this section|#topics-php>}}.
1522
+
1523
+
1524
+
1525
+ .$$ NoCodeEnhancer | nocode-enhancer
1526
+
1527
+ NoCodeEnhancer suppress output of embedded code and prints only normal text.
1528
+ This is useful especially when validating HTML tags.
1529
+
1530
+ .? nocode-example.eruby
1531
+ .-------------------- nocode-example.eruby
1532
+ <h3>List</h3>
1533
+ <% if !@list || @list.empty? %>
1534
+ <p>not found.</p>
1535
+ <% else %>
1536
+ <table>
1537
+ <tbody>
1538
+ <% @list.each_with_index do |item, i| %>
1539
+ <tr bgcolor="<%= i%2 == 0 ? '#FFCCCC' : '#CCCCFF' %>">
1540
+ <td><%= item %></td>
1541
+ </tr>
1542
+ <% end %>
1543
+ </tbody>
1544
+ </table>
1545
+ <% end %>
1546
+ .--------------------
1547
+
1548
+ .? output example of NoCodeEnhancer
1549
+ .==================== nocode_example.result
1550
+ $ erubis -xE NoCode notext-example.eruby
1551
+ .#.<<<:! (cd guide.d; erubis -xE NoCode nocode-example.eruby)
1552
+ <h3>List</h3>
1553
+
1554
+ <p>not found.</p>
1555
+
1556
+ <table>
1557
+ <tbody>
1558
+
1559
+ <tr bgcolor="">
1560
+ <td></td>
1561
+ </tr>
1562
+
1563
+ </tbody>
1564
+ </table>
1565
+
1566
+ .====================
1567
+
1568
+ NoCodeEnhancer is language-independent. It is useful even if you are PHP user, see {{<this section|#topics-php>}}.
1569
+
1570
+
1571
+
1572
+ .$$ SimplifyEnhancer | simplify-enhancer
1573
+
1574
+ SimplifyEnhancer makes compiling a little faster but don't trim spaces around '<% %>'.
1575
+
1576
+ .#.? simplify-example.rb
1577
+ .#.-------------------- simplify-example.rb
1578
+ .#require 'erubis'
1579
+ .#class SimplifiedEruby < Erubis::Eruby
1580
+ .# include Erubis::SimplifyEnhancer
1581
+ .#end
1582
+ .#eruby = SimplifiedEruby.new(File.read('example.eruby'))
1583
+ .#print eruby.src
1584
+ .#.--------------------
1585
+ .#
1586
+ .#.? compiled source code
1587
+ .#.====================
1588
+ .#$ ruby simplify-example.rb
1589
+ .#.<<<:! (cd guide.d; ruby simplify-example.rb)
1590
+ .#.====================
1591
+
1592
+ .? compiled source code
1593
+ .==================== simplify_example.result
1594
+ $ erubis -xE Simplify example.eruby
1595
+ .#.<<<:! erubis -xE Simplify guide.d/example.eruby
1596
+ _buf = ''; _buf << '<div>
1597
+ '; for item in list ; _buf << '
1598
+ <p>'; _buf << ( item ).to_s; _buf << '</p>
1599
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1600
+ '; end ; _buf << '
1601
+ </div>
1602
+ ';
1603
+ _buf.to_s
1604
+ .====================
1605
+
1606
+ SimplifyEnhancer is language-independent.
1607
+
1608
+
1609
+
1610
+ .$$ BiPatternEnhancer | bipattern-enhancer
1611
+
1612
+ BiPatternEnhancer enables to use another embedded pattern with '<% %>'.
1613
+ By Default, '[= ... =]' is available for expression.
1614
+ You can specify pattern by :bipattern property.
1615
+
1616
+ .? bipattern-example.rhtml
1617
+ .-------------------- bipattern-example.rhtml
1618
+ <% for item in list %>
1619
+ <b>{{*[= item =]*}}</b>
1620
+ <b>{{*[== item =]*}}</b>
1621
+ <% end %>
1622
+ .--------------------
1623
+
1624
+ .#.? bipattern-example.rb
1625
+ .#.-------------------- bipattern-example.rb
1626
+ .#require 'erubis'
1627
+ .#class BiPatternEruby < Erubis::Eruby
1628
+ .# include Erubis::BiPatternEnhancer
1629
+ .#end
1630
+ .#
1631
+ .#input = File.read('bipattern-example.rhtml')
1632
+ .#eruby = BiPatternEruby.new(input)
1633
+ .#print eruby.src
1634
+ .#.--------------------
1635
+ .#
1636
+ .#.? compiled source code
1637
+ .#.====================
1638
+ .#$ ruby bipattern-example.rb
1639
+ .#.<<<:! (cd guide.d; ruby bipattern-example.rb)
1640
+ .#.====================
1641
+
1642
+ .? compiled source code
1643
+ .==================== bipattern_example.result
1644
+ $ erubis -xE BiPattern bipattern-example.rhtml
1645
+ .#.<<<:! erubis -xE BiPattern guide.d/bipattern-example.rhtml | ruby -pe 'sub! /_buf << [E(].*;/, "{{*\\&*}}"'
1646
+ _buf = ''; for item in list
1647
+ _buf << ' <b>'; {{*_buf << ( item ).to_s;*}} _buf << '</b>
1648
+ <b>'; {{*_buf << Erubis::XmlHelper.escape_xml( item );*}} _buf << '</b>
1649
+ '; end
1650
+ _buf.to_s
1651
+ .====================
1652
+
1653
+ BiPatternEnhancer is language-independent.
1654
+
1655
+
1656
+
1657
+ .$$ PercentLineEnhancer | percentline-enhancer
1658
+
1659
+ PercentLineEnhancer regards lines starting with '%' as Ruby code.
1660
+ This is for compatibility with eruby and ERB.
1661
+
1662
+ .? percentline-example.rhtml
1663
+ .-------------------- percentline-example.rhtml
1664
+ <ul>
1665
+ {{*% for item in list*}}
1666
+ <li><%= item %></li>
1667
+ {{*% end*}}
1668
+ </ul>
1669
+ {{*%% lines with '%%'*}}
1670
+ .--------------------
1671
+
1672
+ .#.? percentline-example.rb
1673
+ .#.-------------------- percentline-example.rb
1674
+ .#require 'erubis'
1675
+ .#class PercentLineEruby < Erubis::Eruby
1676
+ .# include Erubis::PercentLineEnhancer
1677
+ .#end
1678
+ .#
1679
+ .#input = File.read('percentline-example.rhtml')
1680
+ .#eruby = PercentLineEruby.new(input)
1681
+ .#print eruby.src
1682
+ .#.--------------------
1683
+ .#
1684
+ .#.? compiled source code
1685
+ .#.====================
1686
+ .#$ ruby percentline-example.rb
1687
+ .#.<<<:! (cd guide.d; ruby percentline-example.rb)
1688
+ .#.====================
1689
+
1690
+ .? compiled source code
1691
+ .==================== percentline_example.result
1692
+ $ erubis -xE PercentLine percentline-example.rhtml
1693
+ .#.<<<:! erubis -xE PercentLine guide.d/percentline-example.rhtml | ruby -pe 'sub! /for.*?list|end/, "{{*\\&*}}"'
1694
+ _buf = ''; _buf << '<ul>
1695
+ '; {{*for item in list*}}
1696
+ _buf << ' <li>'; _buf << ( item ).to_s; _buf << '</li>
1697
+ '; {{*end*}}
1698
+ _buf << '</ul>
1699
+ {{*% lines with \'%%\'*}}
1700
+ ';
1701
+ _buf.to_s
1702
+ .====================
1703
+
1704
+ PercentLineEnhancer is language-independent.
1705
+
1706
+
1707
+
1708
+ .$$ PrefixedLineEnhancer | prefixedline-enhancer
1709
+
1710
+ PrefixedlineEnhancer regards lines starting with '%' as Ruby code.
1711
+ It is similar to {{<PercentLineEnhancer|#percentline-enhancer>}}, but there are some differences.
1712
+
1713
+ .* PrefixedlineEnhancer allows to indent lines starting with '%', but PercentLineEnhancer doesn't.
1714
+ .* PrefixedlineEnhancer allows to change prefixed character (default '%'), but PercentLineEnhancer doesn't.
1715
+
1716
+
1717
+ .? prefixedline-example.rhtml
1718
+ .-------------------- prefixedline-example.rhtml
1719
+ <ul>
1720
+ {{*! for item in list*}}
1721
+ <li><%= item %></li>
1722
+ {{*! end*}}
1723
+ </ul>
1724
+ {{*!! lines with '!!'*}}
1725
+ .--------------------
1726
+
1727
+ .? prefixedline-example.rb
1728
+ .-------------------- prefixedline-example.rb
1729
+ require 'erubis'
1730
+
1731
+ class PrefixedLineEruby < Erubis::Eruby
1732
+ include Erubis::PrefixedLineEnhancer
1733
+ end
1734
+
1735
+ input = File.read('prefixedline-example.rhtml')
1736
+ eruby = PrefixedLineEruby.new(input, :prefixchar=>'!') # default '%'
1737
+ print eruby.src
1738
+ .--------------------
1739
+
1740
+ .? compiled source code
1741
+ .==================== prefixedline_example.result
1742
+ $ ruby prefixedline-example.rb
1743
+ _buf = ''; _buf << '<ul>
1744
+ '; {{*for item in list*}}
1745
+ _buf << ' <li>'; _buf << ( item ).to_s; _buf << '</li>
1746
+ '; {{*end*}}
1747
+ _buf << '</ul>
1748
+ {{*! lines with \'!!\'*}}
1749
+ ';
1750
+ _buf.to_s
1751
+ .====================
1752
+
1753
+ PrefixedLineEnhancer is language-independent.
1754
+
1755
+
1756
+
1757
+ .$$ HeaderFooterEnhancer | headerfooter-enhancer
1758
+
1759
+ [experimental]
1760
+
1761
+ HeaderFooterEnhancer enables you to add header and footer in eRuby script.
1762
+
1763
+ .? headerfooter-example.eruby
1764
+ .-------------------- headerfooter-example.eruby
1765
+ {{*<!--#header:*}}
1766
+ {{*def list_items(items)*}}
1767
+ {{*#-->*}}
1768
+ <% for item in items %>
1769
+ <b><%= item %></b>
1770
+ <% end %>
1771
+ {{*<!--#footer:*}}
1772
+ {{*end*}}
1773
+ {{*#-->*}}
1774
+ .--------------------
1775
+
1776
+ .#.? headerfooter-example.rb
1777
+ .#.-------------------- headerfooter-example.rb
1778
+ .#require 'erubis'
1779
+ .#class HeaderFooterEruby < Erubis::Eruby
1780
+ .# include Erubis::HeaderFooterEnhancer
1781
+ .#end
1782
+ .#
1783
+ .#input = File.read('headerfooter-example.eruby')
1784
+ .#eruby = HeaderFooterEruby.new(input)
1785
+ .#print eruby.src
1786
+ .#.--------------------
1787
+ .#
1788
+ .#.? compiled source code
1789
+ .#.====================
1790
+ .#$ ruby headerfooter-example.rb
1791
+ .#.<<<:! (cd guide.d; ruby headerfooter-example.rb)
1792
+ .#.====================
1793
+
1794
+ .? compiled source code
1795
+ .==================== headerfooter_example.result
1796
+ $ erubis -xE HeaderFooter headerfooter-example.eruby
1797
+ .#.<<<:! erubis -xE HeaderFooter guide.d/headerfooter-example.eruby | ruby -pe 'sub! /^(def|end).*$/, "{{*\\&*}}"'
1798
+
1799
+ {{*def list_items(items)*}}
1800
+
1801
+ _buf = ''; for item in items
1802
+ _buf << ' <b>'; _buf << ( item ).to_s; _buf << '</b>
1803
+ '; end
1804
+ _buf.to_s
1805
+
1806
+ {{*end*}}
1807
+
1808
+ .====================
1809
+
1810
+ Compare to the following:
1811
+
1812
+ .? normal-eruby-test.eruby
1813
+ .-------------------- normal-eruby-test.eruby
1814
+ {{*<%*}}
1815
+ {{*def list_items(items)*}}
1816
+ {{*%>*}}
1817
+ <% for item in items %>
1818
+ <li><%= item %></li>
1819
+ <% end %>
1820
+ {{*<%*}}
1821
+ {{*end*}}
1822
+ {{*%>*}}
1823
+ .--------------------
1824
+
1825
+ .? compiled source code
1826
+ .==================== normal_eruby_test.result
1827
+ $ erubis -x normal-eruby-test.eruby
1828
+ .#.<<<:! erubis -x guide.d/normal-eruby-test.eruby | ruby -pe 'sub! /^(def|end).*$/, "{{*\\&*}}"'
1829
+ _buf = '';
1830
+ {{*def list_items(items)*}}
1831
+
1832
+ for item in items
1833
+ _buf << '<li>'; _buf << ( item ).to_s; _buf << '</li>
1834
+ '; end
1835
+
1836
+ {{*end*}}
1837
+
1838
+ _buf.to_s
1839
+ .====================
1840
+
1841
+ Header and footer can be in any position in eRuby script,
1842
+ that is, header is no need to be in the head of eRuby script.
1843
+
1844
+ .#+++
1845
+ .-------------------- headerfooter-example2.rb
1846
+ require 'erubis'
1847
+ class HeaderFooterEruby < Erubis::Eruby
1848
+ include Erubis::HeaderFooterEnhancer
1849
+ end
1850
+
1851
+ input = File.read('headerfooter-example2.rhtml')
1852
+ eruby = HeaderFooterEruby.new(input)
1853
+ print eruby.src
1854
+ .--------------------
1855
+ .#---
1856
+
1857
+ .? headerfooter-example2.rhtml
1858
+ .-------------------- headerfooter-example2.rhtml
1859
+ <?xml version="1.0"?>
1860
+ <html>
1861
+ {{*<!--#header:*}}
1862
+ {{*def page(list)*}}
1863
+ {{*#-->*}}
1864
+ :
1865
+ {{*<!--#footer:*}}
1866
+ {{*end*}}
1867
+ {{*#-->*}}
1868
+ </html>
1869
+ .--------------------
1870
+
1871
+ .#.? compiled source code
1872
+ .#.====================
1873
+ .#$ ruby headerfooter-example2.rb
1874
+ .#.<<<:! (cd guide.d; ruby headerfooter-example2.rb)
1875
+ .#.====================
1876
+
1877
+ .? compiled source code
1878
+ .==================== headerfooter_example2.result
1879
+ $ erubis -xE HeaderFooter headerfooter-example2.rhtml
1880
+ .#.<<<:! erubis -xE HeaderFooter guide.d/headerfooter-example2.rhtml | ruby -pe 'sub! /^(def|end).*$/, "{{*\\&*}}"'
1881
+
1882
+ {{*def page(list)*}}
1883
+
1884
+ _buf = ''; _buf << '<?xml version="1.0"?>
1885
+ <html>
1886
+ '; _buf << ' :
1887
+ '; _buf << '</html>
1888
+ ';
1889
+ _buf.to_s
1890
+
1891
+ {{*end*}}
1892
+
1893
+ .====================
1894
+
1895
+ HeaderFooterEnhancer is experimental and is language-independent.
1896
+
1897
+
1898
+
1899
+ .$$ InterpolationEnhancer | interpolation-enhancer
1900
+
1901
+ [experimental]
1902
+
1903
+ InterpolationEnhancer converts "<h1><%= title %></h1>" into
1904
+ "_buf << %Q`<h1>#{ title }</h1>`".
1905
+ This makes Eruby a litter faster because method call of String#<< are eliminated
1906
+ by expression interpolations.
1907
+
1908
+ .? InterpolationEnhancer elmininates method call of String#<<.
1909
+ .--------------------
1910
+ ## Assume that input is '<a href="<%=url%>"><%=name%></a>'.
1911
+ ## Eruby convert input into the following code. String#<< is called 5 times.
1912
+ _buf << '<a href="'; _buf << (url).to_s; _buf << '">'; _buf << (name).to_s; _buf << '</a>';
1913
+
1914
+ ## If InterpolationEnhancer is used, String#<< is called only once.
1915
+ _buf << %Q`<a href="#{url}">#{name}</a>`;
1916
+ .--------------------
1917
+
1918
+ .#.? interpolation-example.rb
1919
+ .#.-------------------- interpolation-example.rb
1920
+ .#require 'erubis'
1921
+ .#class InterpolationEruby < Erubis::Eruby
1922
+ .# include Erubis::InterpolationEnhancer
1923
+ .#end
1924
+ .#eruby = InterpolationEruby.new(File.read('example.eruby'))
1925
+ .### or
1926
+ .##eruby = Erubis::FastEruby.new(File.read('example.eruby'))
1927
+ .#print eruby.src
1928
+ .#.--------------------
1929
+ .#
1930
+ .#.? compiled source code
1931
+ .#.====================
1932
+ .#$ ruby interpolation-example.rb
1933
+ .#.<<<:! (cd guide.d; ruby interpolation-example.rb)
1934
+ .#.====================
1935
+
1936
+ .? compiled source code
1937
+ .==================== interpolation_example.result
1938
+ $ erubis -xE Interpolation example.eruby
1939
+ .#.<<<:! erubis -xE Interpolation guide.d/example.eruby | ruby -pe 'gsub! /(%Q`|`|\#\{.*?\})/, "{{*\\&*}}"'
1940
+ _buf = ''; _buf << {{*%Q`*}}<div>\n{{*`*}}
1941
+ for item in list
1942
+ _buf << {{*%Q`*}} <p>{{*#{ item }*}}</p>
1943
+ <p>{{*#{Erubis::XmlHelper.escape_xml( item )}*}}</p>\n{{*`*}}
1944
+ end
1945
+ _buf << {{*%Q`*}}</div>\n{{*`*}}
1946
+ _buf.to_s
1947
+ .====================
1948
+
1949
+ Erubis provides Erubis::FastEruby class which includes InterpolationEnhancer.
1950
+ You can use Erubis::FastEruby class instead of Erubis::Eruby class.
1951
+
1952
+ InterpolationEnhancer is only for Eruby.
1953
+
1954
+
1955
+ .$$ DeleteIndentEnhancer | deleteindent-enhancer
1956
+
1957
+ [experimental]
1958
+ DeleteIndentEnhancer deletes indentation of HTML file.
1959
+
1960
+ .? compiled source code
1961
+ .==================== interpolation_example.result
1962
+ $ erubis -xE DeleteIndent example.eruby
1963
+ .#.<<<:! erubis -xE DeleteIndent guide.d/example.eruby
1964
+ _buf = ''; _buf << '<div>
1965
+ '; for item in list
1966
+ _buf << '<p>'; _buf << ( item ).to_s; _buf << '</p>
1967
+ <p>'; _buf << Erubis::XmlHelper.escape_xml( item ); _buf << '</p>
1968
+ '; end
1969
+ _buf << '</div>
1970
+ ';
1971
+ _buf.to_s
1972
+ .====================
1973
+
1974
+ Notice that DeleteIndentEnhancer isn't intelligent.
1975
+ It deletes indentations even if they are in <PRE></PRE>.
1976
+
1977
+ DeleteIndentEnhancer is language-independent.
1978
+
1979
+
1980
+
1981
+ .$ Multi-Language Support | lang
1982
+
1983
+ Erubis supports the following languages{{(If you need template engine in pure PHP/Perl/JavaScript, try {{<Tenjin|http://www.kuwata-lab.com/tenjin/>}} ({{<http://www.kuwata-lab.com/tenjin/>}}). Tenjin is a very fast and full-featured template engine implemented in pure PHP/Perl/JavaScript.)}}:
1984
+
1985
+ .* Ruby
1986
+ .* {{<PHP|#lang-php>}}
1987
+ .* {{<C|#lang-c>}}
1988
+ .* {{<Java|#lang-java>}}
1989
+ .* {{<Scheme|#lang-scheme>}}
1990
+ .* {{<Perl|#lang-perl>}}
1991
+ .* {{<JavaScript|#lang-javascript>}}
1992
+
1993
+
1994
+
1995
+ .$$ PHP | lang-php
1996
+
1997
+ .? example.ephp
1998
+ .-------------------- example.ephp
1999
+ <?xml version="1.0"?>
2000
+ <html>
2001
+ <body>
2002
+ <p>Hello {{*<%= $user %>*}}!</p>
2003
+ <table>
2004
+ <tbody>
2005
+ {{*<% $i = 0; %>*}}
2006
+ {{*<% foreach ($list as $item) { %>*}}
2007
+ {{*<% $i++; %>*}}
2008
+ <tr bgcolor={{*"<%= $i % 2 == 0 ? '#FFCCCC' : '#CCCCFF' %>"*}}>
2009
+ <td>{{*<%= $i %>*}}</td>
2010
+ <td>{{*<%== $item %>*}}</td>
2011
+ </tr>
2012
+ {{*<% } %>*}}
2013
+ </tbody>
2014
+ </table>
2015
+ </body>
2016
+ </html>
2017
+ .--------------------
2018
+
2019
+ .? compiled source code
2020
+ .==================== example_php.result
2021
+ $ erubis -l php example.ephp
2022
+ .#.<<<:! (cd guide.d; erubis -l php example.ephp)
2023
+ <<?php ?>?xml version="1.0"?>
2024
+ <html>
2025
+ <body>
2026
+ <p>Hello <?php echo $user; ?>!</p>
2027
+ <table>
2028
+ <tbody>
2029
+ <?php $i = 0; ?>
2030
+ <?php foreach ($list as $item) { ?>
2031
+ <?php $i++; ?>
2032
+ <tr bgcolor="<?php echo $i % 2 == 0 ? '#FFCCCC' : '#CCCCFF'; ?>">
2033
+ <td><?php echo $i; ?></td>
2034
+ <td><?php echo htmlspecialchars($item); ?></td>
2035
+ </tr>
2036
+ <?php } ?>
2037
+ </tbody>
2038
+ </table>
2039
+ </body>
2040
+ </html>
2041
+ .====================
2042
+
2043
+ .# If you need template engine in pure PHP, try {{<phpTenjin|http://www.kuwata-lab.com/tenjin/>}} ({{<http://www.kuwata-lab.com/tenjin/>}}).
2044
+ .# phpTenjin is a very fast and full-featured template engine implemented in pure PHP.
2045
+
2046
+
2047
+ .$$ C | lang-c
2048
+
2049
+ .? example.ec
2050
+ .-------------------- example.ec
2051
+ {{*<%
2052
+ #include <stdio.h>
2053
+
2054
+ int main(int argc, char *argv[])
2055
+ {
2056
+ int i;
2057
+
2058
+ %>*}}
2059
+ <html>
2060
+ <body>
2061
+ <p>Hello {{*<%= "%s", argv[0] %>*}}!</p>
2062
+ <table>
2063
+ <tbody>
2064
+ {{*<% for (i = 1; i < argc; i++) { %>*}}
2065
+ <tr bgcolor="{{*<%= i % 2 == 0 ? "#FFCCCC" : "#CCCCFF" %>*}}">
2066
+ <td>{{*<%= "%d", i %>*}}</td>
2067
+ <td>{{*<%= "%s", argv[i] %>*}}</td>
2068
+ </tr>
2069
+ {{*<% } %>*}}
2070
+ </tbody>
2071
+ </table>
2072
+ </body>
2073
+ </html>
2074
+ {{*<%
2075
+ return 0;
2076
+ }
2077
+ %>*}}
2078
+ .--------------------
2079
+
2080
+ .? compiled source code
2081
+ .==================== example_c.result
2082
+ $ erubis -l c example.ec
2083
+ .#.<<<:! (cd guide.d; erubis -l c example.ec)
2084
+ #line 1 "example.ec"
2085
+
2086
+ #include <stdio.h>
2087
+
2088
+ int main(int argc, char *argv[])
2089
+ {
2090
+ int i;
2091
+
2092
+
2093
+ fputs("<html>\n"
2094
+ " <body>\n"
2095
+ " <p>Hello ", stdout); fprintf(stdout, "%s", argv[0]); fputs("!</p>\n"
2096
+ " <table>\n"
2097
+ " <tbody>\n", stdout);
2098
+ for (i = 1; i < argc; i++) {
2099
+ fputs(" <tr bgcolor=\"", stdout); fprintf(stdout, i % 2 == 0 ? "#FFCCCC" : "#CCCCFF"); fputs("\">\n"
2100
+ " <td>", stdout); fprintf(stdout, "%d", i); fputs("</td>\n"
2101
+ " <td>", stdout); fprintf(stdout, "%s", argv[i]); fputs("</td>\n"
2102
+ " </tr>\n", stdout);
2103
+ }
2104
+ fputs(" </tbody>\n"
2105
+ " </table>\n"
2106
+ " </body>\n"
2107
+ "</html>\n", stdout);
2108
+
2109
+ return 0;
2110
+ }
2111
+
2112
+ .====================
2113
+
2114
+
2115
+ .$$ C++ | lang-cpp
2116
+
2117
+ .? example.ecpp
2118
+ .-------------------- example.ecpp
2119
+ {{*<%
2120
+ #include <string>
2121
+ #include <iostream>
2122
+ #include <sstream>
2123
+
2124
+ int main(int argc, char *argv[])
2125
+ {
2126
+ std::stringstream _buf;
2127
+ %>*}}
2128
+ <html>
2129
+ <body>
2130
+ <p>Hello {{*<%= argv[0] %>*}}!</p>
2131
+ <table>
2132
+ <tbody>
2133
+ {{*<% for (int i = 1; i < argc; i++) { %>*}}
2134
+ <tr bgcolor="{{*<%= i % 2 == 0 ? "#FFCCCC" : "#CCCCFF" %>*}}">
2135
+ <td>{{*<%= i %>*}}</td>
2136
+ <td>{{*<%= argv[i] %>*}}</td>
2137
+ </tr>
2138
+ {{*<% } %>*}}
2139
+ </tbody>
2140
+ </table>
2141
+ </body>
2142
+ </html>
2143
+ {{*<%
2144
+ std::string output = _buf.str();
2145
+ std::cout << output;
2146
+ return 0;
2147
+ }
2148
+ %>*}}
2149
+ .--------------------
2150
+
2151
+ .? compiled source code
2152
+ .==================== example_c.result
2153
+ $ erubis -l cpp example.ecpp
2154
+ .#.<<<:! (cd guide.d; erubis -l cpp example.ecpp)
2155
+ #line 1 "example.ecpp"
2156
+
2157
+ #include <string>
2158
+ #include <iostream>
2159
+ #include <sstream>
2160
+
2161
+ int main(int argc, char *argv[])
2162
+ {
2163
+ std::stringstream _buf;
2164
+
2165
+ _buf << "<html>\n"
2166
+ " <body>\n"
2167
+ " <p>Hello "; _buf << (argv[0]); _buf << "!</p>\n"
2168
+ " <table>\n"
2169
+ " <tbody>\n";
2170
+ for (int i = 1; i < argc; i++) {
2171
+ _buf << " <tr bgcolor=\""; _buf << (i % 2 == 0 ? "#FFCCCC" : "#CCCCFF"); _buf << "\">\n"
2172
+ " <td>"; _buf << (i); _buf << "</td>\n"
2173
+ " <td>"; _buf << (argv[i]); _buf << "</td>\n"
2174
+ " </tr>\n";
2175
+ }
2176
+ _buf << " </tbody>\n"
2177
+ " </table>\n"
2178
+ " </body>\n"
2179
+ "</html>\n";
2180
+
2181
+ std::string output = _buf.str();
2182
+ std::cout << output;
2183
+ return 0;
2184
+ }
2185
+
2186
+ .====================
2187
+
2188
+
2189
+ .$$ Java | lang-java
2190
+
2191
+ .? Example.ejava
2192
+ .-------------------- Example.ejava
2193
+ {{*<%
2194
+ import java.util.*;
2195
+
2196
+ public class Example {
2197
+ private String user;
2198
+ private String[] list;
2199
+ public example(String user, String[] list) {
2200
+ this.user = user;
2201
+ this.list = list;
2202
+ }
2203
+
2204
+ public String view() {
2205
+ StringBuffer _buf = new StringBuffer();
2206
+ %>*}}
2207
+ <html>
2208
+ <body>
2209
+ <p>Hello {{*<%= user %>*}}!</p>
2210
+ <table>
2211
+ <tbody>
2212
+ {{*<% for (int i = 0; i < list.length; i++) { %>*}}
2213
+ <tr bgcolor={{*"<%= i % 2 == 0 ? "#FFCCCC" : "#CCCCFF" %>"*}}>
2214
+ <td>{{*<%= i + 1 %>*}}</td>
2215
+ <td>{{*<%== list[i] %>*}}</td>
2216
+ </tr>
2217
+ {{*<% } %>*}}
2218
+ </tbody>
2219
+ </table>
2220
+ <body>
2221
+ </html>
2222
+ {{*<%
2223
+ return _buf.toString();
2224
+ }
2225
+
2226
+ public static void main(String[] args) {
2227
+ String[] list = { "<aaa>", "b&b", "\"ccc\"" };
2228
+ Example ex = Example.new("Erubis", list);
2229
+ System.out.print(ex.view());
2230
+ }
2231
+
2232
+ public static String escape(String s) {
2233
+ StringBuffer sb = new StringBuffer();
2234
+ for (int i = 0; i < s.length(); i++) {
2235
+ char ch = s.charAt(i);
2236
+ switch (ch) {
2237
+ case '<': sb.append("&lt;"); break;
2238
+ case '>': sb.append("&gt;"); break;
2239
+ case '&': sb.append("&amp;"); break;
2240
+ case '"': sb.append("&quot;"); break;
2241
+ default: sb.append(ch);
2242
+ }
2243
+ }
2244
+ return sb.toString();
2245
+ }
2246
+ }
2247
+ %>*}}
2248
+ .--------------------
2249
+
2250
+ .? compiled source code
2251
+ .==================== example_java.result
2252
+ $ erubis -b -l java example.ejava
2253
+ .#.<<<:! (cd guide.d; erubis -l java example.ejava)
2254
+
2255
+ import java.util.*;
2256
+
2257
+ public class Example {
2258
+ private String user;
2259
+ private String[] list;
2260
+ public example(String user, String[] list) {
2261
+ this.user = user;
2262
+ this.list = list;
2263
+ }
2264
+
2265
+ public String view() {
2266
+ StringBuffer _buf = new StringBuffer();
2267
+
2268
+ _buf.append("<html>\n"
2269
+ + " <body>\n"
2270
+ + " <p>Hello "); _buf.append(user); _buf.append("!</p>\n"
2271
+ + " <table>\n"
2272
+ + " <tbody>\n");
2273
+ for (int i = 0; i < list.length; i++) {
2274
+ _buf.append(" <tr bgcolor=\""); _buf.append(i % 2 == 0 ? "#FFCCCC" : "#CCCCFF"); _buf.append("\">\n"
2275
+ + " <td>"); _buf.append(i + 1); _buf.append("</td>\n"
2276
+ + " <td>"); _buf.append(escape(list[i])); _buf.append("</td>\n"
2277
+ + " </tr>\n");
2278
+ }
2279
+ _buf.append(" </tbody>\n"
2280
+ + " </table>\n"
2281
+ + " <body>\n"
2282
+ + "</html>\n");
2283
+
2284
+ return _buf.toString();
2285
+ }
2286
+
2287
+ public static void main(String[] args) {
2288
+ String[] list = { "<aaa>", "b&b", "\"ccc\"" };
2289
+ Example ex = Example.new("Erubis", list);
2290
+ System.out.print(ex.view());
2291
+ }
2292
+
2293
+ public static String escape(String s) {
2294
+ StringBuffer sb = new StringBuffer();
2295
+ for (int i = 0; i < s.length(); i++) {
2296
+ char ch = s.charAt(i);
2297
+ switch (ch) {
2298
+ case '<': sb.append("&lt;"); break;
2299
+ case '>': sb.append("&gt;"); break;
2300
+ case '&': sb.append("&amp;"); break;
2301
+ case '"': sb.append("&quot;"); break;
2302
+ default: sb.append(ch);
2303
+ }
2304
+ }
2305
+ return sb.toString();
2306
+ }
2307
+ }
2308
+
2309
+ .====================
2310
+
2311
+
2312
+
2313
+ .$$ Scheme | lang-scheme
2314
+
2315
+ .? example.escheme
2316
+ .-------------------- example.escheme
2317
+ <html>
2318
+ <body>
2319
+ {{*<%
2320
+ (let ((user "Erubis")
2321
+ (items '("<aaa>" "b&b" "\"ccc\""))
2322
+ (i 0))
2323
+ %>*}}
2324
+ <p>Hello {{*<%= user %>*}}!</p>
2325
+ <table>
2326
+ {{*<%
2327
+ (for-each
2328
+ (lambda (item)
2329
+ (set! i (+ i 1))
2330
+ %>*}}
2331
+ <tr bgcolor="{{*<%= (if (= (modulo i 2) 0) "#FFCCCC" "#CCCCFF") %>*}}">
2332
+ <td>{{*<%= i %>*}}</td>
2333
+ <td>{{*<%= item %>*}}</td>
2334
+ </tr>
2335
+ {{*<%
2336
+ ) ; lambda end
2337
+ items) ; for-each end
2338
+ %>*}}
2339
+ </table>
2340
+ {{*<%
2341
+ ) ; let end
2342
+ %>*}}
2343
+ </body>
2344
+ </html>
2345
+ .--------------------
2346
+
2347
+ .? compiled source code
2348
+ .==================== example_scheme.result
2349
+ $ erubis -l scheme example.escheme
2350
+ .#.<<<:! (cd guide.d; erubis -l scheme example.escheme)
2351
+ (let ((_buf '())) (define (_add x) (set! _buf (cons x _buf))) (_add "<html>
2352
+ <body>\n")
2353
+
2354
+ (let ((user "Erubis")
2355
+ (items '("<aaa>" "b&b" "\"ccc\""))
2356
+ (i 0))
2357
+
2358
+ (_add " <p>Hello ")(_add user)(_add "!</p>
2359
+ <table>\n")
2360
+
2361
+ (for-each
2362
+ (lambda (item)
2363
+ (set! i (+ i 1))
2364
+
2365
+ (_add " <tr bgcolor=\"")(_add (if (= (modulo i 2) 0) "#FFCCCC" "#CCCCFF"))(_add "\">
2366
+ <td>")(_add i)(_add "</td>
2367
+ <td>")(_add item)(_add "</td>
2368
+ </tr>\n")
2369
+
2370
+ ) ; lambda end
2371
+ items) ; for-each end
2372
+
2373
+ (_add " </table>\n")
2374
+
2375
+ ) ; let end
2376
+
2377
+ (_add " </body>
2378
+ </html>\n")
2379
+ (reverse _buf))
2380
+ .====================
2381
+
2382
+ .? compiled source code (with {{,--func=display,}} property)
2383
+ .==================== example_scheme_display.result
2384
+ $ erubis -l scheme --func=display example.escheme
2385
+ .#.<<<:! (cd guide.d; erubis -l scheme --func=display example.escheme)
2386
+ (display "<html>
2387
+ <body>\n")
2388
+
2389
+ (let ((user "Erubis")
2390
+ (items '("<aaa>" "b&b" "\"ccc\""))
2391
+ (i 0))
2392
+
2393
+ (display " <p>Hello ")(display user)(display "!</p>
2394
+ <table>\n")
2395
+
2396
+ (for-each
2397
+ (lambda (item)
2398
+ (set! i (+ i 1))
2399
+
2400
+ (display " <tr bgcolor=\"")(display (if (= (modulo i 2) 0) "#FFCCCC" "#CCCCFF"))(display "\">
2401
+ <td>")(display i)(display "</td>
2402
+ <td>")(display item)(display "</td>
2403
+ </tr>\n")
2404
+
2405
+ ) ; lambda end
2406
+ items) ; for-each end
2407
+
2408
+ (display " </table>\n")
2409
+
2410
+ ) ; let end
2411
+
2412
+ (display " </body>
2413
+ </html>\n")
2414
+ .====================
2415
+
2416
+
2417
+
2418
+ .$$ Perl | lang-perl
2419
+
2420
+ .? example.eperl
2421
+ .-------------------- example.eperl
2422
+ {{*<%
2423
+ my $user = 'Erubis';
2424
+ my @list = ('<aaa>', 'b&b', '"ccc"');
2425
+ %>*}}
2426
+ <html>
2427
+ <body>
2428
+ <p>Hello {{*<%= $user %>*}}!</p>
2429
+ <table>
2430
+ {{*<% $i = 0; %>*}}
2431
+ {{*<% for $item (@list) { %>*}}
2432
+ <tr bgcolor={{*<%= ++$i % 2 == 0 ? '#FFCCCC' : '#CCCCFF' %>*}}">
2433
+ <td>{{*<%= $i %>*}}</td>
2434
+ <td>{{*<%= $item %>*}}</td>
2435
+ </tr>
2436
+ {{*<% } %>*}}
2437
+ </table>
2438
+ </body>
2439
+ </html>
2440
+ .--------------------
2441
+
2442
+ .? compiled source code
2443
+ .==================== example_perl.result
2444
+ $ erubis -l perl example.eperl
2445
+ .#.<<<:! (cd guide.d; erubis -l perl example.eperl)
2446
+ use HTML::Entities;
2447
+ my $user = 'Erubis';
2448
+ my @list = ('<aaa>', 'b&b', '"ccc"');
2449
+
2450
+ print('<html>
2451
+ <body>
2452
+ <p>Hello '); print($user); print('!</p>
2453
+ <table>
2454
+ '); $i = 0;
2455
+ for $item (@list) {
2456
+ print(' <tr bgcolor='); print(++$i % 2 == 0 ? '#FFCCCC' : '#CCCCFF'); print('">
2457
+ <td>'); print($i); print('</td>
2458
+ <td>'); print($item); print('</td>
2459
+ </tr>
2460
+ '); }
2461
+ print(' </table>
2462
+ </body>
2463
+ </html>
2464
+ ');
2465
+ .====================
2466
+
2467
+ .# If you need template engine in pure Perl, try {{<plTenjin|http://www.kuwata-lab.com/tenjin/>}} ({{<http://www.kuwata-lab.com/tenjin/>}}).
2468
+ .# plTenjin is a very fast and full-featured template engine implemented in pure Perl.
2469
+
2470
+
2471
+
2472
+ .$$ JavaScript | lang-javascript
2473
+
2474
+ .? example.ejs
2475
+ .-------------------- example.ejs
2476
+ {{*<%
2477
+ var user = 'Erubis';
2478
+ var list = ['<aaa>', 'b&b', '"ccc"'];
2479
+ %>*}}
2480
+ <html>
2481
+ <body>
2482
+ <p>Hello {{*<%= user %>*}}!</p>
2483
+ <table>
2484
+ <tbody>
2485
+ {{*<% var i; %>*}}
2486
+ {{*<% for (i = 0; i < list.length; i++) { %>*}}
2487
+ <tr bgcolor="{{*<%= i % 2 == 0 ? '#FFCCCC' : '#CCCCFF' %>*}}">
2488
+ <td>{{*<%= i + 1 %>*}}</td>
2489
+ <td>{{*<%= list[i] %>*}}</td>
2490
+ </tr>
2491
+ {{*<% } %>*}}
2492
+ </tbody>
2493
+ </table>
2494
+ </body>
2495
+ </html>
2496
+ .--------------------
2497
+
2498
+ .? compiled source code
2499
+ .==================== example_js.result
2500
+ $ erubis -l js example.ejs
2501
+ .#.<<<:! (cd guide.d; erubis -l js example.ejs)
2502
+ var _buf = [];
2503
+ var user = 'Erubis';
2504
+ var list = ['<aaa>', 'b&b', '"ccc"'];
2505
+
2506
+ _buf.push("<html>\n\
2507
+ <body>\n\
2508
+ <p>Hello "); _buf.push(user); _buf.push("!</p>\n\
2509
+ <table>\n\
2510
+ <tbody>\n");
2511
+ var i;
2512
+ for (i = 0; i < list.length; i++) {
2513
+ _buf.push(" <tr bgcolor=\""); _buf.push(i % 2 == 0 ? '#FFCCCC' : '#CCCCFF'); _buf.push("\">\n\
2514
+ <td>"); _buf.push(i + 1); _buf.push("</td>\n\
2515
+ <td>"); _buf.push(list[i]); _buf.push("</td>\n\
2516
+ </tr>\n");
2517
+ }
2518
+ _buf.push(" </tbody>\n\
2519
+ </table>\n\
2520
+ </body>\n\
2521
+ </html>\n");
2522
+ document.write(_buf.join(""));
2523
+ .====================
2524
+
2525
+ If command-line option '{{,--docwrite=false,}}' is specified,
2526
+ '{{,_buf.join("");,}}' is used instead of '{{,document.write(_buf.join(""));,}}'.
2527
+ This is useful when passing converted source code to eval() function in JavaScript.
2528
+
2529
+ You can pass {{,:docwrite=>false,}} to Erubis::Ejavascript.new() in your Ruby script.
2530
+
2531
+ .--------------------
2532
+ s = File.read('example.jshtml')
2533
+ engine = Erubis::Ejavascript.new(s, {{,:docwrite=>false,}})
2534
+ .--------------------
2535
+
2536
+ If you want to specify any JavaScript code, use '--postamble=...'.
2537
+
2538
+ Notice that default value of 'docwrite' property will be false in the future release.
2539
+
2540
+ .# If you need template engine in pure JavaScript, try {{<jsTenjin|http://www.kuwata-lab.com/tenjin/>}} ({{<http://www.kuwata-lab.com/tenjin/>}}).
2541
+ .# jsTenjin is a very fast and full-featured template engine implemented in pure JavaScript and available with not only web browser but also Spidermonkey and Rhino.
2542
+
2543
+
2544
+
2545
+ .$ Ruby on Rails Support | rails
2546
+
2547
+ {{!NOTICE: Rails 3 adopts Erubis as default default engine. You don't need to do anything at all when using Rails 3. This section is for Rails 2.!}}
2548
+
2549
+ Erubis supports Ruby on Rails.
2550
+ This section describes how to use Erubis with Ruby on Rails.
2551
+
2552
+
2553
+ .$$ Settings | rails-settings
2554
+
2555
+
2556
+ Add the following code to your 'config/environment.rb' and restart web server.
2557
+ This replaces ERB in Rails by Erubis entirely.
2558
+
2559
+ .? config/environment.rb
2560
+ .--------------------
2561
+ require 'erubis/helpers/rails_helper'
2562
+ #Erubis::Helpers::RailsHelper.engine_class = Erubis::Eruby # or Erubis::FastEruby
2563
+ #Erubis::Helpers::RailsHelper.init_properties = {}
2564
+ #Erubis::Helpers::RailsHelper.show_src = nil
2565
+ #Erubis::Helpers::RailsHelper.preprocessing = false
2566
+ .--------------------
2567
+
2568
+ Options:
2569
+
2570
+ .% Erubis::Helpers::RailsHelper.engine_class (=Erubis::Eruby)
2571
+ Erubis engine class (default Erubis::Eruby).
2572
+ .% Erubis::Helpers::RailsHelper.init_properties (={})
2573
+ Optional arguments for Erubis::Eruby#initialize() method (default {}).
2574
+ .% Erubis::Helpers::RailsHelper.show_src (=nil)
2575
+ Whether to print converted Ruby code into log file.
2576
+ If true, Erubis prints coverted code into log file.
2577
+ If false, Erubis doesn't.
2578
+ If nil, Erubis prints when ENV['RAILS_ENV'] == 'development'.
2579
+ Default is nil.
2580
+ .% Erubis::Helpers::RailsHelper.preprocessing (=false)
2581
+ Enable preprocessing if true (default false).
2582
+
2583
+
2584
+ .#.2) (Optional) apply the following patch to 'action_pack/lib/action_view/base.rb'.
2585
+ .#
2586
+ .# .? action_view_base_rb.patch
2587
+ .# .--------------------
2588
+ .# --- lib/action_view/base.rb (original)
2589
+ .# +++ lib/action_view/base.rb (working copy)
2590
+ .# @@ -445,6 +445,11 @@
2591
+ .# end
2592
+ .# end
2593
+ .#
2594
+ .# + # convert template into ruby code
2595
+ .# + def convert_template_into_ruby_code(template)
2596
+ .# + ERB.new(template, nil, @@erb_trim_mode).src
2597
+ .# + end
2598
+ .# +
2599
+ .# # Create source code for given template
2600
+ .# def create_template_source(extension, template, render_symbol, locals)
2601
+ .# if template_requires_setup?(extension)
2602
+ .# @@ -458,7 +463,7 @@
2603
+ .# "update_page do |page|\n#{template}\nend"
2604
+ .# end
2605
+ .# else
2606
+ .# - body = ERB.new(template, nil, @@erb_trim_mode).src
2607
+ .# + body = convert_template_into_ruby_code(template)
2608
+ .# end
2609
+ .#
2610
+ .# @@template_args[render_symbol] ||= {}
2611
+ .# .--------------------
2612
+ .#
2613
+ .# This patch is included in erubis_2.X.X/contrib directory and the following is an
2614
+ .# example to apply this patch.
2615
+ .#
2616
+ .# .? how to apply patch:
2617
+ .# .====================
2618
+ .# $ cd /usr/local/lib/ruby/gems/1.8/gems/actionpack-1.13.1/lib/action_view/
2619
+ .# $ sudo patch -p1 < /tmp/erubis_2.X.X/contrib/action_view_base_rb.patch
2620
+ .# .====================
2621
+ .#
2622
+ .# Notice that this patch is not necessary if you are using Ruby on Rails ver 1.1 or 1.2, but it is recommended.
2623
+ .#
2624
+ .#.2) Restart web server.
2625
+ .# .====================
2626
+ .# $ ruby script/server
2627
+ .# .====================
2628
+ .#
2629
+ .#The setting is above all.
2630
+
2631
+
2632
+
2633
+ .$$ Preprosessing | rails-preprocessing
2634
+
2635
+ Erubis supports preprocessing of template files.
2636
+ Preprocessing make your Ruby on Rails application about 20-40 percent faster.
2637
+ To enable preprocessing, set Erubis::Helpers::RailsHelper.preprocessing to true in your 'environment.rb' file.
2638
+
2639
+ For example, assume the following template.
2640
+ This is slow because link_to() method is called every time when template is rendered.
2641
+
2642
+ .--------------------
2643
+ <%= link_to 'Create', :action=>'create' %>
2644
+ .--------------------
2645
+
2646
+ The following is faster than the above, but not flexible because url is fixed.
2647
+
2648
+ .--------------------
2649
+ <a href="/users/create">Create</a>
2650
+ .--------------------
2651
+
2652
+ Preprocessing solves this problem.
2653
+ If you use '[%= %]' instead of '<%= %>', preprocessor evaluate it only once when template is loaded.
2654
+
2655
+ .--------------------
2656
+ {{*[%= link_to 'Create', :action=>'create'%]*}}
2657
+ .--------------------
2658
+
2659
+ The above is evaluated by preprocessor and replaced to the following code automatically.
2660
+
2661
+ .--------------------
2662
+ <a href="/users/create">Create</a>
2663
+ .--------------------
2664
+
2665
+ Notice that this is done only once when template file is loaded.
2666
+ It means that link_to() method is not called when template is rendered.
2667
+
2668
+ If link_to() method have variable arguments, use {{,_?(),}} helper method.
2669
+
2670
+ .--------------------
2671
+ <% for user in @users %>
2672
+ [%= link_to {{*_?('user.name')*}}, :action=>'show', :id=>{{*_?('user.id')*}} %]
2673
+ <% end %>
2674
+ .--------------------
2675
+
2676
+ The above is evaluated by preprocessor when template is loaded and expanded into the following code.
2677
+ This will be much faster because link_to() method is not called when rendering.
2678
+
2679
+ .--------------------
2680
+ <% for user in @users %>
2681
+ <a href="/users/show/{{*<%=user.id%>*}}">{{*<%=user.name%>*}}</a>
2682
+ <% end %>
2683
+ .--------------------
2684
+
2685
+ Preprocessing statement ({{,[% %],}}) is also available as well as preprocessing expression ({{,[%= %],}}).
2686
+ .--------------------
2687
+ <select name="state">
2688
+ <option value="">-</option>
2689
+ {{*[% for code in states.keys.sort %]*}}
2690
+ <option value="{{*[%= code %]*}}">{{*[%= states[code] %]*}}</option>
2691
+ {{*[% end %]*}}
2692
+ </select>
2693
+ .--------------------
2694
+
2695
+ The above will be evaluated by preprocessor and expanded into the following when template is loaded.
2696
+ In the result, rendering speed will be much faster because for-loop is not executed when rendering.
2697
+ .--------------------
2698
+ <select name="state">
2699
+ <option value="">-</option>
2700
+ <option value="AK">Alaska</option>
2701
+ <option value="AL">Alabama</option>
2702
+ <option value="AR">Arkansas</option>
2703
+ <option value="AS">American Samoa</option>
2704
+ <option value="AZ">Arizona</option>
2705
+ <option value="CA">California</option>
2706
+ <option value="CO">Colorado</option>
2707
+ ....
2708
+ </select>
2709
+ .--------------------
2710
+
2711
+ Notice that it is not recommended to use preprocessing with tag helpers,
2712
+ because tag helpers generate different html code when form parameter has errors or not.
2713
+
2714
+ Helper methods of Ruby on Rails are divided into two groups.
2715
+ .* link_to() or _() (method of gettext package) are not need to call for every time
2716
+ as template is rendered because it returns same value when same arguments are passed.
2717
+ These methods can be got faster by preprocessing.
2718
+ .* Tag helper methods should be called for every time as template is rendered
2719
+ because it may return differrent value even if the same arguments are passed.
2720
+ Preprocessing is not available with these methods.
2721
+
2722
+ In Ruby on Rails 2.0, {{,_?('user_id'),}} is OK but {{,_?('user.id'),}} is NG
2723
+ because the latter contains period ('.') character.
2724
+
2725
+ .--------------------
2726
+ <!-- NG in Rails 2.0, because _?('') contains period -->
2727
+ [%= link_to 'Edit', edit_user_path({{*_?('@user.id')*}}) %]
2728
+ [%= link_to 'Show', {{*@user*}} %]
2729
+ [%= link_to 'Delete', {{*@user*}}, :confirm=>'OK?', :method=>:delete %]
2730
+
2731
+ <!-- OK in Rails 2.0 -->
2732
+ {{*<%= user_id = @user.id %>*}}
2733
+ [%= link_to 'Edit', edit_user_path({{*_?('user_id')*}}) %]
2734
+ [%= link_to 'Show', {{*:action=>'show', :id=>_?('user_id')*}} %]
2735
+ [%= link_to 'Delete', {{*{:action=>'destroy', :id=>_?('user_id')}*}},
2736
+ {:confirm=>'OK?', :method=>:delete} %]
2737
+ .--------------------
2738
+
2739
+
2740
+ .$$ Form Helpers for Preprocessing | rails-formhelpers
2741
+
2742
+ {{*(Experimental)*}}
2743
+
2744
+ Erubis provides form helper methods for preprocessing.
2745
+ These are defined in 'erubis/helpers/rails_form_helper.rb'.
2746
+ If you want to use it, require it and include Erubis::Helpers::RailsFormHelper in 'app/helpers/applition_helper.rb'
2747
+
2748
+ .? app/helpers/xxx_helper.rb
2749
+ .--------------------
2750
+ require 'erubis/helpers/rails_form_helper'
2751
+ module ApplicationHelper
2752
+ include Erubis::Helpers::RailsFormHelper
2753
+ end
2754
+ .--------------------
2755
+
2756
+ Form helper methods defined in Erubis::Helpers::RailsFormHelper are named as 'pp_xxxx'
2757
+ ('pp' represents preprocessing).
2758
+
2759
+ Assume the following view template:
2760
+
2761
+ .? _form.rhtml
2762
+ .--------------------
2763
+ <p>
2764
+ Name: <%= text_field :user, :name %>
2765
+ </p>
2766
+ <p>
2767
+ Name: {{*[%= pp_text_field :user, :name %]*}}
2768
+ </p>
2769
+ .--------------------
2770
+
2771
+ Erubis preprocessor converts it to the following eRuby string:
2772
+
2773
+ .? preprocessed
2774
+ .--------------------
2775
+ <p>
2776
+ Name: <%= text_field :user, :name %>
2777
+ </p>
2778
+ <p>
2779
+ Name: {{*<input id="stock_name" name="stock[name]" size="30" type="text" value="<%=h @stock.name%>" />*}}
2780
+ </p>
2781
+ .--------------------
2782
+
2783
+ Erubis converts it to the following Ruby code:
2784
+
2785
+ .? Ruby code
2786
+ .--------------------
2787
+ _buf << ' <p>
2788
+ Name: '; _buf << ( text_field :stock, :name ).to_s; _buf << '
2789
+ '; _buf << ' </p>
2790
+ <p>
2791
+ Name: <input id="stock_name" name="stock[name]" size="30" type="text" value="'; _buf << (h @stock.name).to_s; _buf << '" />
2792
+ </p>
2793
+ ';
2794
+ .--------------------
2795
+
2796
+ The above Ruby code shows that text_field() is called everytime when rendering,
2797
+ but pp_text_field() is called only once when template is loaded.
2798
+ This means that pp_text_field() with preprocessing makes view layer very fast.
2799
+
2800
+ Module Erubis::Helpers::RailsFormHelper defines the following form helper methods.
2801
+
2802
+ .* pp_render_partial(basename)
2803
+ .* pp_form_tag(url_for_options={}, options={}, *parameters_for_url, &block)
2804
+ .* pp_text_field(object_name, method, options={})
2805
+ .* pp_password_field(object_name, method, options={})
2806
+ .* pp_hidden_field(object_name, method, options={})
2807
+ .* pp_file_field(object_name, method, options={})
2808
+ .* pp_text_area(object_name, method, options={})
2809
+ .* pp_check_box(object_name, method, options={}, checked_value="1", unchecked_value="0")
2810
+ .* pp_radio_button(object_name, method, tag_value, options={})
2811
+ .* pp_select(object, method, collection, options={}, html_options={})
2812
+ .* pp_collection_select(object, method, collection, value_method, text_method, options={}, html_options={})
2813
+ .* pp_country_select(object, method, priority_countries=nil, options={}, html_options={})
2814
+ .* pp_time_zone_select(object, method, priority_zones=nil, options={}, html_options={})
2815
+ .* pp_submit_tag(value="Save changes", options={})
2816
+ .* pp_image_submit_tag(source, options={})
2817
+
2818
+ Notice that pp_form_for() is not provided.
2819
+
2820
+ {{!CAUTION:!}} These are experimental and may not work in Ruby on Rails 2.0.
2821
+
2822
+
2823
+ .$$ Others | rails-others
2824
+
2825
+ .* ActionView::Helpers::CaptureHelper#capture() and ActionView::Helpers::Texthelper#concat() are available.
2826
+
2827
+ .* Form helper methods are not tested in Ruby on Rails 2.0.
2828
+
2829
+ .* ERB::Util.h() is redefined if you require 'erubis/helpers/rails_helper.rb'.
2830
+ Original definition of ERB::Util.h() is the following and it is slow
2831
+ because it scans string four times.
2832
+
2833
+ .--------------------
2834
+ def html_escape(s)
2835
+ s.to_s.gsub(/&/, "&amp;").gsub(/\"/, "&quot;").gsub(/>/, "&gt;").gsub(/</, "&lt;")
2836
+ end
2837
+ alias h html_escape
2838
+ .--------------------
2839
+
2840
+ New definition in 'erubis/helpers/rails_helper.rb' is faster than the above
2841
+ because it scans string only once.
2842
+
2843
+ .--------------------
2844
+ ESCAPE_TABLE = { '&'=>'&amp;', '<'=>'&lt;', '>'=>'&gt;', '"'=>'&quot;', "'"=>'&#039;', }
2845
+ def h(value)
2846
+ value.to_s.gsub(/[&<>"]/) { |s| ESCAPE_TABLE[s] }
2847
+ end
2848
+ .--------------------
2849
+
2850
+ Notice that the new definition may be slow if string contains
2851
+ many '< > & "' characters because block is call many time.
2852
+ You should use ERB::Util.html_hscape() if string contains a lot of '< > & "'
2853
+ characters.
2854
+
2855
+
2856
+
2857
+ .$ Other Topics | topics
2858
+
2859
+
2860
+ .$$ {{,Erubis::FastEruby,}} Class | topics-fasteruby
2861
+
2862
+ {{,Erubis::FastEruby,}} class generates more effective code than {{,Erubis::Eruby,}}.
2863
+
2864
+ .? fasteruby-example.rb
2865
+ .-------------------- fasteruby-example.rb
2866
+ require 'erubis'
2867
+ input = File.read('example.eruby')
2868
+
2869
+ puts "----- Erubis::Eruby -----"
2870
+ print Erubis::Eruby.new(input).src
2871
+
2872
+ puts "----- Erubis::FastEruby -----"
2873
+ print {{*Erubis::FastEruby*}}.new(input).src
2874
+ .--------------------
2875
+
2876
+ .? result
2877
+ .==================== fasteruby-example.result
2878
+ $ ruby fasteruby-example.rb
2879
+ ----- Erubis::Eruby -----
2880
+ _buf = ''; _buf << '<div>
2881
+ '; for item in list
2882
+ _buf << ' <p>'; {{*_buf << ( item ).to_s;*}} _buf << '</p>
2883
+ <p>'; {{*_buf << Erubis::XmlHelper.escape_xml( item );*}} _buf << '</p>
2884
+ '; end
2885
+ _buf << '</div>
2886
+ ';
2887
+ _buf.to_s
2888
+ ----- Erubis::FastEruby -----
2889
+ _buf = ''; _buf << %Q`<div>\n`
2890
+ for item in list
2891
+ _buf << %Q` <p>{{*#{ item }*}}</p>
2892
+ <p>{{*#{Erubis::XmlHelper.escape_xml( item )}*}}</p>\n`
2893
+ end
2894
+ _buf << %Q`</div>\n`
2895
+ _buf.to_s
2896
+ .====================
2897
+
2898
+ Technically, {{,Erubis::FastEruby,}} is just a subclass of {{,Erubis::Eruby,}} and includes {{,{{<InterpolationEnhancer|#interpolation-enhancer>}},}}. {{,Erubis::FastEruby,}} is faster than {{,Erubis::Eruby,}} but is not extensible compared to {{,Erubis::Eruby,}}. This is the reason why {{,Erubis::FastEruby,}} is not the default class of Erubis.
2899
+
2900
+
2901
+ .$$ {{,:bufvar,}} Option | topics-bufvar
2902
+
2903
+ Since 2.7.0, Erubis supports {{,:bufvar,}} option which allows you to change buffer variable name (default '{{,_buf,}}').
2904
+
2905
+ .? bufvar-example.rb
2906
+ .-------------------- bufvar-example.rb
2907
+ require 'erubis'
2908
+ input = File.read('example.eruby')
2909
+
2910
+ puts "----- default -----"
2911
+ eruby = Erubis::FastEruby.new(input)
2912
+ puts eruby.src
2913
+
2914
+ puts "----- with :bufvar option -----"
2915
+ eruby = Erubis::FastEruby.new(input, {{*:bufvar=>'@_out_buf'*}})
2916
+ print eruby.src
2917
+ .--------------------
2918
+
2919
+ .? result
2920
+ .==================== bufvar-example.result
2921
+ $ ruby bufvar-example.rb
2922
+ ----- default -----
2923
+ _buf = ''; _buf << %Q`<div>\n`
2924
+ for item in list
2925
+ _buf << %Q` <p>#{ item }</p>
2926
+ <p>#{Erubis::XmlHelper.escape_xml( item )}</p>\n`
2927
+ end
2928
+ _buf << %Q`</div>\n`
2929
+ _buf.to_s
2930
+ ----- with :bufvar option -----
2931
+ {{*@_out_buf*}} = ''; {{*@_out_buf*}} << %Q`<div>\n`
2932
+ for item in list
2933
+ {{*@_out_buf*}} << %Q` <p>#{ item }</p>
2934
+ <p>#{Erubis::XmlHelper.escape_xml( item )}</p>\n`
2935
+ end
2936
+ {{*@_out_buf*}} << %Q`</div>\n`
2937
+ {{*@_out_buf*}}.to_s
2938
+ .====================
2939
+
2940
+
2941
+ .$$ '<%= =%>' and '<%= -%>' | topics-trimspaces
2942
+
2943
+ Since 2.6.0, '<%= -%>' remove tail spaces and newline.
2944
+ This is for compatibiliy with ERB when trim mode is '-'.
2945
+ '<%= =%>' also removes tail spaces and newlines, and this is
2946
+ Erubis-original enhancement (cooler than '<%= -%>', isn't it?).
2947
+
2948
+ .? tailnewline.rhtml
2949
+ .-------------------- tailnewline.rhtml.comment_filter
2950
+ <div>
2951
+ <%= @var -%> # or <%= @var =%>
2952
+ </div>
2953
+ .--------------------
2954
+
2955
+ .? result (version 2.5.0):
2956
+ .====================
2957
+ $ erubis -c '{var: "AAA\n"}' tailnewline.rhtml
2958
+ <div>
2959
+ AAA
2960
+
2961
+ </div>
2962
+ .====================
2963
+
2964
+ .? result (version 2.6.0):
2965
+ .==================== tail_260.result
2966
+ $ erubis -c '{var: "AAA\n"}' tailnewline.rhtml
2967
+ <div>
2968
+ AAA
2969
+ </div>
2970
+ .====================
2971
+
2972
+
2973
+ .$$ '<%% %>' and '<%%= %>' | topics-doublepercent
2974
+
2975
+ Since 2.6.0, '<%% %>' and '<%%= %>' are converted into '<% %>' and '<%= %>' respectively.
2976
+ This is for compatibility with ERB.
2977
+
2978
+ .? doublepercent.rhtml:
2979
+ .--------------------
2980
+ <ul>
2981
+ <%% for item in @list %>
2982
+ <li><%%= item %></li>
2983
+ <%% end %>
2984
+ </ul>
2985
+ .--------------------
2986
+
2987
+ .? result:
2988
+ .====================
2989
+ $ erubis doublepercent.rhtml
2990
+ <ul>
2991
+ <% for item in @list %>
2992
+ <li><%= item %></li>
2993
+ <% end %>
2994
+ </ul>
2995
+ .====================
2996
+
2997
+
2998
+
2999
+ .$$ evaluate(context) v.s. result(binding) | topics-context-vs-binding
3000
+
3001
+ It is recommended to use 'Erubis::Eruby#evaluate(context)' instead of 'Erubis::Eruby#result(binding)' because Ruby's Binding object has some problems.
3002
+
3003
+ .* It is not able to specify variables to use.
3004
+ Using binding() method, all of local variables are passed to templates.
3005
+ .* Changing local variables in templates may affect to varialbes in main program.
3006
+ If you assign '10' to local variable 'x' in templates, it may change variable 'x' in main program unintendedly.
3007
+
3008
+ The following example shows that assignment of some values into variable 'x' in templates affect to local variable 'x' in main program unintendedly.
3009
+
3010
+ .? template1.rhtml (intended to be passed 'items' from main program)
3011
+ .-------------------- template1.rhtml
3012
+ <% for {{*x*}} in {{*items*}} %>
3013
+ item = <%= x %>
3014
+ <% end %>
3015
+ ** debug: local variables=<%= local_variables().inspect() %>
3016
+ .--------------------
3017
+
3018
+ .? main_program1.rb (intended to pass 'items' to template)
3019
+ .-------------------- main_program1.rb
3020
+ require 'erubis'
3021
+ eruby = Erubis::Eruby.new(File.read('template1.rhtml'))
3022
+ items = ['foo', 'bar', 'baz']
3023
+ x = 1
3024
+ ## local variable 'x' and 'eruby' are passed to template as well as 'items'!
3025
+ print {{*eruby.result(binding())*}}
3026
+ ## local variable 'x' is changed unintendedly because it is changed in template!
3027
+ puts "** debug: x=#{x.inspect}" #=> "baz"
3028
+ .--------------------
3029
+
3030
+ .? Result:
3031
+ .==================== main_program1.result
3032
+ $ ruby main_program1.rb
3033
+ item = foo
3034
+ item = bar
3035
+ item = baz
3036
+ ** debug: local variables=["eruby", "items", "x", "_buf"]
3037
+ ** debug: x="baz"
3038
+ .====================
3039
+
3040
+ This problem is caused because Ruby's Binding class is poor to use in template engine.
3041
+ Binding class should support the following features.
3042
+
3043
+ .--------------------
3044
+ b = Binding.new # create empty Binding object
3045
+ b['x'] = 1 # set local variables using binding object
3046
+ .--------------------
3047
+
3048
+ But the above features are not implemented in Ruby.
3049
+
3050
+ A pragmatic solution is to use 'Erubis::Eruby#evaluate(context)' instead of 'Erubis::Eruby#result(binding)'.
3051
+ 'evaluate(context)' uses Erubis::Context object and instance variables instead of Binding object and local variables.
3052
+
3053
+ .? template2.rhtml (intended to be passed '@items' from main program)
3054
+ .-------------------- template2.rhtml
3055
+ <% for {{*x*}} in {{*@items*}} %>
3056
+ item = <%= x %>
3057
+ <% end %>
3058
+ ** debug: local variables=<%= local_variables().inspect() %>
3059
+ .--------------------
3060
+
3061
+ .? main_program2.rb (intended to pass '@items' to template)
3062
+ .-------------------- main_program2.rb
3063
+ require 'erubis'
3064
+ eruby = Erubis::Eruby.new(File.read('template2.rhtml'))
3065
+ items = ['foo', 'bar', 'baz']
3066
+ x = 1
3067
+ ## only 'items' are passed to template
3068
+ print {{*eruby.evaluate(:items=>items)*}}
3069
+ ## local variable 'x' is not changed!
3070
+ puts "** debug: x=#{x.inspect}" #=> 1
3071
+ .--------------------
3072
+
3073
+ .? Result:
3074
+ .==================== main_program2.result
3075
+ $ ruby main_program2.rb
3076
+ item = foo
3077
+ item = bar
3078
+ item = baz
3079
+ ** debug: local variables=["_context", "x", "_buf"]
3080
+ ** debug: x=1
3081
+ .====================
3082
+
3083
+
3084
+
3085
+ .$$ Class Erubis::FastEruby | topics-fasteruby
3086
+
3087
+ [experimental]
3088
+
3089
+ Erubis provides Erubis::FastEruby class which includes {{<InterpolationEnhancer|#interpolation-enhancer>}} and {{<works faster than Erubis::Eruby class|#topics-benchmark>}}.
3090
+ If you desire more speed, try Erubis::FastEruby class.
3091
+
3092
+ .? File 'fasteruby.rhtml':
3093
+ .-------------------- fasteruby.rhtml
3094
+ <html>
3095
+ <body>
3096
+ <h1><%== @title %></h1>
3097
+ <table>
3098
+ <% i = 0 %>
3099
+ <% for item in @list %>
3100
+ <% i += 1 %>
3101
+ <tr>
3102
+ <td><%= i %></td>
3103
+ <td><%== item %></td>
3104
+ </tr>
3105
+ <% end %>
3106
+ </table>
3107
+ </body>
3108
+ </html>
3109
+ .--------------------
3110
+
3111
+
3112
+ .? File 'fasteruby.rb':
3113
+ .-------------------- fasteruby.rb
3114
+ require 'erubis'
3115
+ input = File.read('fasteruby.rhtml')
3116
+ eruby = {{*Erubis::FastEruby.new(input)*}} # create Eruby object
3117
+
3118
+ puts "---------- script source ---"
3119
+ puts eruby.src
3120
+
3121
+ puts "---------- result ----------"
3122
+ context = { :title=>'Example', :list=>['aaa', 'bbb', 'ccc'] }
3123
+ output = eruby.evaluate(context)
3124
+ print output
3125
+ .--------------------
3126
+
3127
+ .? output
3128
+ .==================== fasteruby.result
3129
+ $ ruby fasteruby.rb
3130
+ ---------- script source ---
3131
+ _buf = ''; _buf << {{*%Q`*}}<html>
3132
+ <body>
3133
+ <h1>{{*#{Erubis::XmlHelper.escape_xml( @title )}*}}</h1>
3134
+ <table>\n{{*`*}}
3135
+ i = 0
3136
+ for item in @list
3137
+ i += 1
3138
+ _buf << {{*%Q`*}} <tr>
3139
+ <td>{{*#{ i }*}}</td>
3140
+ <td>{{*#{Erubis::XmlHelper.escape_xml( item )}*}}</td>
3141
+ </tr>\n{{*`*}}
3142
+ end
3143
+ _buf << {{*%Q`*}} </table>
3144
+ </body>
3145
+ </html>\n{{*`*}}
3146
+ _buf.to_s
3147
+ ---------- result ----------
3148
+ <html>
3149
+ <body>
3150
+ <h1>Example</h1>
3151
+ <table>
3152
+ <tr>
3153
+ <td>1</td>
3154
+ <td>aaa</td>
3155
+ </tr>
3156
+ <tr>
3157
+ <td>2</td>
3158
+ <td>bbb</td>
3159
+ </tr>
3160
+ <tr>
3161
+ <td>3</td>
3162
+ <td>ccc</td>
3163
+ </tr>
3164
+ </table>
3165
+ </body>
3166
+ </html>
3167
+ .====================
3168
+
3169
+
3170
+
3171
+ .$$ Syntax Checking | topics-syntax
3172
+
3173
+ Command-line option '-z' checks syntax. It is similar to 'erubis -x file.rhtml | ruby -wc', but it can take several file names.
3174
+
3175
+ .? example of command-line option '-z'
3176
+ .====================
3177
+ $ erubis {{*-z*}} app/views/*/*.rhtml
3178
+ Syntax OK
3179
+ .====================
3180
+
3181
+
3182
+
3183
+ .$$ File Caching | topics-caching
3184
+
3185
+ Erubis::Eruby.load_file(filename) convert file into Ruby script and return Eruby object.
3186
+ In addition, it caches converted Ruby script into cache file (filename + '.cache') if cache file is old or not exist.
3187
+ If cache file exists and is newer than eruby file, Erubis::Eruby.load_file() loads cache file.
3188
+
3189
+ .? example of Erubis::Eruby.load_file()
3190
+ .--------------------
3191
+ require 'erubis'
3192
+ filename = 'example.rhtml'
3193
+ eruby = {{*Erubis::Eruby.load_file(filename)*}}
3194
+ cachename = filename + '.cache'
3195
+ if test(?f, cachename)
3196
+ puts "*** cache file '#{cachename}' created."
3197
+ end
3198
+ .--------------------
3199
+
3200
+ Since 2.6.0, it is able to specify cache filename.
3201
+
3202
+ .? specify cache filename.
3203
+ .--------------------
3204
+ filename = 'example.rhtml'
3205
+ eruby = Erubis::Eruby.load_file(filename, :cachename=>filename+'.cache')
3206
+ .--------------------
3207
+
3208
+ Caching makes Erubis about 40-50 percent faster than no-caching.
3209
+ See {{<benchmark|#topics-benchmark>}} for details.
3210
+
3211
+
3212
+
3213
+ .$$ Erubis::TinyEruby class | topics-tinyeruby
3214
+
3215
+ Erubis::TinyEruby class in 'erubis/tiny.rb' is the smallest implementation of eRuby.
3216
+ If you don't need any enhancements of Erubis and only require simple eRuby implementation,
3217
+ try Erubis::TinyEruby class.
3218
+
3219
+
3220
+
3221
+ .$$ NoTextEnhancer and NoCodeEnhancer in PHP | topics-php
3222
+
3223
+ NoTextEnhancer and NoCodEnahncer are quite useful not only for eRuby but also for PHP.
3224
+ The former "drops" HTML text and show up embedded Ruby/PHP code
3225
+ and the latter drops embedded Ruby/PHP code and leave HTML text.
3226
+
3227
+ For example, see the following PHP script.
3228
+
3229
+ .? notext-example.php
3230
+ .-------------------- notext-example.php
3231
+ <html>
3232
+ <body>
3233
+ <h3>List</h3>
3234
+ <?php if (!$list || count($list) == 0) { ?>
3235
+ <p>not found.</p>
3236
+ <?php } else { ?>
3237
+ <table>
3238
+ <tbody>
3239
+ <?php $i = 0; ?>
3240
+ <?php foreach ($list as $item) { ?>
3241
+ <tr bgcolor="<?php echo ++$i % 2 == 1 ? '#FFCCCC' : '#CCCCFF'; ?>">
3242
+ <td><?php echo $item; ?></td>
3243
+ </tr>
3244
+ <?php } ?>
3245
+ </tbody>
3246
+ </table>
3247
+ <?php } ?>
3248
+ </body>
3249
+ </html>
3250
+ .--------------------
3251
+
3252
+ This is complex because PHP code and HTML document are mixed.
3253
+ NoTextEnhancer can separate PHP code from HTML document.
3254
+
3255
+ .? example of using NoTextEnhancer with PHP file
3256
+ .==================== notext-php.result
3257
+ $ erubis -l php --pi=php -N -E NoText --trim=false notext-example.php
3258
+ 1:
3259
+ 2:
3260
+ 3:
3261
+ 4: <?php if (!$list || count($list) == 0) { ?>
3262
+ 5:
3263
+ 6: <?php } else { ?>
3264
+ 7:
3265
+ 8:
3266
+ 9: <?php $i = 0; ?>
3267
+ 10: <?php foreach ($list as $item) { ?>
3268
+ 11: <?php echo ++$i % 2 == 1 ? '#FFCCCC' : '#CCCCFF'; ?>
3269
+ 12: <?php echo $item; ?>
3270
+ 13:
3271
+ 14: <?php } ?>
3272
+ 15:
3273
+ 16:
3274
+ 17: <?php } ?>
3275
+ 18:
3276
+ 19:
3277
+ .====================
3278
+
3279
+ In the same way, NoCodeEnhancer can extract HTML tags.
3280
+
3281
+ .? example of using NoCodeEnhancer with PHP file
3282
+ .==================== nocode-php.result
3283
+ $ erubis -l php --pi=php -N -E NoCode --trim=false notext-example.php
3284
+ 1: <html>
3285
+ 2: <body>
3286
+ 3: <h3>List</h3>
3287
+ 4:
3288
+ 5: <p>not found.</p>
3289
+ 6:
3290
+ 7: <table>
3291
+ 8: <tbody>
3292
+ 9:
3293
+ 10:
3294
+ 11: <tr bgcolor="">
3295
+ 12: <td></td>
3296
+ 13: </tr>
3297
+ 14:
3298
+ 15: </tbody>
3299
+ 16: </table>
3300
+ 17:
3301
+ 18: </body>
3302
+ 19: </html>
3303
+ .====================
3304
+
3305
+
3306
+
3307
+ .$$ Helper Class for mod_ruby | topcs-modruby
3308
+
3309
+ Thanks Andrew R Jackson, he developed 'erubis-run.rb' which enables you to use Erubis with mod_ruby.
3310
+
3311
+ .1) Copy 'erubis-$Release$/contrib/erubis-run.rb' to the 'RUBYLIBDIR/apache' directory (for example '/usr/local/lib/ruby/1.8/apache') which contains 'ruby-run.rb', 'eruby-run.rb', and so on.
3312
+ .====================
3313
+ $ cd erubis-$Release$/
3314
+ $ sudo copy contrib/erubis-run.rb /usr/local/lib/ruby/1.8/apache/
3315
+ .====================
3316
+ .2) Add the following example to your 'httpd.conf' (for example '/usr/local/apache2/conf/httpd.conf')
3317
+ .--------------------
3318
+ LoadModule ruby_module modules/mod_ruby.so
3319
+ <IfModule mod_ruby.c>
3320
+ RubyRequire apache/ruby-run
3321
+ RubyRequire apache/eruby-run
3322
+ RubyRequire apache/erubis-run
3323
+ <Location /erubis>
3324
+ SetHandler ruby-object
3325
+ RubyHandler Apache::ErubisRun.instance
3326
+ </Location>
3327
+ <Files *.rhtml>
3328
+ SetHandler ruby-object
3329
+ RubyHandler Apache::ErubisRun.instance
3330
+ </Files>
3331
+ </IfModule>
3332
+ .--------------------
3333
+ .3) Restart Apache web server.
3334
+ .====================
3335
+ $ sudo /usr/local/apache2/bin/apachectl stop
3336
+ $ sudo /usr/local/apache2/bin/apachectl start
3337
+ .====================
3338
+ .4) Create *.rhtml file, for example:
3339
+ .--------------------
3340
+ <html>
3341
+ <body>
3342
+ Now is <%= Time.now %>
3343
+ Erubis version is <%= Erubis::VERSION %>
3344
+ </body>
3345
+ </html>
3346
+ .--------------------
3347
+ .5) Change mode of your directory to be writable by web server process.
3348
+ .====================
3349
+ $ cd /usr/local/apache2/htdocs/erubis
3350
+ $ sudo chgrp daemon .
3351
+ $ sudo chmod 775 .
3352
+ .====================
3353
+ .6) Access the *.rhtml file and you'll get the web page.
3354
+
3355
+ You must set your directories to be writable by web server process, because
3356
+ Apache::ErubisRun calls Erubis::Eruby.load_file() internally which creates cache files
3357
+ in the same directory in which '*.rhtml' file exists.
3358
+
3359
+
3360
+ .$$ Helper CGI Script for Apache | topics-index-cgi
3361
+
3362
+ Erubis provides helper CGI script for Apache.
3363
+ Using this script, it is very easy to publish *.rhtml files as *.html.
3364
+
3365
+ .====================
3366
+ ### install Erubis
3367
+ $ tar xzf erubis-X.X.X.tar.gz
3368
+ $ cd erubis-X.X.X/
3369
+ $ ruby setup.py install
3370
+ ### copy files to ~/public_html
3371
+ $ mkdir -p ~/public_html
3372
+ $ cp public_html/_htaccess ~/public_html/.htaccess
3373
+ $ cp public_html/index.cgi ~/public_html/
3374
+ $ cp public_html/index.rhtml ~/public_html/
3375
+ ### add executable permission to index.cgi
3376
+ $ chmod a+x ~/public_html/index.cgi
3377
+ ### edit .htaccess
3378
+ $ vi ~/public_html/.htaccess
3379
+ ### (optional) edit index.cgi to configure
3380
+ $ vi ~/public_html/index.cgi
3381
+ .====================
3382
+
3383
+ Edit ~/public_html/.htaccess and modify user name.
3384
+
3385
+ .? ~/public_html/.htaccess
3386
+ .--------------------
3387
+ ## enable mod_rewrie
3388
+ RewriteEngine on
3389
+ ## deny access to *.rhtml and *.cache
3390
+ #RewriteRule \.(rhtml|cache)$ - [R=404,L]
3391
+ RewriteRule \.(rhtml|cache)$ - [F,L]
3392
+ ## rewrite only if requested file is not found
3393
+ RewriteCond %{SCRIPT_FILENAME} !-f
3394
+ ## handle request to *.html and directories by index.cgi
3395
+ RewriteRule (\.html|/|^)$ /~{{*username*}}/index.cgi
3396
+ #RewriteRule (\.html|/|^)$ index.cgi
3397
+ .--------------------
3398
+
3399
+ After these steps, *.rhtml will be published as *.html.
3400
+ For example, if you access to {{,http://{{/host/}}.{{/domain/}}/~{{/username/}}/index.html,}} (or {{,http://{{/host/}}.{{/domain/}}/~{{/username/}}/,}}), file {{,~/public_html/index.rhtml,}} will be displayed.
3401
+
3402
+
3403
+ .$$ Define method | topics-defmethod
3404
+
3405
+ Erubis::Eruby#def_method() defines instance method or singleton method.
3406
+
3407
+ .-------------------- def_method.rb
3408
+ require 'erubis'
3409
+ s = "hello <%= name %>"
3410
+ eruby = Erubis::Eruby.new(s)
3411
+ filename = 'hello.rhtml'
3412
+
3413
+ ## define instance method to Dummy class (or module)
3414
+ class Dummy; end
3415
+ {{*eruby.def_method(Dummy, 'render(name)', filename)*}} # filename is optional
3416
+ p Dummy.new.render('world') #=> "hello world"
3417
+
3418
+ ## define singleton method to dummy object
3419
+ obj = Object.new
3420
+ {{*eruby.def_method(obj, 'render(name)', filename)*}} # filename is optional
3421
+ p obj.render('world') #=> "hello world"
3422
+ .--------------------
3423
+
3424
+ .#+++
3425
+ .==================== def_method.result
3426
+ $ ruby def_method.rb
3427
+ "hello world"
3428
+ "hello world"
3429
+ .====================
3430
+ .#---
3431
+
3432
+
3433
+ .$$ Benchmark | topics-benchmark
3434
+
3435
+ A benchmark script is included in Erubis package at 'erubis-$Release$/benchark/' directory.
3436
+ Here is an example result of benchmark.
3437
+
3438
+ .? MacOS X 10.4 Tiger, Intel CoreDuo 1.83GHz, Ruby1.8.6, eruby1.0.5, gcc4.0.1
3439
+ .====================
3440
+ $ cd erubis-$Release$/benchmark/
3441
+ $ ruby bench.rb -n 10000 -m execute
3442
+ *** ntimes=10000, testmode=execute
3443
+ user system total real
3444
+ eruby 12.720000 0.240000 {{*12.960000*}} ( 12.971888)
3445
+ ERB 36.760000 0.350000 {{*37.110000*}} ( 37.112019)
3446
+ ERB(cached) 11.990000 0.440000 {{*12.430000*}} ( 12.430375)
3447
+ Erubis::Eruby 10.840000 0.300000 {{*11.140000*}} ( 11.144426)
3448
+ Erubis::Eruby(cached) 7.540000 0.410000 {{*7.950000*}} ( 7.969305)
3449
+ Erubis::FastEruby 10.440000 0.300000 {{*10.740000*}} ( 10.737808)
3450
+ Erubis::FastEruby(cached) 6.940000 0.410000 {{*7.350000*}} ( 7.353666)
3451
+ Erubis::TinyEruby 9.550000 0.290000 9.840000 ( 9.851729)
3452
+ Erubis::ArrayBufferEruby 11.010000 0.300000 11.310000 ( 11.314339)
3453
+ Erubis::PrintOutEruby 11.640000 0.290000 11.930000 ( 11.942141)
3454
+ Erubis::StdoutEruby 11.590000 0.300000 11.890000 ( 11.886512)
3455
+ .#$ ruby erubybench.rb -n 10000 -m execute
3456
+ .### execute
3457
+ .# user system total real
3458
+ .#eruby 12.870000 0.290000 {{*13.160000*}} ( 14.020219)
3459
+ .#ERB 37.090000 0.460000 {{*37.550000*}} ( 39.639027)
3460
+ .#Erubis::Eruby 11.420000 0.330000 {{*11.750000*}} ( 12.385562)
3461
+ .#Erubis::Eruby(cached) 7.580000 0.440000 {{*8.020000*}} ( 8.536019)
3462
+ .#Erubis::ArrayBufferEruby 11.550000 0.340000 11.890000 ( 12.597665)
3463
+ .#Erubis::SimplifiedEruby 10.410000 0.320000 10.730000 ( 11.406730)
3464
+ .#Erubis::StdoutEruby 12.170000 0.340000 12.510000 ( 13.252177)
3465
+ .#Erubis::PrintOutEruby 12.070000 0.330000 12.400000 ( 13.142734)
3466
+ .#Erubis::TinyEruby 9.710000 0.320000 10.030000 ( 10.771446)
3467
+ .#Erubis::PI::Eruby 12.010000 0.340000 12.350000 ( 13.104801)
3468
+ .====================
3469
+
3470
+ This shows that...
3471
+ .* Erubis::Eruby runs more than 10 percent faster than eruby.
3472
+ .* Erubis::Eruby runs about 3 times faster than ERB.
3473
+ .* Caching (by Erubis::Eruby.load_file()) makes Erubis about 40-50 percent faster.
3474
+ .* Erubis::FastEruby is a litte faster than Erubis::Eruby.
3475
+ .* Array buffer (ArrayBufferEnhancer) is a little slower than string buffer (StringBufferEnhancer which Erubis::Eruby includes)
3476
+ .* $stdout and print() make Erubis a little slower.
3477
+ .* Erubis::TinyEruby (at 'erubis/tiny.rb') is the fastest in all eRuby implementations when no caching.
3478
+
3479
+ Escaping HTML characters (such as '< > & "') makes Erubis more faster than eruby and ERB,
3480
+ because Erubis::XmlHelper#escape_xml() works faster than CGI.escapeHTML() and ERB::Util#h().
3481
+ The following shows that Erubis runs more than 40 percent (when no-cached) or 90 percent (when cached) faster than eruby if HTML characters are escaped.
3482
+
3483
+ .? When escaping HTML characters with option '-e'
3484
+ .====================
3485
+ $ ruby bench.rb -n 10000 -m execute -ep
3486
+ *** ntimes=10000, testmode=execute
3487
+ user system total real
3488
+ eruby 21.700000 0.290000 {{*21.990000*}} ( 22.050687)
3489
+ ERB 45.140000 0.390000 {{*45.530000*}} ( 45.536976)
3490
+ ERB(cached) 20.340000 0.470000 {{*20.810000*}} ( 20.822653)
3491
+ Erubis::Eruby 14.830000 0.310000 {{*15.140000*}} ( 15.147930)
3492
+ Erubis::Eruby(cached) 11.090000 0.420000 {{*11.510000*}} ( 11.514954)
3493
+ Erubis::FastEruby 14.850000 0.310000 {{*15.160000*}} ( 15.172499)
3494
+ Erubis::FastEruby(cached) 10.970000 0.430000 {{*11.400000*}} ( 11.399605)
3495
+ Erubis::ArrayBufferEruby 14.970000 0.300000 15.270000 ( 15.281061)
3496
+ Erubis::PrintOutEruby 15.780000 0.300000 16.080000 ( 16.088289)
3497
+ Erubis::StdoutEruby 15.840000 0.310000 16.150000 ( 16.235338)
3498
+ .#$ ruby erubybench.rb -n 10000 -m execute -e
3499
+ .### execute
3500
+ .# user system total real
3501
+ .#eruby 22.730000 0.350000 {{*23.080000*}} ( 24.815081)
3502
+ .#ERB 46.590000 0.520000 {{*47.110000*}} ( 50.360891)
3503
+ .#Erubis::Eruby 16.750000 0.360000 {{*17.110000*}} ( 18.253436)
3504
+ .#Erubis::Eruby(cached) 12.540000 0.450000 {{*12.990000*}} ( 13.935044)
3505
+ .#Erubis::ArrayBufferEruby 16.860000 0.370000 17.230000 ( 18.373771)
3506
+ .#Erubis::SimplifiedEruby 15.750000 0.350000 16.100000 ( 17.344105)
3507
+ .#Erubis::StdoutEruby 17.650000 0.360000 18.010000 ( 19.194326)
3508
+ .#Erubis::PrintOutEruby 17.560000 0.360000 17.920000 ( 19.293728)
3509
+ .#Erubis::TinyEruby 16.300000 0.350000 16.650000 ( 17.887278)
3510
+ .#Erubis::PI::Eruby 17.210000 0.360000 17.570000 ( 18.836510)
3511
+ .====================
3512
+
3513
+
3514
+
3515
+ .#.? Env: Linux FedoraCore4, Celeron 667MHz, Mem512MB, Ruby1.8.4, eruby1.0.5
3516
+ .#.____________________
3517
+ .# user system total real
3518
+ .#ERuby 131.990000 1.900000 133.890000 (135.061456)
3519
+ .#ERB 385.040000 3.180000 388.220000 (391.570653)
3520
+ .#Erubis::Eruby 127.750000 2.520000 130.270000 (131.385922)
3521
+ .#Erubis::StringBufferEruby 167.610000 2.600000 170.210000 (171.712798)
3522
+ .#.#Erubis::SimplifiedEruby 121.400000 2.210000 123.610000 (124.663233)
3523
+ .#Erubis::StdoutEruby 92.790000 2.000000 94.790000 ( 95.532633)
3524
+ .#.#Erubis::StdoutSimplifiedEruby 89.260000 2.190000 91.450000 ( 92.164058)
3525
+ .#.#Erubis::PrintOutEruby 92.730000 1.940000 94.670000 ( 95.417965)
3526
+ .#.#Erubis::PrintOutSimplifiedEruby 82.030000 2.190000 84.220000 ( 84.879534)
3527
+ .#Erubis::TinyEruby 118.720000 2.250000 120.970000 (122.022996)
3528
+ .#Erubis::TinyStdoutEruby 87.130000 2.030000 89.160000 ( 89.879538)
3529
+ .#.#Erubis::TinyPrintEruby 84.160000 1.940000 86.100000 ( 86.774579)
3530
+ .#.____________________
3531
+ .#.#____________________
3532
+ .#.# user system total real
3533
+ .#.#ERuby 138.280000 1.900000 140.180000 (141.470426)
3534
+ .#.#ERB 402.220000 3.190000 405.410000 (408.886894)
3535
+ .#.#Erubis::Eruby 147.080000 2.400000 149.480000 (150.752255)
3536
+ .#.#Erubis::StringBufferEruby 186.130000 2.600000 188.730000 (190.374098)
3537
+ .#.#Erubis::SimplifiedEruby 130.100000 2.210000 132.310000 (133.426010)
3538
+ .#.#Erubis::StdoutEruby 106.010000 2.130000 108.140000 (108.999193)
3539
+ .#.#Erubis::StdoutSimplifiedEruby 97.130000 2.180000 99.310000 (100.104433)
3540
+ .#.#.#Erubis::PrintOutEruby 109.900000 2.090000 111.990000 (112.854442)
3541
+ .#.#.#Erubis::PrintOutSimplifiedEruby 93.120000 2.140000 95.260000 ( 96.002970)
3542
+ .#.#Erubis::TinyEruby 118.740000 2.360000 121.100000 (122.141380)
3543
+ .#.#Erubis::TinyStdoutEruby 86.140000 1.840000 87.980000 ( 88.679196)
3544
+ .#.#.#Erubis::TinyPrintEruby 86.540000 1.970000 88.510000 ( 89.208078)
3545
+ .#.#.____________________
3546
+ .#
3547
+ .#.? Env: MacOS X 10.4, PowerPC 1.42GHz, Mem1.5GB, Ruby1.8.4, eruby1.0.5
3548
+ .#.____________________
3549
+ .# user system total real
3550
+ .#ERuby 55.040000 2.120000 57.160000 ( 89.311397)
3551
+ .#ERB 103.960000 3.480000 107.440000 (159.231792)
3552
+ .#Erubis::Eruby 36.130000 1.570000 37.700000 ( 52.188574)
3553
+ .#Erubis::StringBufferEruby 47.270000 1.980000 49.250000 ( 73.867537)
3554
+ .#.#Erubis::SimplifiedEruby 34.310000 1.600000 35.910000 ( 51.762841)
3555
+ .#Erubis::StdoutEruby 26.240000 1.490000 27.730000 ( 41.840430)
3556
+ .#.#Erubis::StdoutSimplifiedEruby 25.380000 1.340000 26.720000 ( 37.231918)
3557
+ .#.#Erubis::PrintOutEruby 26.850000 1.260000 28.110000 ( 38.378227)
3558
+ .#.#Erubis::PrintOutSimplifiedEruby 24.160000 1.280000 25.440000 ( 40.048199)
3559
+ .#Erubis::TinyEruby 31.690000 1.590000 33.280000 ( 49.862091)
3560
+ .#Erubis::TinyStdoutEruby 22.550000 1.230000 23.780000 ( 33.316978)
3561
+ .#.#Erubis::TinyPrintEruby 22.340000 1.150000 23.490000 ( 33.577150)
3562
+ .#.____________________
3563
+ .#
3564
+ .#This shows that:
3565
+ .#.* Erubis::Eruby is about 3 times faster than ERB.
3566
+ .#.* Erubis::Eruby is about 3% faster than ERuby in linux or 1.5 times faster in Mac.
3567
+ .#.#.* Erubis::SimplifiedEruby (which incudes SimplifiedEnhander) is faster than ERuby.
3568
+ .#.* String buffer (StringBufferEnhancer) is slower than array buffer (ArrayBufferEnhancer which Erubis::Eruby includes)
3569
+ .#.* Using $stdout is faster than array buffer and string buffer.
3570
+ .#.* Erubis::TinyEruby (at 'erubis/tiny.rb') and it's subclasses are the fastest in all eRuby implementation.
3571
+ .#
3572
+
3573
+
3574
+ .$ Command Reference | command
3575
+
3576
+
3577
+
3578
+ .$$ Usage | command-usage
3579
+
3580
+ erubis [..options..] [{{/file/}} ...]
3581
+
3582
+
3583
+
3584
+ .$$ Options | command-options
3585
+
3586
+ .[ -h, --help ] Help.
3587
+ .[ -v ] Release version.
3588
+ .[ -x ] Show compiled source.
3589
+ .[ -X ] Show compiled source but only Ruby code.
3590
+ This is equivarent to '-E NoText'.
3591
+ .[ -N ] Numbering: add line numbers. (for '-x/-X')
3592
+ .[ -U ] Unique mode: zip empty lines into a line. (for '-x/-X')
3593
+ .[ -C ] Compact: remove empty lines. (for '-x/-X')
3594
+ .[ -b ] Body only: no preamble nor postamble. (for '-x/-X')
3595
+ This is equivarent to '--preamble=false --postamble=false'.
3596
+ .[ -z ] Syntax checking.
3597
+ .# .[ -T ] No trimming spaces around '<% %>'.
3598
+ .# This is equivarent to '--trim=false'.
3599
+ .[ -e ] Escape. This is equivarent to '-E Escape'.
3600
+ .[ -p pattern ] Embedded pattern (default '<% %>').
3601
+ This is equivarent to '--pattern={{/pattern/}}'.
3602
+ .[ -l lang ] Language name.
3603
+ This option makes erubis command to compile script but no execute.
3604
+ .# .[ -C class ] Class name (Eruby, XmlEruby, ...) to compile. (default Eruby).
3605
+ .[ -E enhacers ] Enhancer name (Escape, PercentLine, ...).
3606
+ It is able to specify several enhancer name separating with ','
3607
+ (ex. -f Escape,PercentLine,HeaderFooter).
3608
+ .[ -I path ] Require library path ($:).
3609
+ It is able to specify several paths separating with ','
3610
+ (ex. -f path1,path2,path3).
3611
+ .[ -K kanji ] Kanji code (euc, sjis, utf8, or none) (default none).
3612
+ .[ -f datafile ] Context data file in YAML format ('*.yaml', '*.yml') or
3613
+ Ruby script ('*.rb').
3614
+ It is able to specify several filenames separating with ','
3615
+ (ex. -f file1,file2,file3).
3616
+ .[ -c context ] Context data string in YAML inline style or Ruby code.
3617
+ .# .[ -t ] Expand tab characters in YAML file.
3618
+ .[ -T ] Don't expand tab characters in YAML file.
3619
+ .[ -S ] Convert mapping key from string to symbol in YAML file.
3620
+ .[ -B ] invoke Eruby#result() instead of Eruby#evaluate()
3621
+ .[ --pi[=name] ] parse '<?name ... ?>' instead of '<% ... %>'
3622
+ .[ --trim=false ] No trimming spaces around '<% %>'.
3623
+
3624
+
3625
+
3626
+ .$$ Properties | command-props
3627
+
3628
+ Some Eruby classes can take optional properties to change it's compile option.
3629
+ For example, property '--indent=" "' may change indentation of compiled source code.
3630
+ Try 'erubis -h' for details.
3631
+