ramaze 0.1.0 → 0.1.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (195) hide show
  1. data/Rakefile +4 -12
  2. data/bin/ramaze +95 -171
  3. data/doc/CHANGELOG +387 -4
  4. data/doc/README +81 -13
  5. data/doc/meta/announcement.txt +51 -8
  6. data/doc/meta/configuration.txt +17 -34
  7. data/doc/meta/internals.txt +34 -4
  8. data/doc/migrate/1110_to_1111.txt +131 -0
  9. data/doc/readme_chunks/features.txt +81 -12
  10. data/doc/readme_chunks/installing.txt +0 -1
  11. data/doc/tutorial/todolist.html +293 -65
  12. data/doc/tutorial/{todolist.txt → todolist.mkd} +251 -51
  13. data/examples/blog/main.rb +1 -1
  14. data/examples/blog/src/model.rb +0 -1
  15. data/examples/hello.rb +2 -5
  16. data/examples/templates/template/external.haml +5 -5
  17. data/examples/templates/template/external.liquid +1 -1
  18. data/examples/templates/template/external.mab +8 -8
  19. data/examples/templates/template/external.rem +30 -0
  20. data/examples/templates/template/external.rhtml +6 -7
  21. data/examples/templates/template/external.zmr +13 -9
  22. data/examples/templates/template_amrita2.rb +8 -8
  23. data/examples/templates/template_erubis.rb +11 -11
  24. data/examples/templates/template_ezamar.rb +9 -11
  25. data/examples/templates/template_haml.rb +13 -13
  26. data/examples/templates/template_liquid.rb +10 -10
  27. data/examples/templates/template_markaby.rb +13 -10
  28. data/examples/templates/template_remarkably.rb +59 -0
  29. data/examples/todolist/main.rb +1 -7
  30. data/examples/todolist/src/controller/main.rb +26 -13
  31. data/examples/todolist/src/element/page.rb +5 -0
  32. data/examples/whywiki/main.rb +1 -1
  33. data/lib/proto/main.rb +0 -8
  34. data/lib/proto/public/css/ramaze_error.css +12 -4
  35. data/lib/proto/public/error.zmr +6 -25
  36. data/lib/ramaze.rb +35 -245
  37. data/lib/ramaze/action.rb +21 -0
  38. data/lib/ramaze/adapter.rb +94 -29
  39. data/lib/ramaze/adapter/base.rb +57 -0
  40. data/lib/ramaze/adapter/mongrel.rb +12 -19
  41. data/lib/ramaze/adapter/webrick.rb +21 -20
  42. data/lib/ramaze/cache.rb +47 -3
  43. data/lib/ramaze/cache/memcached.rb +22 -0
  44. data/lib/ramaze/cache/yaml_store.rb +19 -0
  45. data/lib/ramaze/controller.rb +47 -271
  46. data/lib/ramaze/controller/error.rb +43 -0
  47. data/lib/ramaze/controller/render.rb +90 -0
  48. data/lib/ramaze/controller/resolve.rb +147 -0
  49. data/lib/ramaze/dispatcher.rb +41 -9
  50. data/lib/ramaze/dispatcher/file.rb +1 -1
  51. data/lib/ramaze/global.rb +73 -158
  52. data/lib/ramaze/global/dsl.rb +29 -0
  53. data/lib/ramaze/global/globalstruct.rb +90 -0
  54. data/lib/ramaze/helper.rb +1 -1
  55. data/lib/ramaze/helper/aspect.rb +39 -179
  56. data/lib/ramaze/helper/cache.rb +8 -9
  57. data/lib/ramaze/helper/cgi.rb +23 -0
  58. data/lib/ramaze/helper/file.rb +3 -0
  59. data/lib/ramaze/helper/inform.rb +3 -0
  60. data/lib/ramaze/helper/link.rb +56 -63
  61. data/lib/ramaze/helper/nitroform.rb +4 -0
  62. data/lib/ramaze/helper/redirect.rb +1 -1
  63. data/lib/ramaze/inform.rb +6 -2
  64. data/lib/ramaze/inform/analogger.rb +5 -1
  65. data/lib/ramaze/inform/hub.rb +1 -1
  66. data/lib/ramaze/inform/informing.rb +7 -0
  67. data/lib/ramaze/snippets/kernel/aquire.rb +2 -0
  68. data/lib/ramaze/snippets/kernel/constant.rb +2 -0
  69. data/lib/ramaze/snippets/kernel/pretty_inspect.rb +2 -0
  70. data/lib/ramaze/snippets/object/traits.rb +4 -0
  71. data/lib/ramaze/snippets/openstruct/temp.rb +3 -0
  72. data/lib/ramaze/snippets/string/DIVIDE.rb +2 -0
  73. data/lib/ramaze/snippets/string/camel_case.rb +2 -0
  74. data/lib/ramaze/snippets/string/color.rb +2 -0
  75. data/lib/ramaze/snippets/string/each.rb +2 -0
  76. data/lib/ramaze/snippets/string/snake_case.rb +3 -0
  77. data/lib/ramaze/snippets/struct/fill.rb +8 -2
  78. data/lib/ramaze/snippets/struct/values_at.rb +16 -0
  79. data/lib/ramaze/snippets/symbol/to_proc.rb +3 -0
  80. data/lib/ramaze/sourcereload.rb +89 -0
  81. data/lib/ramaze/template.rb +21 -12
  82. data/lib/ramaze/template/amrita2.rb +6 -6
  83. data/lib/ramaze/template/erubis.rb +4 -9
  84. data/lib/ramaze/template/ezamar.rb +13 -57
  85. data/lib/ramaze/template/ezamar/element.rb +10 -12
  86. data/lib/ramaze/template/ezamar/engine.rb +40 -101
  87. data/lib/ramaze/template/ezamar/morpher.rb +3 -3
  88. data/lib/ramaze/template/haml.rb +3 -6
  89. data/lib/ramaze/template/liquid.rb +4 -9
  90. data/lib/ramaze/template/markaby.rb +16 -22
  91. data/lib/ramaze/template/remarkably.rb +28 -0
  92. data/lib/ramaze/tool/mime.rb +2 -0
  93. data/lib/ramaze/tool/record.rb +6 -0
  94. data/lib/ramaze/trinity/request.rb +44 -54
  95. data/lib/ramaze/trinity/response.rb +1 -1
  96. data/lib/ramaze/trinity/session.rb +15 -37
  97. data/lib/ramaze/version.rb +1 -1
  98. data/rake_tasks/gem.rake +2 -2
  99. data/rake_tasks/maintaince.rake +42 -1
  100. data/rake_tasks/spec.rake +45 -0
  101. data/spec/examples/caching.rb +1 -1
  102. data/spec/examples/simple.rb +1 -1
  103. data/spec/examples/templates/template_amrita2.rb +1 -0
  104. data/spec/examples/templates/template_erubis.rb +2 -1
  105. data/spec/examples/templates/template_ezamar.rb +1 -1
  106. data/spec/examples/templates/template_haml.rb +2 -1
  107. data/spec/examples/templates/template_liquid.rb +2 -1
  108. data/spec/examples/templates/template_markaby.rb +2 -1
  109. data/spec/examples/templates/template_remarkably.rb +22 -0
  110. data/spec/examples/todolist.rb +125 -0
  111. data/spec/helper.rb +2 -23
  112. data/spec/helper/minimal.rb +20 -0
  113. data/spec/helper/mock_http.rb +24 -30
  114. data/spec/helper/simple_http.rb +2 -2
  115. data/spec/helper/wrap.rb +6 -9
  116. data/spec/ramaze/adapter.rb +1 -1
  117. data/spec/ramaze/adapter/record.rb +31 -0
  118. data/spec/ramaze/cache.rb +41 -54
  119. data/spec/ramaze/controller.rb +121 -137
  120. data/spec/ramaze/controller/template/list.xhtml +1 -0
  121. data/spec/ramaze/controller/template/other/greet/other.xhtml +1 -0
  122. data/spec/ramaze/controller/template_resolving.rb +27 -3
  123. data/spec/ramaze/element.rb +11 -7
  124. data/spec/ramaze/error.rb +1 -1
  125. data/spec/ramaze/gestalt.rb +2 -0
  126. data/spec/ramaze/helper/aspect.rb +30 -21
  127. data/spec/ramaze/helper/auth.rb +1 -1
  128. data/spec/ramaze/helper/cache.rb +2 -1
  129. data/spec/ramaze/helper/form.rb +14 -11
  130. data/spec/ramaze/helper/link.rb +18 -41
  131. data/spec/ramaze/localize.rb +29 -2
  132. data/spec/ramaze/morpher.rb +23 -12
  133. data/spec/ramaze/params.rb +46 -24
  134. data/spec/ramaze/request.rb +6 -2
  135. data/spec/ramaze/store/yaml.rb +5 -0
  136. data/spec/ramaze/template.rb +22 -27
  137. data/spec/ramaze/template/amrita2.rb +1 -2
  138. data/spec/ramaze/template/erubis.rb +1 -1
  139. data/spec/ramaze/template/ezamar.rb +1 -2
  140. data/spec/ramaze/template/haml.rb +2 -2
  141. data/spec/ramaze/template/haml/with_vars.haml +1 -1
  142. data/spec/ramaze/template/liquid.rb +1 -1
  143. data/spec/ramaze/template/markaby.rb +1 -1
  144. data/spec/ramaze/template/remarkably.rb +56 -0
  145. data/spec/ramaze/template/remarkably/external.rem +8 -0
  146. data/spec/ramaze/template/remarkably/sum.rem +1 -0
  147. metadata +38 -63
  148. data/doc/README.html +0 -637
  149. data/doc/allison/LICENSE +0 -184
  150. data/doc/allison/README +0 -37
  151. data/doc/allison/allison.css +0 -299
  152. data/doc/allison/allison.gif +0 -0
  153. data/doc/allison/allison.js +0 -307
  154. data/doc/allison/allison.rb +0 -287
  155. data/doc/allison/cache/BODY +0 -588
  156. data/doc/allison/cache/CLASS_INDEX +0 -4
  157. data/doc/allison/cache/CLASS_PAGE +0 -1
  158. data/doc/allison/cache/FILE_INDEX +0 -4
  159. data/doc/allison/cache/FILE_PAGE +0 -1
  160. data/doc/allison/cache/FONTS +0 -1
  161. data/doc/allison/cache/FR_INDEX_BODY +0 -1
  162. data/doc/allison/cache/IMGPATH +0 -1
  163. data/doc/allison/cache/INDEX +0 -1
  164. data/doc/allison/cache/JAVASCRIPT +0 -307
  165. data/doc/allison/cache/METHOD_INDEX +0 -4
  166. data/doc/allison/cache/METHOD_LIST +0 -1
  167. data/doc/allison/cache/SRC_PAGE +0 -1
  168. data/doc/allison/cache/STYLE +0 -321
  169. data/doc/allison/cache/URL +0 -1
  170. data/doc/changes.txt +0 -3375
  171. data/doc/changes.xml +0 -3378
  172. data/examples/todolist/conf/benchmark.yaml +0 -35
  173. data/examples/todolist/conf/debug.yaml +0 -34
  174. data/examples/todolist/conf/live.yaml +0 -33
  175. data/examples/todolist/conf/silent.yaml +0 -31
  176. data/examples/todolist/conf/stage.yaml +0 -33
  177. data/examples/todolist/public/css/coderay.css +0 -105
  178. data/examples/todolist/public/css/ramaze_error.css +0 -42
  179. data/lib/proto/conf/benchmark.yaml +0 -21
  180. data/lib/proto/conf/debug.yaml +0 -21
  181. data/lib/proto/conf/live.yaml +0 -21
  182. data/lib/proto/conf/silent.yaml +0 -21
  183. data/lib/proto/conf/stage.yaml +0 -21
  184. data/lib/proto/public/css/coderay.css +0 -105
  185. data/lib/ramaze/http_status.rb +0 -66
  186. data/lib/ramaze/snippets/hash/keys_to_sym.rb +0 -19
  187. data/lib/ramaze/snippets/kernel/method.rb +0 -26
  188. data/lib/ramaze/snippets/method/name.rb +0 -22
  189. data/lib/ramaze/snippets/ramaze/autoreload.rb +0 -135
  190. data/lib/ramaze/snippets/rdoc/usage_no_exit.rb +0 -65
  191. data/spec/all.rb +0 -32
  192. data/spec/ramaze/conf/locale_de.yaml +0 -6
  193. data/spec/ramaze/conf/locale_en.yaml +0 -6
  194. data/spec/ramaze/dependencies.rb +0 -16
  195. data/spec/ramaze/global.rb +0 -44
