nitro 0.14.0 → 0.15.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (60) hide show
  1. data/CHANGELOG +117 -0
  2. data/INSTALL +4 -0
  3. data/README +30 -31
  4. data/Rakefile +2 -2
  5. data/bin/nitro +10 -1
  6. data/bin/{new_app.rb → nitrogen} +12 -22
  7. data/doc/AUTHORS +4 -13
  8. data/doc/RELEASES +98 -0
  9. data/examples/ajax/run.rb +1 -3
  10. data/examples/blog/cache/entriesadmin +1 -1
  11. data/examples/blog/conf/locales/de.yml +4 -0
  12. data/examples/blog/conf/locales/en.yml +4 -0
  13. data/examples/blog/public/fcgi.rb +2 -3
  14. data/examples/blog/run.rb +10 -5
  15. data/examples/blog/src/controller.rb +21 -10
  16. data/examples/blog/src/mailer.rb +1 -1
  17. data/examples/blog/src/views/index.xhtml +2 -2
  18. data/examples/blog/src/xsl/style.xsl +6 -1
  19. data/examples/flash/run.rb +1 -3
  20. data/examples/no_xsl_blog/conf/locales/de.yml +4 -0
  21. data/examples/no_xsl_blog/conf/locales/en.yml +4 -0
  22. data/examples/no_xsl_blog/lib/blog/controller.rb +10 -0
  23. data/examples/no_xsl_blog/lib/blog/template.rb +4 -0
  24. data/examples/no_xsl_blog/public/fcgi.rb +2 -1
  25. data/examples/no_xsl_blog/public/index.xhtml +1 -1
  26. data/examples/no_xsl_blog/run.rb +8 -4
  27. data/examples/tiny/public/deep/dir/hello.xhtml +1 -0
  28. data/examples/tiny/public/fcgi.rb +2 -1
  29. data/examples/tiny/public/index.xhtml +5 -2
  30. data/examples/tiny/run.rb +1 -3
  31. data/examples/wee_style/run.rb +1 -3
  32. data/examples/why_wiki/run.rb +1 -3
  33. data/lib/nitro.rb +5 -2
  34. data/lib/nitro/builders/form.rb +8 -3
  35. data/lib/nitro/caching/stores.rb +3 -3
  36. data/lib/nitro/controller.rb +26 -6
  37. data/lib/nitro/dispatcher.rb +21 -13
  38. data/lib/nitro/environment.rb +23 -0
  39. data/lib/nitro/filters.rb +10 -8
  40. data/lib/nitro/localization.rb +127 -13
  41. data/lib/nitro/part.rb +24 -0
  42. data/lib/nitro/render.rb +19 -15
  43. data/lib/nitro/runner.rb +2 -1
  44. data/lib/nitro/scaffold.rb +69 -17
  45. data/lib/nitro/shaders.rb +54 -83
  46. data/lib/nitro/template.rb +7 -1
  47. data/proto/README +11 -0
  48. data/proto/conf/apache.conf +51 -0
  49. data/proto/conf/lhttpd.conf +107 -0
  50. data/proto/public/error.xhtml +56 -0
  51. data/proto/public/fcgi.rb +5 -0
  52. data/proto/public/index.xhtml +83 -0
  53. data/proto/public/js/ajax.js +63 -0
  54. data/proto/public/media/nitro.png +0 -0
  55. data/proto/run.rb +11 -0
  56. data/test/nitro/tc_controller.rb +1 -4
  57. data/test/nitro/tc_dispatcher.rb +8 -0
  58. data/test/nitro/tc_localization.rb +49 -0
  59. metadata +34 -6
  60. data/bin/new_form.rb +0 -54
data/lib/nitro/runner.rb CHANGED
@@ -6,6 +6,7 @@
6
6
 
7
7
  require 'optparse'
8
8
 
9
+ require 'glue/misc'
9
10
  require 'nitro/conf'
10
11
 
11
12
  module N
