cuca 0.06 → 0.07

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/CHANGELOG CHANGED
@@ -1,3 +1,12 @@
1
+ * 2009/xx/xx - 0.07
2
+ - 'stop' option :cancel_execution added. This can be raised in before filters
3
+ and will avoid that the run/get/post... methods are called.
4
+ - ARFormWidget will set attribites by the setter method which allows
5
+ overwriting within the model
6
+ - Minor Bugfixes
7
+ - Added subcall? method to controller to easily detect subcalls
8
+
9
+
1
10
  * 2009/03/04 - 0.06
2
11
  - Fixed sorting bug of filters with priority specified
3
12
  - Nicer pagination on listwidget for large lists
data/README CHANGED
@@ -1,34 +1,43 @@
1
-
2
- == Installing Cuca
3
-
4
- To use the source code you can simply run:
5
- sudo renew.sh
6
-
7
- To install the gem from the internet use
8
- gem install --remote cuca
9
-
10
- See http://cuca.rubyforge.org for more information how to get started.
11
-
12
-
13
- == Coding on the Framework
14
-
15
- You can tell your application to load the cuca framework from a
16
- different location instead from rubygems. For that create a new dispatcher
17
- cgi script, a minimal version would be:
18
-
19
- #!/usr/bin/ruby
20
-
21
- FRAMEWORK_PATH = '/home/bones/path/to/cuca-framework/lib'
22
- $: << FRAMEWORK_PATH
23
-
24
- require 'cuca'
25
- require 'rubygems'
26
-
27
- application = Cuca::App.new
28
- application.cgicall
29
-
30
-
31
- And tell your webserver to use this new handler (or edit the script/server*
32
- files).
33
-
34
-
1
+ # = Cuca - a web application framework
2
+ #
3
+ # Cuca is another web application framework written in Ruby. It's made to
4
+ # build applications with focus on functionality - less design. You can
5
+ # create and application without writing HTML. Once written Widgets
6
+ # (a smart screen element) can be reused thorough your project with
7
+ # minimum effort allowing to build fast and secure web applications.
8
+ #
9
+ # It implements the following concepts:
10
+ # * A Widget is a screen element. Can be a full page or part of it.
11
+ # The Controller and the Layout are Widgets, too.
12
+ # * A Controller deals with one request URI (get, post or both) and can set variables
13
+ # other widgets can make use of. It can also define a Layout and filters.
14
+ # * A Layout wraps the output of a controller and finally return the
15
+ # built web page.
16
+ # * A Generator (NOT "code generator") can be used within any Widget to help building the web content.
17
+ # Cuca comes with a Markaby and eruby Generator.
18
+ # * A Session can used optionally to keep stateful data.
19
+ #
20
+ #
21
+ # == Installation & Getting started
22
+ #
23
+ # Download and install from the internet:
24
+ #
25
+ # gem install --remote cuca
26
+ #
27
+ #
28
+ # Create an application skeleton:
29
+ #
30
+ # cuca my_project # this will create a new project
31
+ # cd my_project
32
+ # ruby ./script/server-webrick.rb
33
+ #
34
+ # Open http://localhost:2000/
35
+ #
36
+ #
37
+ # == Read on
38
+ #
39
+ # * Cuca::Widget
40
+ # * Cuca::Controller
41
+ # * Cuca::Layout
42
+ # * Cuca::Session
43
+ # * Cuca::App
@@ -11,7 +11,7 @@ class SimpleLayout < Cuca::Layout
11
11
  <BODY>
12
12
  #{@content_for_layout}
13
13
  <HR/>
14
- <SMALL>Generated by Cuca Framework #{Time.now} (using 'simple' demo layout on Cuca Version #{Cuca::VERSION})</SMALL>
14
+ <SMALL>Generated by Cuca Framework #{Time.now} (using 'simple' demo layout on Cuca Version #{Cuca::VERSION} on Ruby #{RUBY_VERSION})</SMALL>
15
15
  </BODY>
16
16
  </HTML>
17
17
  EOF