@@ -4,87 +4,80 @@
4
4
  module Ramaze
5
5
  # LinkHelper is included into the Controller by default
6
6
  #
7
- # this helper tries to get along without any major magic, the only 'magic'
8
- # thing is that it looks up controller-paths if you pass it a controller
9
- # the text shown is always the last segmet of the finished link from split('/')
10
- #
11
- # usage is pretty much shown in test/tc_helper
12
- # however, to give you some idea of how it actually works, some examples:
13
- #
14
- # link MainController, :foo #=> '<a href="/foo">foo</a>'
15
- # link MinorController, :foo #=> '<a href="/minor/foo">foo</a>'
16
- # link MinorController, :foo, :bar #=> '<a href="/minor/foo/bar">bar</a>'
17
- # link MainController, :foo, :raw => true #=> '/foo'
18
- # link MainController, :foo => :bar #=> '/?foo=bar'
19
- #
20
- # link_raw MainController, :foo #=> '/foo'
21
- # link_raw MinorController, :foo #=> '/minor/foo'
22
- # link_raw MinorController, :foo, :bar #=> '/minor/foo/bar'
23
- #
24
- # TODO:
25
- # - handling of no passed parameters
26
- # - setting imagelinks
27
- # - setting of id or class
28
- # - taking advantae of Gestalt to build links
29
- # - lots of other minor niceties, for the moment i'm only concerned to keep
30
- # it as simple as possible
31
- #
7
+ # Usage is pretty much shown in test/tc_helper and the rdocs below.
32
8
 