@@ -65,7 +66,7 @@ class Runner
65
66
  # and false.
66
67
 
67
68
  attr :spider
68
-
69
+
69
70
  # Parse the command line arguments and the environment
70
71
  # parameters to setup the application.
71
72
 
@@ -1,6 +1,6 @@
1
1
  # * George Moschovitis <gm@navel.gr>
2
2
  # (c) 2004-2005 Navel, all rights reserved.
3
- # $Id: scaffold.rb 300 2005-03-16 13:23:10Z gmosx $
3
+ # $Id: scaffold.rb 335 2005-03-31 14:02:02Z gmosx $
4
4
 
5
5
  require 'glue/inflector'
6
6
 
@@ -10,10 +10,10 @@ module Scaffolding
10
10
 
11
11
  def self.append_features(base) # :nodoc:
12
12
  super
13
- base.extend(SingletonMethods)
13
+ base.extend(ClassMethods)
14
14
  end
15
15
 
16
- module SingletonMethods
16
+ module ClassMethods
17
17
 
18
18
  # Enchant the caller with a number of default methods.
19
19
  # Override the automatically generated methods as needed.
@@ -27,33 +27,75 @@ module Scaffolding
27
27
 
28
28
  # Add methods to the scaffolded class.
29
29
 
30
- klass.module_eval <<-"end_eval", __FILE__, __LINE__
31
-
30
+ klass.module_eval %{
32
31
  def view_uri
33
32
  # "view#{suffix}?oid=\#\{@oid\}"
34
33
  "view#{suffix}/\#\{@oid\}"
35
34
  end
36
-
37
- end_eval
35
+ }
38
36
 
39
37
  # Add methods to the service.
40
-
38
+
39
+ code = ''
40
+
41
41
  if options[:index]
42
- module_eval <<-"end_eval", __FILE__, __LINE__
43
-
42
+ code << %{
44
43
  def index
45
44
  list#{suffix}
46
45
  end
47
-
48
- end_eval
46
+ }
49
47
  end
50
48
 