@@ -0,0 +1,21 @@
1
+ #!/usr/bin/ruby1.9.1
2
+
3
+ FRAMEWORK_PATH = '/home/bones/workspace/cuca_svn/cuca/lib'
4
+
5
+ $cuca_path = File.dirname(__FILE__)+"/../"
6
+ $: << FRAMEWORK_PATH
7
+
8
+ require 'cuca'
9
+ require 'rubygems'
10
+
11
+ Signal.trap("INT") do
12
+ $stderr.puts "INT caught"
13
+ exit
14
+ end
15
+
16
+ start = (Time.now.to_f * 1000).to_i
17
+ application = Cuca::App.new
18
+ application.cgicall
19
+ stop = (Time.now.to_f * 1000).to_i
20
+ dur_msec = stop - start
21
+ application.logger.info("App::cgicall: #{dur_msec} msec [= #{(1000 / dur_msec).to_i} pages / second]")
@@ -1,4 +1,4 @@
1
- #!/usr/bin/ruby
1
+ #!/usr/bin/ruby1.9
2
2
 
3
3
  $cuca_path = File.dirname(__FILE__)+"/../"
4
4
 
@@ -0,0 +1,18 @@
1
+ #!/usr/bin/ruby
2
+
3
+ $cuca_path = File.dirname(__FILE__)+"/../"
4
+
5
+ require 'rubygems'
6
+ require 'cuca'
7
+
8
+ Signal.trap("INT") do
9
+ $stderr.puts "INT caught"
10
+ exit
11
+ end
12
+
13
+ start = (Time.now.to_f * 1000).to_i
14
+ application = Cuca::App.new
15
+ application.cgicall
16
+ stop = (Time.now.to_f * 1000).to_i
17
+ dur_msec = stop - start
18
+ application.logger.info("App::cgicall: #{dur_msec} msec [= #{(1000 / dur_msec).to_i} pages / second]")
@@ -0,0 +1,25 @@
1
+ #!/usr/bin/ruby
2
+
3
+
4
+ $cuca_path = File.dirname(__FILE__)+"/../"
5
+
6
+ require 'rubygems'
7
+ require 'cuca'
8
+
9
+ require "fcgi"
10
+
11
+ Signal.trap("INT") do
12
+ $stderr.puts "INT caught"
13
+ exit
14
+ end
15
+
16
+ application = Cuca::App.new
17
+
18
+ FCGI.each_cgi do |cgi|
19
+ CGI::fix_env(cgi.env_table)
20
+ start = (Time.now.to_f * 1000).to_i
21
+ application.cgicall(cgi)
22
+ stop = (Time.now.to_f * 1000).to_i
23
+ dur_msec = stop - start
24
+ application.logger.info("App::cgicall (#{cgi.path_info}: #{dur_msec} msec [= #{(1000 / dur_msec).to_i} pages / second]")
25
+ end
@@ -0,0 +1,52 @@
1
+
2
+ require 'rubygems'
3
+ require 'rack'
4
+ require 'rack/session/cookie'
5
+
6
+
7
+ class Middle
8
+ def initialize(app)
9
+ @app = app
10
+ end
11
+
12
+ def call(env)
13
+ $stderr.puts "CAll for MIDDLE"
14
+ status, headers, body = @app.call(env)
15
+ [400, headers, [body.first.upcase]]
16
+ end
17
+ end
18
+
19
+ class Cuca
20
+ def initialize(app)
21
+ @app = app
22
+ end
23
+
24
+ def call(env)
25
+ $stderr.puts "CAll for CUCA"
26
+ $stderr.puts "#{@app.inspect}"
27
+ @app.call(env)
28
+ [200, {'Content-Type' => 'text/html'}, ['some Dynamic Website']]
29
+ end
30
+ end
31
+
32
+
33
+
34
+ class App < Rack::Builder
35
+
36
+ end
37
+
38
+
39
+ app = App.new
40
+ app.use Cuca
41
+
42
+ app.use Middle
43
+ puts app.to_app.inspect
44
+
45
+
46
+ Rack::Handler::Thin.run(
47
+ Rack::ShowExceptions.new(
48
+ Rack::Lint.new(
49
+ app.to_app
50
+ )
51
+ ), :Port => 1234)
52
+
@@ -0,0 +1,40 @@
1
+ $: << '/home/bones/workspace/cuca_svn/cuca/lib'
2
+ require 'cuca'
3
+ require 'rubygems'
4
+ # require 'cuca'
5
+ require 'rack/request'
6
+ require 'rack/response'
7
+ require 'rack/showexceptions'
8
+ require 'rack/handler'
9
+ require 'rack/handler/thin'
10
+ require 'rack/lint'
11
+
12
+
13
+ class MakeError
14
+ def initialize(app)
15
+ @app = app
16
+ end
17
+
18
+ def call(env)
19
+ status, headers, body = @app.call(env)
20
+ [500, headers,body]
21
+ end
22
+ end
23
+
24
+
25
+
26
+ app = Cuca::App.new
27
+ app.use MakeError
28
+
29
+
30
+ Rack::Handler::Thin.run \
31
+ Rack::ShowExceptions.new(app),
32
+ :Port => 1234
33
+
34
+
35
+
36
+ # Rack::Handler::WEBrick.run \
37
+ # Rack::ShowExceptions.new(Rack::Lint.new(Cuca::App.new)),
38
+ # :Port => 1234
39
+
40
+
@@ -0,0 +1,22 @@
1
+ $: << '/home/bones/workspace/cuca_svn/cuca/lib'
2
+ require 'cuca'
3
+ require 'rubygems'
4
+ # require 'cuca'
5
+ require 'rack/request'
6
+ require 'rack/response'
7
+ require 'rack/showexceptions'
8
+ require 'rack/handler'
9
+ require 'rack/handler/webrick'
10
+ require 'rack/lint'
11
+
12
+ Rack::Handler::WEBrick.run \
13
+ Rack::ShowExceptions.new(Cuca::App.new),
14
+ :Port => 1234
15
+
16
+
17
+
18
+ # Rack::Handler::WEBrick.run \
19
+ # Rack::ShowExceptions.new(Rack::Lint.new(Cuca::App.new)),
20
+ # :Port => 1234
21
+
22
+
@@ -0,0 +1,26 @@
1
+ #!/usr/bin/ruby
2
+
3
+ require 'webrick'
4
+ require 'cgi'
5
+
6
+
7
+ # this is for http debugging
8
+ class CucaHandler < WEBrick::HTTPServlet::CGIHandler
9
+ alias :old_do_GET :do_GET
10
+
11
+ def do_GET(req, res)
12
+ # puts "------------ Request ----------\n #{req.to_s}"
13
+ start = (Time.now.to_f * 100).to_i
14
+ r = old_do_GET(req, res)
15
+ stop = (Time.now.to_f * 100).to_i
16
+ # $stderr.puts "WEBRICK: Time: #{stop - start} ms"
17
+ # puts "------------ RESPONSE ----------\n #{res.to_s}"
18
+ end
19
+
20
+ end
21
+
22
+ server = WEBrick::HTTPServer.new(:Port => 2000)
23
+ server.mount("/", CucaHandler, File.expand_path(File.dirname(__FILE__))+"/../public/dispatch.cgi")
24
+
25
+ trap("INT"){ server.shutdown }
26
+ server.start
@@ -20,7 +20,7 @@ class CucaHandler < WEBrick::HTTPServlet::CGIHandler
20
20
  end