33
9
  module LinkHelper
34
10
 
35
11
  private
36
12
 
13
+ # Builds a basic <a> tag.
14
+ #
15
+ # `title` is mandatory, the second hash of options will be transformed into
16
+ # arguments of the tag, :href is a special case and its segments will be
17
+ # CGI.escaped.
18
+ #
19
+ # If you pass no :href, the title will be run through Rs and its result is
20
+ # used instead. If you really want an empty href, use :href => ''
21
+ #
37
22
  # Usage:
38
- # link MainController, :foo #=> '<a href="/foo">foo</a>'
39
- # link MinorController, :foo #=> '<a href="/minor/foo">foo</a>'
40
- # link MinorController, :foo, :bar #=> '<a href="/minor/foo/bar">bar</a>'
41
- # link MainController, :foo, :raw => true #=> '/foo'
42
- # link MainController, :foo, :title => 'a' #=> '<a href="/minor/foo/bar">a</a>'
43
- # link MainController, :foo => :bar #=> '/?foo=bar'
23
+ # A('title') #=> <a href="/title">title</a>
24
+ # A('foo/bar') #=> <a href="/foo/bar">foo/bar</a>
25
+ # A('Home' :href => Rs(:/)) #=> <a href="/foo/bar">foo/bar</a>
44
26
 