51
- module_eval <<-"end_eval", __FILE__, __LINE__
52
-
49
+ code << %{
50
+ def new#{suffix}
51
+ @#{name} = #{klass}.new
52
+ render '/form#{suffix}'
53
+ end
54
+
55
+ def edit#{suffix}
56
+ @#{name} = #{klass}[request['oid']]
57
+ render '/form#{suffix}'
58
+ end
59
+ }
60
+
61
+ unless Rendering.template_for_action(self.template_root, "form#{suffix}")
62
+ code << %{
63
+ def form#{suffix}
64
+ o << %|
65
+ <html>
66
+ <form action="save#{suffix}" method="post">
67
+ |
68
+ if @#{name}.oid
69
+ o << %|
70
+ <input type="hidden" name="oid" value="\#\{@#{name}\}" />
71
+ |
72
+ end
73
+ o.build_form(@#{name})
74
+ o << %|
75
+ <input type="submit" value="Save" />
76
+ </form>
77
+ </html>
78
+ |
79
+ end
80
+ }
81
+ end
82
+
83
+ code << %{
53
84
  # TODO: add pager support here!
54
85
 
55
86
  def list#{suffix}
56
87
  @#{list_name} = #{klass}.all('ORDER BY oid')
88
+ }
89
+ unless Rendering.template_for_action(self.template_root, "form#{suffix}")
90
+ code << %{
91
+ o.ul {
92
+ for item in @#{list_name}
93
+ o.li(item.to_s)
94
+ end
95
+ }
96
+ }
97
+ end
98
+ code << %{
57
99
  end
58
100
 
59
101
  def view#{suffix}
@@ -63,16 +105,26 @@ module Scaffolding
63
105
  action :view#{suffix}, :route => \%r\{view#{suffix}/(.*)\}, 'oid' => 1
64
106
 
65
107
  def save#{suffix}
108
+ if oid = request['oid']
109
+ @#{name} = request.fill(#{klass}[oid])
110
+ else
111
+ @#{name} = request.fill(#{klass}.new)
112
+ end
113
+
114
+ @#{name}.save
115
+
116
+ redirect 'list#{suffix}'
66
117
  end
67
118
 
68
119
  def del#{suffix}
69
120
  #{klass}.delete(@context['#{oid}'])
70
121
  end
71
122
  alias_method :delete#{suffix}, :del#{suffix}
72
-
73
- end_eval
74
-
123
+ }
124
+
125
+ class_eval(code)
75
126
  end
127
+
76
128
  end
77
129
 
78
130
  end
data/lib/nitro/shaders.rb CHANGED
@@ -10,8 +10,7 @@ module N
10
10
  # the .xhtml files to actual ruby code ready for evaluation
11
11
  # (compilation) by the engine.
12
12
  #
13
- # Shaders are equivalend to the render-pipeline filters, ie they
14
- # share their folded-filter design.
13
+ # Shaders employ a folded-filter design.
15
14
  #--
16
15
  # TODO: pipeline stage mixin to be reused in filters too.
17
16
  #++
@@ -27,8 +26,8 @@ class Shader
27
26
  end
28
27
 
29
28
  # Process the text and optionally update the hash.
30
- # The hash is a short, unique representation of the input text,
31
- # typically used as a caching key.
29
+ # The hash is a short, unique representation of the
30
+ # input text, typically used as a caching key.
32
31
 
33
32
  def process(hash, text)
34
33
  process_next(hash, text)
@@ -52,14 +51,14 @@ class Shader
52
51
  end
53
52
  end
54
53
 
55
- # Convert the xhtml script to actual Ruby code, ready to be
56
- # evaluated.
54
+ # Convert the xhtml script to actual Ruby code, ready
55
+ # to be evaluated.
57
56
 
58
57
  class RubyShader < Shader
59
58
  include TemplateMixin
60
59
 
61
- # Convert the xhtml script to actual Ruby code, ready to be
62
- # evaluated.
60
+ # Convert the xhtml script to actual Ruby code, ready
61
+ # to be evaluated.
63
62
  #
64
63
  #--
65
64
  # Investigate:
@@ -71,78 +70,6 @@ class RubyShader < Shader
71
70
  process_next(hash, text)
72
71
  end
73
72
 
74
- =begin
75
- def process(hash, text)
76
- # strip the xml header! (interracts with the following gsub!)
77
- text.gsub!(/<\?xml.*\?>/, "")
78
-
79
- # Statically include sub script files.
80
- # The target file is included at compile time.
81
- #
82
- # gmosx: must be xformed before the <?r pi.
83
- #
84
- # Example:
85
- # <?include xl:href="root/myfile.sx" ?>
86
-
87
- text.gsub!(/<\?include href="(.*?)"(.*)\?>/) { |match|
88
- # gmosx: xmm match matches the whole string.
89
- # match = overload_path($1)
90
- load_statically_included("#$root_dir/#$1")
91
- }
92
-
93
- # xform include instructions <include href="xxx" />
94
- # must be transformed before the processinc instructions.
95
- # Useful to include fragments cached on disk
96
- #
97
- # gmosx, FIXME: NOT TESTED! test and add caching.
98
- # add load_statically_included fixes.
99
-
100
- text.gsub!(/<include href="(.*?)"(.*)(.?)\/>/) { |match|
101
- "<?r File.read( '\#\{@dispatcher.root\}/#$1' ?>"
102
- }
103
-
104
- # xform render/inject instructions <render href="xxx" />
105
- # must be transformed before the processinc instructions.
106
-
107
- text.gsub!(/<inject href="(.*?)"(.*)(.?)\/>/) { |match|
108
- "<?r render '/#$1' ?>"
109
- }
110
-
111
- text.gsub!(/<render href="(.*?)"(.*)(.?)\/>/) { |match|
112
- "<?r render '/#$1' ?>"
113
- }
114
-
115
- # remove <root> elements. typically removed by xslt but lets
116
- # play it safe.
117
-
118
- text.gsub!(/<(\/)?root>/, '')
119
-
120
- # runtime ruby code.
121
-
122
- # xform the processing instructions, use <?r as
123
- # a marker.
124
-
125
- text.gsub!(/\?>/, "\n@out << %^")
126
- text.gsub!(/<\?r(\s?)/, "^\n")
127
-
128
- # xform alternative code tags (very useful in xsl stylesheets)
129
-
130
- text.gsub!(/<\/ruby>/, "\n@out << %^")
131
- text.gsub!(/<ruby>/, "^\n")
132
-
133
- # compile time ruby code.
134
- # Usefull for example to prevaluate localization.
135
-
136
- text.gsub!(/\#\[(.*?)\]/) { |match|
137
- eval($1)
138
- }
139
-
140
- text = "@out << %^" + text + "^"
141
-
142
- process_next(hash, text)
143
- end
144
- =end
145
-
146
73
  # Loads and statically includes a file.
147
74
 
148
75
  def load_statically_included(filename)
@@ -155,12 +82,11 @@ class RubyShader < Shader
155
82
  return text
156
83
  end
157
84
 
158
-
159
85
  end
160
86
 
161
87
  # Apply an XSL transformation to the script code.
162
- # There is no need to keep post xsl. I can reuse the same xsl
163
- # by calling transform again.
88
+ # There is no need to keep post xsl. I can reuse the
89
+ # same xsl by calling transform again.
164
90
 
165
91
  class XSLTShader < Shader
166
92
 
@@ -230,4 +156,49 @@ class CompressShader < Shader
230
156
 
231
157
  end
232
158
 
159
+ # MorphingShader
160
+
161
+ class MorphingShader < Shader
162
+
163
+ def process(hash, text)
164
+
165
+ # <tag if="x">..</tag>
166
+ # <tag unless="x">..</tag>
167
+
168
+ text.gsub!(/<(\w*?)([^>]*?)(if|unless)="(.*?)"(.*?)>(.*?)<\/\1>/m) do |match|
169
+ %{<?r #$3 #$4 ?>
170
+ <#$1#$2#$5>#$6</#$1>
171
+ <?r end ?>}
172
+ end
173
+
174
+ # <tag times="x">..</tag>
175
+
176
+ text.gsub!(/<(\w*?)([^>]*?)times="(.*?)"(.*?)>(.*?)<\/\1>/m) do |match|
177
+ %{<?r #$3.times do ?>
178
+ <#$1#$2#$4>#$5</#$1>
179
+ <?r end ?>}
180
+ end
181
+
182
+ # <tag each="x">..</tag>
183
+
184
+ text.gsub!(/<(\w*?)([^>]*?)each="(.*?)"(.*?)>(.*?)<\/\1>/m) do |match|
185
+ %{<?r for #$3 ?>
186
+ <#$1#$2#$4>#$5</#$1>
187
+ <?r end ?>}
188
+ end
189
+
190
+ process_next(hash, text)
191
+ end
192
+
193
+ end
194
+
195
+ # ElementsShader
196
+
197
+ class ElementsShader < Shader
198
+
199
+ def process(hash, text)
200
+ end
201
+
202
+ end
203
+
233
204
  end
@@ -1,6 +1,6 @@
1
1
  # * George Moschovitis <gm@navel.gr>
2
2
  # (c) 2004-2005 Navel, all rights reserved.
3
- # $Id: template.rb 300 2005-03-16 13:23:10Z gmosx $
3
+ # $Id: template.rb 332 2005-03-29 11:31:52Z gmosx $
4
4
 
5
5
  require 'glue/flexob'
6
6
 
@@ -87,6 +87,12 @@ module TemplateMixin
87
87
 
88
88
  text.gsub!(/<\/ruby>/, "\n#{buffer} << %^")
89
89
  text.gsub!(/<ruby>/, "^\n")
90
+
91
+ # Also handle erb/asp/jsp style tags. Those tags
92
+ # *cannot* be used with an xslt stylesheet.
93
+
94
+ text.gsub!(/%>/, "\n#{buffer} << %^")
95
+ text.gsub!(/<%/, "^\n")
90
96
 
91
97
  # Alterative versions of interpolation.
92
98
  # (very useful in xsl stylesheets)
data/proto/README ADDED
@@ -0,0 +1,11 @@
1
+ = Proto
2
+
3
+ A prototype NITRO application.
4
+
5
+ === Running
6
+
7
+ Start the application with:
8
+
9
+ $ ruby run.rb
10
+
11
+
@@ -0,0 +1,51 @@
1
+ # Apache Configuration
2
+ # Change as needed for your system.
3
+
4
+ Listen 9999
5
+
6
+ PidFile /var/tmp/httpd.pid
7
+ TypesConfig /etc/mime.types
8
+ DocumentRoot /home/gmosx/navel/nitro/examples/blog/public
9
+
10
+ # The error log.
11
+
12
+ ErrorLog log/apache.error_log
13
+ CustomLog log/access_log combined
14
+
15
+ # Load dynamic modules.
16
+
17
+ LoadModule fastcgi_module /usr/local/apache2/modules/mod_fastcgi.so
18
+ # LoadModule rewrite_module /usr/local/apache2/modules/mod_rewrite.so
19
+
20
+ FastCgiIpcDir /var/tmp/fcgi
21
+ # gmosx: if you have installed the gems
22
+ # distribution the -I is not needed.
23
+ FastCgiConfig -initial-env 'RUBYOPT=-rubygems -I/home/gmosx/navel/nitro/lib -I/home/gmosx/navel/og/lib -I/home/gmosx/navel/glue/lib'
24
+
25
+
26
+ AddHandler fastcgi-script fcgi rb
27
+ AddHandler cgi-script cgi rb
28
+ Options +FollowSymLinks +ExecCGI
29
+
30
+ # Redirect all requests not available on the filesystem
31
+ # to Nitro. By default the cgi dispatcher is used which
32
+ # is very slow. For better performance replace the
33
+ # dispatcher with the fastcgi one
34
+ #
35
+ # Example:
36
+ # RewriteRule ^(.*)$ dispatch.fcgi [QSA,L]
37
+
38
+ RewriteEngine On
39
+ RewriteRule ^$ index.html [QSA]
40
+ RewriteRule ^([^.]+)$ $1.html [QSA]
41
+ RewriteCond %{REQUEST_FILENAME} !-f
42
+ RewriteRule ^(.*)$ dispatch.cgi [QSA,L]
43
+
44
+ # In case Nitro experiences terminal errors.
45
+ # Instead of displaying this message you can supply a
46
+ # file here which will be rendered instead.
47
+ #
48
+ # Example:
49
+ # ErrorDocument 500 /500.html
50
+
51
+ ErrorDocument 500 "<h2>Application error</h2>Nitro failed to start properly"
@@ -0,0 +1,107 @@
1
+ # Lighttpd configuration file
2
+ # For more options check out the default configuration
3
+ # file that comes with Lighttpd.
4
+ # $Id$
5
+
6
+ server.port = 9999
7
+ server.bind = "127.0.0.1"
8
+ # server.event-handler = "freebsd-kqueue" # needed on OS X
9
+
10
+ server.modules = ( "mod_rewrite", "mod_fastcgi", "mod_access", "mod_accesslog" )
11
+
12
+ server.document-root = "/path/to/your/app/public/"
13
+ server.errorlog = "/path/to/your/app/log/lighttpd.error.log"
14
+ accesslog.filename = "/path/to/your/app/log/access.log"
15
+
16
+ server.indexfiles = ( "index.html" )
17
+ url.access-deny = ( "~", ".inc" )
18
+
19
+ url.rewrite = ( "^/$" => "index.html", "^([^.]+)$" => "$1.html" )
20
+ server.error-handler-404 = "/fcgi.rb"
21
+
22
+ fastcgi.server = ( ".rb" =>
23
+ ( "localhost" =>
24
+ (
25
+ "min-procs" => 1,
26
+ "max-procs" => 5,
27
+ "socket" => "/tmp/blog.fcgi.socket",
28
+ "bin-path" => "/home/gmosx/navel/nitro/examples/blog/public/fcgi.rb"
29
+ "bin-environment" => ( "NITRO_ENV" => "development" )
30
+ )
31
+ )
32
+ )
33
+
34
+ mimetype.assign = (
35
+ ".pdf" => "application/pdf",
36
+ ".sig" => "application/pgp-signature",
37
+ ".spl" => "application/futuresplash",
38
+ ".class" => "application/octet-stream",
39
+ ".ps" => "application/postscript",
40
+ ".torrent" => "application/x-bittorrent",
41
+ ".dvi" => "application/x-dvi",
42
+ ".gz" => "application/x-gzip",
43
+ ".pac" => "application/x-ns-proxy-autoconfig",
44
+ ".swf" => "application/x-shockwave-flash",
45
+ ".tar.gz" => "application/x-tgz",
46
+ ".tgz" => "application/x-tgz",
47
+ ".tar" => "application/x-tar",
48
+ ".zip" => "application/zip",
49
+ ".mp3" => "audio/mpeg",
50
+ ".m3u" => "audio/x-mpegurl",
51
+ ".wma" => "audio/x-ms-wma",
52
+ ".wax" => "audio/x-ms-wax",
53
+ ".ogg" => "audio/x-wav",
54
+ ".wav" => "audio/x-wav",
55
+ ".gif" => "image/gif",
56
+ ".jpg" => "image/jpeg",
57
+ ".jpeg" => "image/jpeg",
58
+ ".png" => "image/png",
59
+ ".xbm" => "image/x-xbitmap",
60
+ ".xpm" => "image/x-xpixmap",
61
+ ".xwd" => "image/x-xwindowdump",
62
+ ".css" => "text/css",
63
+ ".html" => "text/html",
64
+ ".htm" => "text/html",
65
+ ".js" => "text/javascript",
66
+ ".asc" => "text/plain",
67
+ ".c" => "text/plain",
68
+ ".conf" => "text/plain",
69
+ ".text" => "text/plain",
70
+ ".txt" => "text/plain",
71
+ ".dtd" => "text/xml",
72
+ ".xml" => "text/xml",
73
+ ".mpeg" => "video/mpeg",
74
+ ".mpg" => "video/mpeg",
75
+ ".mov" => "video/quicktime",
76
+ ".qt" => "video/quicktime",
77
+ ".avi" => "video/x-msvideo",
78
+ ".asf" => "video/x-ms-asf",
79
+ ".asx" => "video/x-ms-asf",
80
+ ".wmv" => "video/x-ms-wmv"
81
+ )
82
+
83
+
84
+ server.port = 9999
85
+ server.bind = "127.0.0.1"
86
+ # server.event-handler = "freebsd-kqueue" # needed on OS X
87
+
88
+ server.modules = ( "mod_rewrite", "mod_fastcgi" )
89
+
90
+ url.rewrite = ( "^/$" => "index.html", "^([^.]+)$" => "$1.html" )
91
+ server.error-handler-404 = "/fcgi.rb"
92
+
93
+ server.document-root = "/path/application/public"
94
+ server.errorlog = "/path/application/log/server.log"
95
+
96
+ fastcgi.server = ( ".rb" =>
97
+ ( "localhost" =>
98
+ (
99
+ "min-procs" => 1,
100
+ "max-procs" => 5,
101
+ "socket" => "/tmp/application.fcgi.socket",
102
+ "bin-path" => "/path/application/public/dispatch.fcgi",
103
+ "bin-environment" => ( "RAILS_ENV" => "development" )
104
+ )
105
+ )
106
+ )
107
+