21
21
 
22
22
  server = WEBrick::HTTPServer.new(:Port => 2000)
23
- server.mount("/", CucaHandler, File.expand_path(File.dirname(__FILE__))+"/../public/dispatch.cgi")
23
+ server.mount("/", CucaHandler, File.expand_path(File.dirname(__FILE__))+"/../public/dispatch-fwdev.cgi")
24
24
 
25
25
  trap("INT"){ server.shutdown }
26
26
  server.start
data/lib/cuca.rb CHANGED
@@ -1,33 +1,3 @@
1
- # == Cuca - a ruby web framework
2
- #
3
- # Cuca is a small web development framework mainly designed to build
4
- # applications - there is little focus on design but more on coding
5
- # efficiency.
6
- #
7
- # It implements the following concepts:
8
- # * A Widget is a screen element. Can be a full page or part of it.
9
- # The Controller and the Layout are Widgets, too.
10
- # * A Controller deals with one request URI (get, post or both) and can set variables
11
- # other widgets can make use of. It can also define a Layout and filters.
12
- # * A Layout wraps the output of a controller and finally return the
13
- # built web page.
14
- # * A Generator (NOT "code generator") can be used within any Widget to help building the web content.
15
- # Cuca comes with a Markaby and eruby Generator.
16
- # * A Session can used optionally to keep stateful data.
17
- #
18
- #
19
- # When you 'require' cuca you must set the global varibale $cuca_path to the root of your
20
- # application structure. This is normally done by your dispatch.cgi or dispatch.fcgi
21
- # script that comes with the cuca application skeleton.
22
- #
23
- # === See also
24
- #
25
- # * Cuca::Widget
26
- # * Cuca::Controller
27
- # * Cuca::Layout
28
- # * Cuca::Session
29
- # * Cuca::App
30
-
31
1
  require 'cgi'