45
- def Rlink *to
46
- hash = to.last.is_a?(Hash) ? to.pop : {}
27
+ def A(title, hash = {})
28
+ hash[:href] ||= Rs(title)
29
+ hash[:href].to_s.gsub!(/[^\/]+/){|m| CGI.escape(m) }
47
30
 
48
- to = to.flatten
31
+ args = ['']
32
+ hash.each{|k,v| args << %(#{k}="#{v}") if k and v }
49
33
 
50
- to.map! do |t|
51
- t = t.class if not t.respond_to?(:transform) and t.is_a?(Controller)
52
- Global.mapping.invert[t] || t
53
- end
34
+ %(<a#{args.join(' ')}>#{title || hash[:href]}</a>)
35
+ end
54
36
 
55
- raw, title = hash.delete(:raw), hash.delete(:title)
56
- params = {:class => hash.delete(:class), :id => hash.delete(:id)}
57
- opts = hash.inject('?'){|s,(k,v)| s << "#{k}=#{v};"}[0..-2]
58
- link = to.join('/').squeeze('/') << (opts.empty? ? '' : opts)
37
+ # Builds links out of segments.
38
+ #
39
+ # Pass it strings, symbols, controllers and it will produce a link out of
40
+ # it. Paths to Controllers are obtained from Global.mapping.
41
+ #
42
+ # For brevity, the mapping for the example below is following:
43
+ # { MC => '/', OC => '/o', ODC => '/od' }
44
+ #
45
+ # Usage:
46
+ # R(MC) #=> '/'
47
+ # R(OC) #=> '/o'
48
+ # R(ODC) #=> '/od'
49
+ # R(MC, :foo) #=> '/foo'
50
+ # R(OC, :foo) #=> '/o/foo'
51
+ # R(ODC, :foo) #=> '/od/foo'
52
+ # R(MC, :foo, :bar => :x) #=> '/foo?bar=x'
59
53
 
60
- if raw
61
- link
62
- else
63
- title ||= link.split('/').last.to_s.split('?').first || 'index'
64
- params = params.inject(''){|s,(k,v)| s + (k and v ? %{ #{k}="#{v}"} : '')}
65
- l = %{<a href="#{link}"#{params}>#{title}</a>}
54
+ def R(*atoms)
55
+ args, atoms = atoms.partition{|a| a.is_a?(Hash) }
56
+ args = args.flatten.inject{|s,v| s.merge!(v) }
57
+
58
+ map = Global.mapping.invert
59
+ atoms.map! do |atom|
60
+ if atom.respond_to?(:new)
61
+ map[atom] || atom
62
+ else
63
+ map[atom.class] || atom
64
+ end
66
65
  end
67
- end
68
66
 
69
- alias link Rlink
67
+ front = atoms.join('/').squeeze('/')
70
68
 
71
- # Usage:
72
- # R MainController, :foo #=> '/foo'
73
- # R MinorController, :foo #=> '/minor/foo'
74
- # R MinorController, :foo, :bar #=> '/minor/foo/bar'
75
-
76
- def R *to
77
- if to.last.is_a?(Hash)
78
- to.last[:raw] = true
69
+ if args
70
+ rear = args.inject('?'){|s,(k,v)| s << "#{k}=#{v};"}[0..-2]
71
+ front + rear
79
72
  else
80
- to << {:raw => true}
73
+ front
81
74
  end
82
-
83
- Rlink(*to)
84
75
  end
85
76
 
86
- def Rs(*to)
87
- R(Controller.current, *to)
77
+ # Uses R with self as first element.
78
+
79
+ def Rs(*atoms)
80
+ R(self, *atoms)
88
81
  end
89
82
  end
90
83
  end
@@ -4,6 +4,10 @@
4
4
  require 'nitro/helper/form'
5
5
 
6
6
  module Ramaze
7
+
8
+ # This helper simply includes the Nitro::FormHelper so you can use its methods
9
+ # in your Controller.
10
+
7
11
  module NitroformHelper
8
12
  include ::Nitro::FormHelper
9
13
  end
@@ -34,7 +34,7 @@ module Ramaze
34
34
  'Location' => target
35
35
  }.merge(response.header)
36
36
 
37
- status = opts[:status] || STATUS_CODE[:see_other]
37
+ status = opts[:status] || STATUS_CODE["See Other"]
38
38
 
39
39
  body = %{Please follow <a href="#{target}">#{target}</a>!}
40
40
 
@@ -2,12 +2,16 @@
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
4
  require 'ramaze/inform/informing'
5
+ require 'ramaze/inform/hub'
6
+ require 'ramaze/inform/informer'
5
7
 
6
8
  module Ramaze
7
9
  autoload :Analogger, "ramaze/inform/analogger.rb"
8
- autoload :Informer, "ramaze/inform/informer.rb"
9
10
  autoload :Syslog, "ramaze/inform/syslog.rb"
10
11
  autoload :Growl, "ramaze/inform/growl.rb"
11
12
  autoload :Xosd, "ramaze/inform/xosd.rb"
12
- autoload :LogHub, "ramaze/inform/hub.rb"
13
+
14
+ unless defined?(Inform)
15
+ Inform = LogHub.new(Informer)
16
+ end
13
17
  end
@@ -8,7 +8,11 @@ module Ramaze
8
8
  class Analogger < ::Swiftcore::Analogger::Client
9
9
  include Informing
10
10
 
11
- def initialize(name = 'walrus', host = '127.0.0.1', port = 6766)
11
+ trait :name => 'walrus'
12
+ trait :host => '127.0.0.1'
13
+ trait :port => 6766
14
+
15
+ def initialize(name = class_trait[:name], host = class_trait[:host], port = class_trait[:port])
12
16
  super
13
17
  end
14
18
 
@@ -10,9 +10,9 @@ module Ramaze
10
10
  def initialize(*loggers)
11
11
  @loggers = loggers
12
12
  @loggers.map! do |logger|
13
+ next(nil) if logger == self
13
14
  logger.is_a?(Class) ? logger.new : logger
14
15
  end
15
- @loggers.delete_if {|x| x == self }
16
16
  @loggers.uniq!
17
17
  @loggers.compact!
18
18
  end
@@ -27,6 +27,7 @@ module Ramaze
27
27
  def error(ex)
28
28
  if ex.respond_to?(:exception)
29
29
  message = ex.backtrace[0..Global.backtrace_size]
30
+ message.map!{|m| m.gsub(/^#{Dir.pwd}/, '.') }
30
31
  message.unshift(ex.inspect)
31
32
  else
32
33
  message = ex.to_s
@@ -40,5 +41,11 @@ module Ramaze
40
41
 
41
42
  def shutdown
42
43
  end
44
+
45
+ # stub for WEBrick
46
+
47
+ def debug?
48
+ false
49
+ end
43
50
  end
44
51
  end
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for Kernel
5
+
4
6
  module Kernel
5
7
 
6
8
  # Example:
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for Kernel
5
+
4
6
  module Kernel
5
7
  # Original from Trans (Facets 1.4.5)
6
8
  # This is similar to +Module#const_get+ but is accessible at all levels,
@@ -3,6 +3,8 @@
3
3
 
4
4
  require 'pp'
5
5
 
6
+ # Extensions for Kernel
7
+
6
8
  module Kernel
7
9
  unless defined?(pretty_inspect)
8
10
  # returns a pretty printed object as a string.
@@ -3,6 +3,8 @@
3
3
 
4
4
  Traits = Hash.new{|h,k| h[k] = {}} unless defined?(Traits)
5
5
 
6
+ # Extensions for Object
7
+
6
8
  class Object
7
9
 
8
10
  # Adds a method to Object to annotate your objects with certain traits.
@@ -62,6 +64,8 @@ class Object
62
64
  ancs.reverse.inject({}){|s,v| s.merge(v.trait)}.merge(trait)
63
65
  end
64
66
 
67
+ # trait for self.class
68
+
65
69
  def class_trait
66
70
  if respond_to?(:ancestors)
67
71
  trait
@@ -1,5 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
+
4
+ # Extensions for OpenStruct
5
+
3
6
  class OpenStruct
4
7
 
5
8
  # create a new OpenStruct and fill it with a merge of the old @table and the passed hash
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for String
5
+
4
6
  class String
5
7
 
6
8
  # A convinient way to do File.join
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for String
5
+
4
6
  class String
5
7
 
6
8
  # simple transformation to CamelCase from snake_case
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for String
5
+
4
6
  class String
5
7
 
6
8
  {
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for String
5
+
4
6
  class String
5
7
  alias each each_line unless ''.respond_to?(:each)
6
8
  end
@@ -1,5 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
+
4
+ # Extensions for String
5
+
3
6
  class String
4
7
 
5
8
  # convert to snake_case from CamelCase
@@ -1,6 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
+ # Extensions for Struct
5
+
4
6
  class Struct
5
7
 
6
8
  # Action = Struct.new('Action', :template, :method, :params)
@@ -9,7 +11,11 @@ class Struct
9
11
  # # => #<struct Struct::Action template=nil, method=:meth, params=[1]>
10
12
 
11
13
  def self.fill(hash = {})
12
- values = hash.values_at(*members.map{|m| m.to_sym})
13
- new(*values)
14
+ instance = new
15
+ hash.each do |key, value|
16
+ next unless members.include?(key.to_s)
17
+ instance.send("#{key}=", value)
18
+ end
19
+ instance
14
20
  end
15
21
  end
@@ -0,0 +1,16 @@
1
+ # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
+ # All files in this distribution are subject to the terms of the Ruby license.
3
+
4
+ # Extensions for Struct
5
+
6
+ class Struct
7
+
8
+ # Point = Struct.new(:x, :y)
9
+ # point = Point.new(15, 10)
10
+ # point.values_at(:y, :x)
11
+ # # => [10, 15]
12
+
13
+ def values_at(*keys)
14
+ keys.map{|k| self[k.to_sym] }
15
+ end
16
+ end
@@ -1,5 +1,8 @@
1
1
  # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
+
4
+ # Extensions for Symbol
5
+
3
6
  class Symbol
4
7
 
5
8
  # the well-known #to_proc
@@ -0,0 +1,89 @@
1
+ # Copyright (c) 2006 Michael Fellinger m.fellinger@gmail.com
2
+ # All files in this distribution are subject to the terms of the Ruby license.
3
+
4
+ require 'set'
5
+
6
+ module Ramaze
7
+ class SourceReload
8
+ attr_accessor :thread, :interval, :reload_glob, :map
9
+
10
+ def initialize interval = 1, reload_glob = %r{(^\./)|#{Dir.pwd}|ramaze}
11
+ @interval, @reload_glob = interval, reload_glob
12
+ @mtimes, @map = {}, []
13
+ end
14
+
15
+ def start
16
+ Inform.debug("initialize automatic source reload every #{interval} seconds")
17
+ @thread = reloader
18
+ end
19
+
20
+ def self.startup options = {}
21
+ interval = Global.sourcereload
22
+ instance = new(interval)
23
+ Thread.main[:sourcereload] = instance
24
+ instance.reload # initial scan of all files
25
+ instance.start if interval
26
+ end
27
+
28
+ def reloader
29
+ Thread.new do
30
+ loop do
31
+ reload
32
+ sleep(@interval)
33
+ end
34
+ end
35
+ end
36
+
37
+ # This method is quite handy if you want direct control over when your code is reloaded
38
+ #
39
+ # Usage example:
40
+ #
41
+ # trap :HUB do
42
+ # Ramaze::Inform.info "reloading source"
43
+ # Thread.main[:sourcereload].reload
44
+ # end
45
+ #
46
+
47
+ def reload
48
+ all_reload_files.each do |file|
49
+ mtime = mtime(file)
50
+
51
+ next if (@mtimes[file] ||= mtime) == mtime
52
+
53
+ Inform.debug("reload #{file}")
54
+ @mtimes[file] = mtime if safe_load(file)
55
+ end
56
+ end
57
+
58
+ def all_reload_files
59
+ files, paths = $LOADED_FEATURES, Array['', './', *$LOAD_PATH]
60
+
61
+ unless [@files, @paths] == [files, paths]
62
+ @files, @paths = files.dup, paths.dup
63
+
64
+ map = files.map do |file|
65
+ possible = paths.map{|pa| File.join(pa.to_s, file.to_s) }
66
+ possible.find{|po| File.exists?(po) }
67
+ end
68
+
69
+ @map = map.compact
70
+ end
71
+
72
+ m = @map.grep(@reload_glob)
73
+ end
74
+
75
+ def mtime(file)
76
+ File.mtime(file)
77
+ rescue Errno::ENOENT
78
+ false
79
+ end
80
+
81
+ def safe_load(file)
82
+ load(file)
83
+ true
84
+ rescue Object => ex
85
+ Inform.error(ex)
86
+ false
87
+ end
88
+ end
89
+ end