32
2
  require 'cuca/cgi_fix'
33
3
  require 'rubygems'
@@ -73,6 +43,8 @@ require 'cuca/const'
73
43
 
74
44
  $cuca_path = File.expand_path($cuca_path) + '/'
75
45
 
46
+ $cuca_path.freeze
47
+
76
48
  require 'cuca/app'
77
49
 
78
50
  $LOAD_PATH << $cuca_path+'/lib'
data/lib/cuca/app.rb CHANGED
@@ -20,6 +20,8 @@ class Sandbox
20
20
  self.class.send(:include, mod)
21
21
  controller_class = mod::const_get(controller_class_name)
22
22
  controller = controller_class.send(:new, :assigns=>assigns)
23
+ $controller_object = controller
24
+
23
25
  controller.run_before_filters
24
26
 
25
27
 
@@ -33,7 +35,7 @@ class Sandbox
33
35
 
34
36
  controller.run_after_filters
35
37
 
36
- return [controller.http_status, controller.mime_type, controller.to_s]
38
+ return [controller.http_status, controller.mime_type, controller.to_s, controller.http_header]
37
39
  end
38
40
  end
39
41
 
@@ -41,9 +43,9 @@ end
41
43
  #
42
44
  # A Cuca::App object will be created directly by the dispatcher - which again is the
43
45
  # direct cgi or fastcgi script that get run by the webserver.
44
- # Normally you just create a Cuca::App object and run the cgicall function with optional with
46
+ # Normally you just create a Cuca::App object and run the cgicall method with optional with
45
47
  # a cgi object as paramenter.
46
- # Before doing that you must set $cuca_path to the root of your appication structure.
48
+ # Before doing that you must set $cuca_path to the root of your application directory structure.
47
49
  class App
48
50
 
49
51
 
@@ -70,6 +72,7 @@ class App
70
72
  @public_path.freeze
71
73
  @log_path.freeze
72
74
  @logger = Logger.new("#{@log_path}/messages")
75
+ @logger.level = App::config['logger_level'] || Logger::WARN
73
76
  end
74
77
 
75
78
 
@@ -104,14 +107,14 @@ class App
104
107
  # this will schedule all files for autoloading
105
108
  private
106
109
  def autoload_files(path, naming_proc)
107
- $app.logger.info "Autoload on #{path}"
110
+ $app.logger.debug "Autoload on #{path}"
108
111
  return unless File.exist?(path)
109
112
  pwd = Dir.pwd
110
113
  Dir.chdir(path)
111
114
  Dir['*.rb'].each do |f|
112
115
  fn = f.scan(/(.*)\.rb/)[0][0]
113
116
  classname = naming_proc.call(fn)
114
- $app.logger.info "Scheduling Autoload Object '#{classname}' ==> #{path}/#{f}"
117
+ $app.logger.debug "Scheduling Autoload Object '#{classname}' ==> #{path}/#{f}"
115
118
  cuca_register_autoload(classname.intern, "#{path}/#{f}")
116
119
  end
117
120
  Dir.chdir(pwd)
@@ -139,18 +142,7 @@ class App
139
142
 
140
143
  public
141
144
  def load_support_files(urlmap) # :nodoc:
142
- # $stderr.puts "======== load support files ========="
143
- # $stderr.puts "Inc Dir: #{App::config['include_directories'].inspect}"
144
- # $stderr.puts "Path tr: #{@conf['PATH_TREE'].inspect}"
145
- # $stderr.puts "====================================="
146
-
147
- # db = $:.dup
148
- # all_support_directories(@conf['APP_PATH']) { |d,p| $: << d }
149
-
150
- # all_support_directories(@app_path, @urlmap.path_tree) do |dir, proc|
151
- # $stderr.puts "PATH TREE: #{urlmap.path_tree.inspect}"
152
145
  all_support_directories(urlmap.path_tree) do |dir, proc|
153
- # $stderr.puts "Support Directory #{dir}"
154
146
  if proc then
155
147
  autoload_files(dir, proc)
156
148
  else
@@ -168,7 +160,7 @@ class App
168
160
  $stderr.puts "ERROR: #{title} - #{exception.class.to_s}: #{exception.to_s}"
169
161
  if (show_trace) then
170
162
  exception.backtrace.each do |b|
171
- $stderr.puts " #{b}"
163
+ $stderr.puts " #{b}"
172
164
  err +="<br/>#{b}"
173
165
  end
174
166
  else
@@ -185,7 +177,6 @@ class App
185
177
  def cgicall(cgi = nil)
186
178
  @cgi = cgi || CGI.new
187
179
 
188
-
189
180
  #
190
181
  # 1st priority: Serve a file if it exists in the 'public' folder
191
182
  #
@@ -197,7 +188,7 @@ class App
197
188
  extension = file.scan(/.*\.(.*)$/)[0][0] if file.include?('.')
198
189
  extension ||= 'html'
199
190
  mime = mt[extension] || 'text/html'
200
- @cgi.out('type' => mime,
191
+ @cgi.out('type' => mime,
201
192
  'expires' => (Time.now+App.config['http_static_content_expires'])) { f.read }
202
193
  f.close
203
194
  return
@@ -232,9 +223,6 @@ class App
232
223
  # 3rd: Load additional files
233
224
  load_support_files(@urlmap)
234
225
 
235
- test = ApplicationController.new
236
-
237
-
238
226
  # 4th: Now let's run the actual page script code
239
227
  controller_class_name = @urlmap.action.capitalize+"Controller"
240
228
 
@@ -248,8 +236,15 @@ class App
248
236
  # things fail in this block get error logged and/or displayed in browser
249
237
  begin
250
238
  # load controller
251
- controller_module.module_eval(File.open(script).read, script) unless \
252
- controller_module.const_defined?(controller_class_name.intern)
239
+ begin
240
+ controller_module.module_eval(File.open(script).read, script) unless \
241
+ controller_module.const_defined?(controller_class_name.intern)
242
+ rescue SyntaxError => e
243
+ err = get_error("Load Error", e,
244
+ Cuca::App.config['display_errors'], Cuca::App.config['http_500'])
245
+ @cgi.out('status' => 'SERVER_ERROR') { err }
246
+ return
247
+ end
253
248
 
254
249
  # Catch a common user error
255
250
  raise Cuca::ApplicationException.new("Could not find #{controller_class_name} defined in #{script}") \
@@ -257,22 +252,32 @@ class App
257
252
 
258
253
 
259
254
  # run controller
260
- (status, mime, content) = Sandbox.run(controller_class_name,
255
+ (status, mime, content, headers) = Sandbox.run(controller_class_name,
261
256
  @urlmap.action_module, @urlmap.assigns,
262
257
  @cgi.request_method, @urlmap.subcall)
263
-
264
- logger.info "CGICall OK"
265
- @cgi.out('type' => mime, 'status' => status) {content}
258
+
259
+ logger.debug "CGICall OK: #{status}/#{mime}"
260
+
261
+ @cgi.out(headers.merge( { 'type' => mime, 'status' => status} )) {content}
262
+
263
+ rescue SyntaxError => e
264
+ err = get_error("Syntax Error", e,
265
+ Cuca::App.config['display_errors'], Cuca::App.config['http_500'])
266
+ @cgi.out('status' => 'SERVER_ERROR') { err }
267
+
268
+ logger.info "CGICall Syntax Error"
269
+ return
270
+
266
271
 
267
272
  rescue Cuca::ApplicationException => e
268
273
  err = get_error("Application Error", e,
269
274
  Cuca::App.config['display_errors'], Cuca::App.config['http_500'])
270
275
  @cgi.out('status' => 'SERVER_ERROR') { err }
271
276
 
272
- logger.info "CGICall Application Error"
277
+ logger.info "CGICall Application Error"
273
278
  return
274
279
 
275
- rescue => e
280
+ rescue => e
276
281
  err = get_error("System Error", e,
277
282
  Cuca::App.config['display_errors'], Cuca::App.config['http_500'])
278
283
  @cgi.out('status' => 'SERVER_ERROR') { err }