ramaze 2011.07.25 → 2011.10.23

Sign up to get free protection for your applications and to get access to all the features.
Files changed (181) hide show
  1. data/.gitignore +3 -0
  2. data/.mailmap +3 -2
  3. data/.travis.yml +17 -0
  4. data/.yardopts +13 -0
  5. data/README.md +95 -352
  6. data/examples/app/blog/app.rb +25 -64
  7. data/examples/app/blog/config.ru +11 -9
  8. data/examples/app/blog/controller/init.rb +29 -86
  9. data/examples/app/blog/controller/posts.rb +232 -0
  10. data/examples/app/blog/controller/users.rb +160 -0
  11. data/examples/app/blog/layout/default.xhtml +61 -0
  12. data/examples/app/blog/migrations/01_create_schema.rb +50 -0
  13. data/examples/app/blog/model/comment.rb +41 -54
  14. data/examples/app/blog/model/init.rb +41 -13
  15. data/examples/app/blog/model/post.rb +35 -0
  16. data/examples/app/blog/model/user.rb +105 -0
  17. data/examples/app/blog/public/.htaccess +24 -0
  18. data/examples/app/blog/public/css/grid.css +107 -0
  19. data/examples/app/blog/public/css/layout.css +203 -0
  20. data/examples/app/blog/public/css/reset.css +123 -0
  21. data/examples/app/blog/public/css/text.css +109 -0
  22. data/examples/app/blog/public/dispatch.fcgi +11 -0
  23. data/examples/app/blog/public/favicon.ico +0 -0
  24. data/examples/app/blog/public/images/bg.png +0 -0
  25. data/examples/app/blog/start.rb +18 -3
  26. data/examples/app/blog/view/feed.xhtml +23 -0
  27. data/examples/app/blog/view/form.xhtml +11 -0
  28. data/examples/app/blog/view/index.xhtml +44 -0
  29. data/examples/app/blog/view/users/form.xhtml +12 -0
  30. data/examples/app/blog/view/users/index.xhtml +30 -0
  31. data/examples/app/blog/view/users/login.xhtml +8 -0
  32. data/examples/app/blog/view/view.xhtml +68 -0
  33. data/{doc → guide}/AUTHORS +5 -3
  34. data/{doc → guide}/CHANGELOG +428 -0
  35. data/{doc/GPL → guide/GPL_LICENSE} +0 -0
  36. data/{doc/COPYING → guide/RUBY_LICENSE} +3 -6
  37. data/guide/_static/logo.png +0 -0
  38. data/guide/_static/logo.svg +49 -0
  39. data/guide/_static/ramaze_console.png +0 -0
  40. data/guide/css/common.css +20 -0
  41. data/guide/general/cache.md +167 -0
  42. data/guide/general/configuration.md +168 -0
  43. data/guide/general/contributing.md +108 -0
  44. data/guide/general/controllers.md +115 -0
  45. data/guide/general/helpers.md +76 -0
  46. data/guide/general/installation.md +58 -0
  47. data/guide/general/logging.md +99 -0
  48. data/guide/general/middlewares.md +100 -0
  49. data/guide/general/models.md +78 -0
  50. data/guide/general/principles.md +53 -0
  51. data/guide/general/ramaze_command.md +155 -0
  52. data/guide/general/routes.md +81 -0
  53. data/guide/general/sessions.md +140 -0
  54. data/guide/general/special_thanks.md +67 -0
  55. data/guide/general/testing.md +61 -0
  56. data/guide/general/views.md +322 -0
  57. data/guide/tutorials/introduction.md +259 -0
  58. data/lib/proto/config.ru +1 -1
  59. data/lib/proto/public/favicon.ico +0 -0
  60. data/lib/proto/view/index.xhtml +7 -7
  61. data/lib/ramaze.rb +4 -4
  62. data/lib/ramaze/app.rb +11 -11
  63. data/lib/ramaze/app_graph.rb +2 -4
  64. data/lib/ramaze/bin/console.rb +3 -3
  65. data/lib/ramaze/bin/create.rb +2 -2
  66. data/lib/ramaze/bin/restart.rb +4 -4
  67. data/lib/ramaze/bin/runner.rb +5 -5
  68. data/lib/ramaze/bin/start.rb +19 -4
  69. data/lib/ramaze/bin/status.rb +3 -3
  70. data/lib/ramaze/bin/stop.rb +3 -3
  71. data/lib/ramaze/cache.rb +1 -0
  72. data/lib/ramaze/cache/lru.rb +8 -4
  73. data/lib/ramaze/cache/memcache.rb +32 -13
  74. data/lib/ramaze/cache/redis.rb +164 -0
  75. data/lib/ramaze/cache/sequel.rb +43 -28
  76. data/lib/ramaze/controller.rb +1 -2
  77. data/lib/ramaze/dependencies.rb +40 -3
  78. data/lib/ramaze/helper/bench.rb +26 -16
  79. data/lib/ramaze/helper/blue_form.rb +46 -73
  80. data/lib/ramaze/helper/cache.rb +10 -6
  81. data/lib/ramaze/helper/csrf.rb +35 -39
  82. data/lib/ramaze/helper/disqus.rb +5 -4
  83. data/lib/ramaze/helper/email.rb +35 -24
  84. data/lib/ramaze/helper/erector.rb +9 -13
  85. data/lib/ramaze/helper/flash.rb +7 -9
  86. data/lib/ramaze/helper/formatting.rb +194 -179
  87. data/lib/ramaze/helper/gravatar.rb +4 -8
  88. data/lib/ramaze/helper/identity.rb +3 -3
  89. data/lib/ramaze/helper/layout.rb +23 -8
  90. data/lib/ramaze/helper/markaby.rb +1 -1
  91. data/lib/ramaze/helper/paginate.rb +46 -39
  92. data/lib/ramaze/helper/request_accessor.rb +3 -1
  93. data/lib/ramaze/helper/simple_captcha.rb +18 -17
  94. data/lib/ramaze/helper/stack.rb +1 -1
  95. data/lib/ramaze/helper/tagz.rb +4 -2
  96. data/lib/ramaze/helper/upload.rb +523 -0
  97. data/lib/ramaze/helper/user.rb +4 -8
  98. data/lib/ramaze/helper/xhtml.rb +11 -15
  99. data/lib/ramaze/log.rb +9 -6
  100. data/lib/ramaze/log/rotatinginformer.rb +62 -27
  101. data/lib/ramaze/log/syslog.rb +20 -15
  102. data/lib/ramaze/log/xosd.rb +2 -1
  103. data/lib/ramaze/reloader.rb +2 -0
  104. data/lib/ramaze/request.rb +11 -10
  105. data/lib/ramaze/setup.rb +23 -6
  106. data/lib/ramaze/snippets/array/put_within.rb +3 -9
  107. data/lib/ramaze/snippets/binding/locals.rb +5 -10
  108. data/lib/ramaze/snippets/fiber.rb +1 -23
  109. data/lib/ramaze/snippets/kernel/pretty_inspect.rb +3 -6
  110. data/lib/ramaze/snippets/numeric/filesize_format.rb +3 -5
  111. data/lib/ramaze/snippets/numeric/time.rb +3 -7
  112. data/lib/ramaze/snippets/object/__dir__.rb +3 -7
  113. data/lib/ramaze/snippets/object/instance_variable_defined.rb +3 -6
  114. data/lib/ramaze/snippets/object/pretty.rb +3 -7
  115. data/lib/ramaze/snippets/object/scope.rb +7 -9
  116. data/lib/ramaze/snippets/proc/locals.rb +12 -12
  117. data/lib/ramaze/snippets/ramaze/acquire.rb +15 -14
  118. data/lib/ramaze/snippets/ramaze/deprecated.rb +1 -1
  119. data/lib/ramaze/snippets/ramaze/fiber.rb +1 -1
  120. data/lib/ramaze/snippets/ramaze/lru_hash.rb +2 -3
  121. data/lib/ramaze/snippets/ramaze/struct.rb +2 -4
  122. data/lib/ramaze/snippets/string/camel_case.rb +8 -10
  123. data/lib/ramaze/snippets/string/color.rb +3 -4
  124. data/lib/ramaze/snippets/string/end_with.rb +3 -6
  125. data/lib/ramaze/snippets/string/esc.rb +3 -8
  126. data/lib/ramaze/snippets/string/ord.rb +3 -8
  127. data/lib/ramaze/snippets/string/snake_case.rb +6 -9
  128. data/lib/ramaze/snippets/string/start_with.rb +3 -8
  129. data/lib/ramaze/snippets/string/unindent.rb +3 -6
  130. data/lib/ramaze/snippets/thread/into.rb +1 -3
  131. data/lib/ramaze/spec.rb +2 -31
  132. data/lib/ramaze/spec/bacon.rb +18 -2
  133. data/lib/ramaze/version.rb +1 -1
  134. data/lib/ramaze/view.rb +1 -1
  135. data/ramaze.gemspec +1 -1
  136. data/spec/helper.rb +2 -1
  137. data/spec/ramaze/bin/start.rb +16 -20
  138. data/spec/ramaze/cache/localmemcache.rb +4 -7
  139. data/spec/ramaze/cache/memcache.rb +3 -1
  140. data/spec/ramaze/cache/redis.rb +62 -0
  141. data/spec/ramaze/helper/blue_form.rb +33 -4
  142. data/spec/ramaze/helper/layout.rb +40 -7
  143. data/spec/ramaze/helper/upload.rb +149 -0
  144. data/spec/ramaze/helper/uploads/text_1.txt +1 -0
  145. data/spec/ramaze/helper/uploads/text_2.txt +1 -0
  146. data/spec/ramaze/log/growl.rb +4 -6
  147. data/spec/ramaze/log/syslog.rb +6 -0
  148. data/spec/ramaze/view/lokar.rb +5 -0
  149. data/spec/ramaze/view/nagoro.rb +5 -0
  150. data/tasks/authors.rake +1 -1
  151. data/tasks/bacon.rake +14 -5
  152. data/tasks/changelog.rake +1 -1
  153. data/tasks/yard.rake +12 -4
  154. metadata +277 -239
  155. data/doc/LEGAL +0 -26
  156. data/examples/app/blog/README +0 -3
  157. data/examples/app/blog/controller/comment.rb +0 -45
  158. data/examples/app/blog/controller/entry.rb +0 -85
  159. data/examples/app/blog/controller/main.rb +0 -20
  160. data/examples/app/blog/controller/tag.rb +0 -9
  161. data/examples/app/blog/layout/default.nag +0 -31
  162. data/examples/app/blog/model/entry.rb +0 -89
  163. data/examples/app/blog/model/tag.rb +0 -36
  164. data/examples/app/blog/public/css/screen.css +0 -273
  165. data/examples/app/blog/spec/blog.rb +0 -87
  166. data/examples/app/blog/view/comment/form.nag +0 -10
  167. data/examples/app/blog/view/comment/show.nag +0 -16
  168. data/examples/app/blog/view/entry/edit.nag +0 -14
  169. data/examples/app/blog/view/entry/feed.atom.nag +0 -8
  170. data/examples/app/blog/view/entry/feed.rss.nag +0 -7
  171. data/examples/app/blog/view/entry/index.nag +0 -7
  172. data/examples/app/blog/view/entry/new.nag +0 -13
  173. data/examples/app/blog/view/entry/show.nag +0 -36
  174. data/examples/app/blog/view/feed.atom.nag +0 -18
  175. data/examples/app/blog/view/feed.rss.nag +0 -25
  176. data/examples/app/blog/view/index.nag +0 -6
  177. data/examples/app/blog/view/tag/index.nag +0 -5
  178. data/lib/proto/public/ramaze.png +0 -0
  179. data/lib/ramaze/rest.rb +0 -36
  180. data/spec/ramaze/rest.rb +0 -28
  181. data/tasks/rcov.rake +0 -22
@@ -17,29 +17,29 @@ module Ramaze
17
17
  # However, there's no need to panic as it's very easy to setup a basic anti
18
18
  # CSRF system.
19
19
  #
20
- # == Usage
20
+ # ## Usage
21
21
  #
22
22
  # In order to enable CSRF protection we need to do two things. Load the
23
23
  # helper and create a before_all block in a controller. Take a look at the
24
24
  # following code:
25
25
  #
26
- # class BaseController < Ramaze::Controller
27
- # before_all do
28
- # puts "Hello, before_all!"
29
- # end
30
- # end
26
+ # class BaseController < Ramaze::Controller
27
+ # before_all do
28
+ # puts "Hello, before_all!"
29
+ # end
30
+ # end
31
31
  #
32
32
  # This would output "Hello, before_all!" to the console upon each request.
33
33
  # Not very useful but it does show what the before_all block can do. On to
34
34
  # actual CSRF related code!
35
35
  #
36
- # class BaseController < Ramaze::Controller
37
- # before_all do
38
- # csrf_protection :save do
39
- # # ....
40
- # end
41
- # end
42
- # end
36
+ # class BaseController < Ramaze::Controller
37
+ # before_all do
38
+ # csrf_protection :save do
39
+ # # ....
40
+ # end
41
+ # end
42
+ # end
43
43
  #
44
44
  # This example introduces an extra block that validates the current
45
45
  # request. Whenever a user requests a controller that either extends
@@ -47,13 +47,13 @@ module Ramaze
47
47
  # current request data contains a CSRF token. Of course an if/end isn't
48
48
  # very useful if it doesn't do anything, let's add some code.
49
49
  #
50
- # class BaseController < Ramaze::Controller
51
- # before_all do
52
- # csrf_protection :save do
53
- # puts "Hello, unsafe data!"
54
- # end
55
- # end
56
- # end
50
+ # class BaseController < Ramaze::Controller
51
+ # before_all do
52
+ # csrf_protection :save do
53
+ # puts "Hello, unsafe data!"
54
+ # end
55
+ # end
56
+ # end
57
57
  #
58
58
  # The code above checks if the current method is "save" (or any other of
59
59
  # the provided methods) and checks if an CSRF token is supplied if the
@@ -67,18 +67,17 @@ module Ramaze
67
67
  # If you're a lazy person you can copy-paste the example below and adapt it
68
68
  # to your needs.
69
69
  #
70
- # class BaseController < Ramaze::Controller
71
- # before_all do
72
- # csrf_protection :save do
73
- # respond("The supplied CSRF token is invalid.", 401)
74
- # end
75
- # end
76
- # end
70
+ # class BaseController < Ramaze::Controller
71
+ # before_all do
72
+ # csrf_protection :save do
73
+ # respond("The supplied CSRF token is invalid.", 401)
74
+ # end
75
+ # end
76
+ # end
77
77
  #
78
78
  # @author Yorick Peterse
79
79
  #
80
80
  module CSRF
81
-
82
81
  ##
83
82
  # Method that can be used to protect the specified methods against CSRF
84
83
  # exploits. Each protected method will require the token to be stored in
@@ -86,10 +85,10 @@ module Ramaze
86
85
  # against the current token in the session.
87
86
  #
88
87
  # @author Yorick Peterse
89
- # @param [Strings/Symbol] *methods Methods that will be protected/unprotected.
88
+ # @param [Strings/Symbol] *methods Methods that will be
89
+ # protected/unprotected.
90
90
  # @param [Block] Block that will be executed if the token is invalid.
91
91
  # @example
92
- #
93
92
  # # Protect "create" and "save" against CSRF exploits
94
93
  # before_all do
95
94
  # csrf_protection :create, :save do
@@ -97,7 +96,7 @@ module Ramaze
97
96
  # end
98
97
  # end
99
98
  #
100
- def csrf_protection *methods, &block
99
+ def csrf_protection(*methods, &block)
101
100
  # Only protect the specified methods
102
101
  if methods.include?(action.name) or methods.include?(action.name.to_sym)
103
102
  # THINK: For now the field name is hard-coded to "csrf_token". While
@@ -120,9 +119,8 @@ module Ramaze
120
119
  #
121
120
  # @author Yorick Peterse
122
121
  # @param [Hash] Additional arguments that can be set such as the TTL.
123
- # @return [Void]
124
122
  #
125
- def generate_csrf_token args = {}
123
+ def generate_csrf_token(args = {})
126
124
  # Default TTL is 15 minutes
127
125
  ttl = args[:ttl] || (15 * 60)
128
126
 
@@ -154,7 +152,6 @@ module Ramaze
154
152
  # @author Yorick Peterse
155
153
  # @return [String] The current CSRF token.
156
154
  # @example
157
- #
158
155
  # form(@data, :method => :post) do |f|
159
156
  # f.input_hidden :csrf_token, get_csrf_token()
160
157
  # end
@@ -180,9 +177,8 @@ module Ramaze
180
177
  #
181
178
  # @author Yorick Peterse
182
179
  # @param [String] input_token The CSRF token to validate.
183
- # @return [Bool]
180
+ # @return [TrueClass|FalseClass]
184
181
  # @example
185
- #
186
182
  # before_all do
187
183
  # if validate_csrf_token(request.params['csrf_token']) != true
188
184
  # respond("Invalid CSRF token", 401)
@@ -205,6 +201,6 @@ module Ramaze
205
201
  _csrf[:ip] == request.env['REMOTE_ADDR'] &&
206
202
  _csrf[:agent] == request.env['HTTP_USER_AGENT']
207
203
  end
208
- end
209
- end
210
- end
204
+ end # CSRF
205
+ end # Helper
206
+ end # Ramaze
@@ -3,7 +3,7 @@ require 'disqus/view_helpers'
3
3
 
4
4
  module Ramaze
5
5
  module Helper
6
-
6
+ ##
7
7
  # Provides shortcuts via Disqus::ViewHelpers.
8
8
  #
9
9
  # Make sure that you set your disqus credentials when using this helper:
@@ -19,8 +19,9 @@ module Ramaze
19
19
  # disqus_recent_comments
20
20
  # disqus_thread
21
21
  # disqus_top_commenters
22
+ #
22
23
  module Disqus
23
24
  include ::Disqus::ViewHelpers
24
- end
25
- end
26
- end
25
+ end # Disqus
26
+ end # Helper
27
+ end # Ramaze
@@ -6,35 +6,37 @@ module Ramaze
6
6
  # The Email helper can be used as a simple way of sending Emails from your
7
7
  # application. In order to use this helper you first need to load it:
8
8
  #
9
- # class Comments < Ramaze::Controller
10
- # helper :email
11
- # end
9
+ # class Comments < Ramaze::Controller
10
+ # helper :email
11
+ # end
12
12
  #
13
13
  # Sending an Email can be done by calling the method send_email():
14
14
  #
15
- # send_email('info@yorickpeterse.com', 'Hello, world!', 'Hello, this is an Email')
15
+ # send_email(
16
+ # 'user@domain.tld',
17
+ # 'Hello, world!',
18
+ # 'Hello, this is an Email'
19
+ # )
16
20
  #
17
- # Ramaze will log any errors in case the Email could not be sent so you don't have to
18
- # worry about this.
21
+ # Ramaze will log any errors in case the Email could not be sent so you
22
+ # don't have to worry about this.
19
23
  #
20
- # == Options
24
+ # ## Options
21
25
  #
22
- # This module can be configured using Innate::Optioned. Say you want to change the
23
- # SMTP host you simply need to do the following:
26
+ # This module can be configured using Innate::Optioned. Say you want to
27
+ # change the SMTP host you simply need to do the following:
24
28
  #
25
- # Ramaze::Helper::Email.options.host = 'mail.google.com'
29
+ # Ramaze::Helper::Email.options.host = 'mail.google.com'
26
30
  #
27
- # Various other options are available, for a full list of these options run the
28
- # following in an IRB session:
31
+ # Various other options are available, for a full list of these options run
32
+ # the following in an IRB session:
29
33
  #
30
- # puts Ramaze::Helper::Email.options
34
+ # puts Ramaze::Helper::Email.options
31
35
  #
32
- # By default this helper uses \r\n for newlines, this can be changed as following:
36
+ # By default this helper uses ``\r\n`` for newlines, this can be changed as
37
+ # following:
33
38
  #
34
- # Ramaze::Helper::Email.options.newline = "\n"
35
- #
36
- # It's important that this setting matches the settings of your SMTP server as
37
- # otherwise you (usually) won't be able to send any Emails.
39
+ # Ramaze::Helper::Email.options.newline = "\n"
38
40
  #
39
41
  # @author Yorick Peterse
40
42
  # @author Michael Fellinger
@@ -59,12 +61,12 @@ module Ramaze
59
61
  "<" + Time.now.to_i.to_s + "@" + Ramaze::Helper::Email.options.helo_domain + ">"
60
62
  }
61
63
  end
62
-
64
+
63
65
  ##
64
66
  # Sends an Email over SMTP.
65
67
  #
66
68
  # @example
67
- # send_email('info@yorickpeterse.com', 'Hello, world!', 'Hello, this is an Email')
69
+ # send_email('user@domain.tld', 'Hello, world!', 'Hello, this is an Email')
68
70
  #
69
71
  # @author Yorick Peterse
70
72
  # @author Michael Fellinger
@@ -79,7 +81,7 @@ module Ramaze
79
81
  id = Email.options.generator.call
80
82
 
81
83
  # Generate the body of the Email
82
- email = [
84
+ email = [
83
85
  "From: #{sender}", "To: <#{recipient}>", "Date: #{Time.now.rfc2822}",
84
86
  "Subject: #{subject}", "Message-Id: #{id}", '', message
85
87
  ].join(Email.options.newline)
@@ -93,11 +95,20 @@ module Ramaze
93
95
 
94
96
  begin
95
97
  Net::SMTP.start(*email_options) do |smtp|
96
- smtp.send_message(email, Email.options.sender, [recipient, *Email.options.bcc])
97
- Ramaze::Log.info("Email sent to #{recipient} with subject \"#{subject}\"")
98
+ smtp.send_message(
99
+ email,
100
+ Email.options.sender,
101
+ [recipient, *Email.options.bcc]
102
+ )
103
+
104
+ Ramaze::Log.info(
105
+ "Email sent to #{recipient} with subject \"#{subject}\""
106
+ )
98
107
  end
99
108
  rescue => e
100
- Ramaze::Log.error("Failed to send an Email to #{recipient}: #{e.inspect}")
109
+ Ramaze::Log.error(
110
+ "Failed to send an Email to #{recipient}: #{e.inspect}"
111
+ )
101
112
  end
102
113
  end
103
114
  end # Email
@@ -8,7 +8,7 @@ module Ramaze
8
8
  ##
9
9
  # Allows you to use some shortcuts for Erector in your Controller.
10
10
  #
11
- # use this inside your controller to directly build Erector
11
+ # use this inside your controller to directly build Erector
12
12
  # Refer to the Erector-documentation and testsuite for more examples.
13
13
  #
14
14
  # @example
@@ -26,19 +26,18 @@ module Ramaze
26
26
  # Method that generates a XHTML 1.0 Strict doctype.
27
27
  #
28
28
  # @example
29
- #
30
29
  # strict_html do
31
30
  # head do
32
31
  # title "Ramaze Rocks!"
33
32
  # end
34
33
  # body
35
34
  # div do
36
- #
35
+ #
37
36
  # end
38
37
  # end
39
38
  # end
40
39
  #
41
- # @param [Hash] args Hash containing extra options such as the xml:lang
40
+ # @param [Hash] args Hash containing extra options such as the xml:lang
42
41
  # and xmlns attribute.
43
42
  # @param [Block] block Block that contains the inner data of the <html>
44
43
  # element.
@@ -53,7 +52,6 @@ module Ramaze
53
52
  # Generate a Javascript tag.
54
53
  #
55
54
  # @example
56
- #
57
55
  # js 'javascript/jquery.js'
58
56
  #
59
57
  # @param [String] src The full or relative path to the Javascript file.
@@ -66,13 +64,12 @@ module Ramaze
66
64
  # Generate a pair of conditional tags for a specific browser.
67
65
  #
68
66
  # @example
69
- #
70
67
  # ie_if 'IE' do
71
68
  # ......
72
69
  # end
73
70
  #
74
71
  # @param [String] expr The if expression, such as 'IE' or 'lte IE7'.
75
- # @param [block] block Block that contains the data that needs to be
72
+ # @param [block] block Block that contains the data that needs to be
76
73
  # loaded for the specified browser.
77
74
  #
78
75
  def ie_if(expr, &block)
@@ -94,19 +91,18 @@ module Ramaze
94
91
  # Generate a stylesheet tag.
95
92
  #
96
93
  # @example
97
- #
98
94
  # css 'css/reset.css', :media => 'print'
99
95
  #
100
- # @param [String] href The path (either absolute or relative) to the CSS
96
+ # @param [String] href The path (either absolute or relative) to the CSS
101
97
  # file.
102
- # @param [Hash] args A hash containing additional arguments to add to
98
+ # @param [Hash] args A hash containing additional arguments to add to
103
99
  # the CSS tag.
104
100
  #
105
101
  def css(href, args = {})
106
102
  attrs = {
107
- :rel => "stylesheet",
108
- :href => href,
109
- :type => "text/css"
103
+ :rel => "stylesheet",
104
+ :href => href,
105
+ :type => "text/css"
110
106
  }.merge(args)
111
107
 
112
108
  link attrs
@@ -9,16 +9,14 @@ module Ramaze
9
9
  # Flash is a way to keep a temporary pairs of keys and values for the duration
10
10
  # of two requests, the current and following.
11
11
  #
12
- # Very vague Example:
12
+ # Time for an example. On the first request, for example on registering:
13
13
  #
14
- # On the first request, for example on registering:
15
- #
16
- # flash[:error] = "You should reconsider your username, it's taken already"
17
- # redirect r(:register)
14
+ # flash[:error] = "You should reconsider your username, it's taken already"
15
+ # redirect r(:register)
18
16
  #
19
17
  # This is the request from the redirect:
20
18
  #
21
- # do_stuff if flash[:error]
19
+ # do_stuff if flash[:error]
22
20
  #
23
21
  # On the request after this, flash[:error] is gone.
24
22
 
@@ -59,6 +57,6 @@ module Ramaze
59
57
  end
60
58
  }.flatten.join("\n")
61
59
  end
62
- end
63
- end
64
- end
60
+ end # Flash
61
+ end # Helper
62
+ end # Ramaze
@@ -2,191 +2,206 @@
2
2
  # All files in this distribution are subject to the terms of the Ruby license.
3
3
 
4
4
  module Ramaze
5
- module Helper::Formatting
6
- module_function
7
-
8
- FORMATTING_NUMBER_COUNTER = { 0 => 'no', 2 => 'two', 3 => 'three',
9
- 4 => 'four', 5 => 'five', 6 => 'six', 7 => 'seven', 8 => 'eight',
10
- 9 => 'nine', 10 => 'ten' }
11
-
12
- # Answers with a representation of given +count+ with correct grammar.
13
- # If no +items+ argument is given, and the +count+ argument is not 1, then
14
- # we first check whether the +item+ argument responds to #pluralize (for
15
- # example if you are using Sequel). If this doesn't work we append 's' to
16
- # the +item+ argument.
17
- #
18
- # @example usage
19
- # number_counter(0, 'comment') # => 'no comments'
20
- # number_counter(1, 'comment') # => 'one comment'
21
- # number_counter(2, 'comment') # => '2 comments'
22
-
23
- def number_counter(count, item, items = nil)
24
- count, item = count.to_i, item.to_s
25
-
26
- if count == 1
27
- "one #{item}"
28
- else
29
- items ||= item.respond_to?(:pluralize) ? item.pluralize : "#{item}s"
30
- prefix = FORMATTING_NUMBER_COUNTER[count] || count
31
- "#{prefix} #{items}"
32
- end
33
- end
34
-
35
- # Format a floating number nicely for display.
36
- #
37
- # Usage:
38
- # number_format(123.123) # => '123.123'
39
- # number_format(123456.12345) # => '123,456.12345'
40
- # number_format(123456.12345, '.') # => '123.456,12345'
41
-
42
- def number_format(n, delimiter = ',')
43
- delim_l, delim_r = delimiter == ',' ? %w[, .] : %w[. ,]
44
- h, r = n.to_s.split('.')
45
- [h.reverse.scan(/\d{1,3}/).join(delim_l).reverse, r].compact.join(delim_r)
46
- end
47
-
48
- # Answer with the ordinal version of a number.
49
- #
50
- # Usage:
51
- # ordinal(1) # => "1st"
52
- # ordinal(2) # => "2nd"
53
- # ordinal(3) # => "3rd"
54
- # ordinal(13) # => "13th"
55
- # ordinal(33) # => "33rd"
56
- # ordinal(100) # => "100th"
57
- # ordinal(133) # => "133rd"
58
-
59
- def ordinal(number)
60
- number = number.to_i
61
-
62
- case number % 100
63
- when 11..13; "#{number}th"
64
- else
65
- case number % 10
66
- when 1; "#{number}st"
67
- when 2; "#{number}nd"
68
- when 3; "#{number}rd"
69
- else "#{number}th"
5
+ module Helper
6
+ module Formatting
7
+ module_function
8
+
9
+ FORMATTING_NUMBER_COUNTER = {
10
+ 0 => 'no',
11
+ 2 => 'two',
12
+ 3 => 'three',
13
+ 4 => 'four',
14
+ 5 => 'five',
15
+ 6 => 'six',
16
+ 7 => 'seven',
17
+ 8 => 'eight',
18
+ 9 => 'nine',
19
+ 10 => 'ten'
20
+ }
21
+
22
+ # Answers with a representation of given +count+ with correct grammar. If
23
+ # no +items+ argument is given, and the +count+ argument is not 1, then we
24
+ # first check whether the +item+ argument responds to ``#pluralize`` (for
25
+ # example if you are using Sequel). If this doesn't work we append 's'
26
+ # to the +item+ argument.
27
+ #
28
+ # @example usage
29
+ # number_counter(0, 'comment') # => 'no comments'
30
+ # number_counter(1, 'comment') # => 'one comment'
31
+ # number_counter(2, 'comment') # => '2 comments'
32
+ #
33
+ def number_counter(count, item, items = nil)
34
+ count, item = count.to_i, item.to_s
35
+
36
+ if count == 1
37
+ "one #{item}"
38
+ else
39
+ items ||= item.respond_to?(:pluralize) ? item.pluralize : "#{item}s"
40
+ prefix = FORMATTING_NUMBER_COUNTER[count] || count
41
+ "#{prefix} #{items}"
70
42
  end
71
43
  end
72
- end
73
-
74
- # stolen and adapted from rails
75
- def time_diff(from_time, to_time = Time.now, include_seconds = false)
76
- distance_in_minutes = (((to_time - from_time).abs)/60).round
77
- distance_in_seconds = ((to_time - from_time).abs).round if include_seconds
78
-
79
- case distance_in_minutes
80
- when 0..1
81
- return (distance_in_minutes == 0) ? 'less than a minute' : '1 minute' unless include_seconds
82
- case distance_in_seconds
83
- when 0..4 then 'less than 5 seconds'
84
- when 5..9 then 'less than 10 seconds'
85
- when 10..19 then 'less than 20 seconds'
86
- when 20..39 then 'half a minute'
87
- when 40..59 then 'less than a minute'
88
- else '1 minute'
89
- end
90
44
 
91
- when 2..44 then "#{distance_in_minutes} minutes"
92
- when 45..89 then 'about 1 hour'
93
- when 90..1439 then "about #{(distance_in_minutes.to_f / 60.0).round} hours"
94
- when 1440..2879 then '1 day'
95
- when 2880..43199 then "#{(distance_in_minutes / 1440).round} days"
96
- when 43200..86399 then 'about 1 month'
97
- when 86400..525959 then "#{(distance_in_minutes / 43200).round} months"
98
- when 525960..1051919 then 'about 1 year'
99
- else "over #{(distance_in_minutes / 525960).round} years"
45
+ # Format a floating number nicely for display.
46
+ #
47
+ # @example
48
+ # number_format(123.123) # => '123.123'
49
+ # number_format(123456.12345) # => '123,456.12345'
50
+ # number_format(123456.12345, '.') # => '123.456,12345'
51
+ #
52
+ def number_format(n, delimiter = ',')
53
+ delim_l, delim_r = delimiter == ',' ? %w[, .] : %w[. ,]
54
+ h, r = n.to_s.split('.')
55
+ [h.reverse.scan(/\d{1,3}/).join(delim_l).reverse, r].compact.join(delim_r)
100
56
  end
101
- end
102
-
103
- # Copied from actionpack, and revised by insane-dreamer to fix a bug (original fails on some URLs)
104
- AUTO_LINK_RE = %r{
105
- ( # leading text
106
- <\w+.*?>| # leading HTML tag, or
107
- [^=!:'"/]| # leading punctuation, or
108
- ^ # beginning of line
109
- )
110
- (
111
- (?:https?://)| # protocol spec, or
112
- (?:www\.) # www.*
113
- )
114
- (
115
- [-\w]+ # subdomain or domain
116
- (?:\.[-\w]+)* # remaining subdomains or domain
117
- (?::\d+)? # port
118
- (?:/(?:[~\w\+@%=\(\)-]|(?:[,.;:'][^\s<$]))*)* # path
119
- (?:\?[\w\+@%&=.;:-]+)? # query string
120
- (?:\#[\w\-]*)? # trailing anchor
121
- )
122
- ([[:punct:]]|<|$|) # trailing text
123
- }x unless defined? AUTO_LINK_RE
124
-
125
- # Turns all urls into clickable links. If a block is given, each url
126
- # is yielded and the result is used as the link text.
127
- def auto_link(text, opts = {})
128
- html_options = ' ' + opts.map{|k,v| "#{k}='#{v}'"}.join(' ') if opts.any?
129
- text.gsub(AUTO_LINK_RE) do
130
- all, a, b, c, d = $&, $1, $2, $3, $4
131
- if a =~ /<a\s/i # don't replace URL's that are already linked
132
- all
57
+
58
+ # Answer with the ordinal version of a number.
59
+ #
60
+ # @example
61
+ # ordinal(1) # => "1st"
62
+ # ordinal(2) # => "2nd"
63
+ # ordinal(3) # => "3rd"
64
+ # ordinal(13) # => "13th"
65
+ # ordinal(33) # => "33rd"
66
+ # ordinal(100) # => "100th"
67
+ # ordinal(133) # => "133rd"
68
+ #
69
+ def ordinal(number)
70
+ number = number.to_i
71
+
72
+ case number % 100
73
+ when 11..13; "#{number}th"
133
74
  else
134
- text = b + c
135
- text = yield(text) if block_given?
136
- %(#{a}<a href="#{b=="www."?"http://www.":b}#{c}"#{html_options}>#{text}</a>#{d})
75
+ case number % 10
76
+ when 1; "#{number}st"
77
+ when 2; "#{number}nd"
78
+ when 3; "#{number}rd"
79
+ else "#{number}th"
80
+ end
81
+ end
82
+ end
83
+
84
+ # stolen and adapted from rails
85
+ def time_diff(from_time, to_time = Time.now, include_seconds = false)
86
+ distance_in_minutes = (((to_time - from_time).abs)/60).round
87
+ distance_in_seconds = ((to_time - from_time).abs).round if include_seconds
88
+
89
+ case distance_in_minutes
90
+ when 0..1
91
+ return (distance_in_minutes == 0) ? 'less than a minute' : '1 minute' unless include_seconds
92
+ case distance_in_seconds
93
+ when 0..4 then 'less than 5 seconds'
94
+ when 5..9 then 'less than 10 seconds'
95
+ when 10..19 then 'less than 20 seconds'
96
+ when 20..39 then 'half a minute'
97
+ when 40..59 then 'less than a minute'
98
+ else '1 minute'
99
+ end
100
+
101
+ when 2..44 then "#{distance_in_minutes} minutes"
102
+ when 45..89 then 'about 1 hour'
103
+ when 90..1439 then "about #{(distance_in_minutes.to_f / 60.0).round} hours"
104
+ when 1440..2879 then '1 day'
105
+ when 2880..43199 then "#{(distance_in_minutes / 1440).round} days"
106
+ when 43200..86399 then 'about 1 month'
107
+ when 86400..525959 then "#{(distance_in_minutes / 43200).round} months"
108
+ when 525960..1051919 then 'about 1 year'
109
+ else "over #{(distance_in_minutes / 525960).round} years"
110
+ end
111
+ end
112
+
113
+ # Copied from actionpack, and revised by insane-dreamer to fix a bug
114
+ # (original fails on some URLs)
115
+ AUTO_LINK_RE = %r{
116
+ ( # leading text
117
+ <\w+.*?>| # leading HTML tag, or
118
+ [^=!:'"/]| # leading punctuation, or
119
+ ^ # beginning of line
120
+ )
121
+ (
122
+ (?:https?://)| # protocol spec, or
123
+ (?:www\.) # www.*
124
+ )
125
+ (
126
+ [-\w]+ # subdomain or domain
127
+ (?:\.[-\w]+)* # remaining subdomains or domain
128
+ (?::\d+)? # port
129
+ (?:/(?:[~\w\+@%=\(\)-]|(?:[,.;:'][^\s<$]))*)* # path
130
+ (?:\?[\w\+@%&=.;:-]+)? # query string
131
+ (?:\#[\w\-]*)? # trailing anchor
132
+ )
133
+ ([[:punct:]]|<|$|) # trailing text
134
+ }x unless defined? AUTO_LINK_RE
135
+
136
+ # Turns all urls into clickable links. If a block is given, each url
137
+ # is yielded and the result is used as the link text.
138
+ def auto_link(text, opts = {})
139
+ html_options = ' ' + opts.map{|k,v| "#{k}='#{v}'"}.join(' ') if opts.any?
140
+ text.gsub(AUTO_LINK_RE) do
141
+ all, a, b, c, d = $&, $1, $2, $3, $4
142
+ if a =~ /<a\s/i # don't replace URL's that are already linked
143
+ all
144
+ else
145
+ text = b + c
146
+ text = yield(text) if block_given?
147
+ %(#{a}<a href="#{b=="www."?"http://www.":b}#{c}"#{html_options}>#{text}</a>#{d})
148
+ end
137
149
  end
138
150
  end
139
- end
140
- alias autolink auto_link
141
-
142
- # takes a string and optional argument for outputting compliance HTML
143
- # instead of XHTML.
144
- # e.g nl2br "a\nb\n\c" #=> 'a<br />b<br />c'
145
-
146
- def nl2br(string, xhtml = true)
147
- br = xhtml ? '<br />' : '<br>'
148
- string.gsub(/\n/, br)
149
- end
150
-
151
- # Maybe port to ruby < 1.8.7 ?
152
- def obfuscate_email(email, text = nil)
153
- obfuscated = []
154
- email.to_s.each_byte{|c| obfuscated << "&#%03d" % c }
155
- joined = obfuscated.join
156
-
157
- %(<a href="mailto:#{joined}">#{text || joined}</a>)
158
- end
159
-
160
- # Returns Hash with tags as keys and their weight as value.
161
- #
162
- # Example:
163
- # tags = %w[ruby ruby code ramaze]
164
- # tagcloud(tags)
165
- # # => {"code"=>0.75, "ramaze"=>0.75, "ruby"=>1.0}
166
- #
167
- # The weight can be influenced by adjusting the +min+ and +max+ parameters,
168
- # please make sure that +max+ is larger than +min+ to get meaningful output.
169
- #
170
- # This is not thought as immediate output to your template but rather to
171
- # help either implementing your own algorithm or using the result as input
172
- # for your tagcloud.
173
- #
174
- # Example:
175
- # - tagcloud(tags).each do |tag, weight|
176
- # - style = "font-size: %0.2fem" % weight
177
- # %a{:style => style, :href => Rs(tag)}= h(tag)
178
-
179
- def tagcloud(tags, min = 0.5, max = 1.5)
180
- result = {}
181
- total = tags.size.to_f
182
- diff = max - min
183
-
184
- tags.uniq.each do |tag|
185
- count = tags.respond_to?(:count) ? tags.count(tag) : tags.select{|t| t==tag }.size
186
- result[tag] = ((count / total) * diff) + min
151
+ alias autolink auto_link
152
+
153
+ # takes a string and optional argument for outputting compliance HTML
154
+ # instead of XHTML.
155
+ #
156
+ # @example
157
+ # nl2br "a\nb\n\c" #=> 'a<br />b<br />c'
158
+ #
159
+ def nl2br(string, xhtml = true)
160
+ br = xhtml ? '<br />' : '<br>'
161
+ string.gsub(/\n/, br)
187
162
  end
188
163
 
189
- result
190
- end
191
- end
192
- end
164
+ def obfuscate_email(email, text = nil)
165
+ obfuscated = []
166
+ email.to_s.each_byte{|c| obfuscated << "&#%03d" % c }
167
+ joined = obfuscated.join
168
+
169
+ %(<a href="mailto:#{joined}">#{text || joined}</a>)
170
+ end
171
+
172
+ # Returns Hash with tags as keys and their weight as value.
173
+ #
174
+ # Example:
175
+ # tags = %w[ruby ruby code ramaze]
176
+ # tagcloud(tags)
177
+ # # => {"code"=>0.75, "ramaze"=>0.75, "ruby"=>1.0}
178
+ #
179
+ # The weight can be influenced by adjusting the +min+ and +max+
180
+ # parameters, please make sure that +max+ is larger than +min+ to get
181
+ # meaningful output.
182
+ #
183
+ # This is not thought as immediate output to your template but rather to
184
+ # help either implementing your own algorithm or using the result as input
185
+ # for your tagcloud.
186
+ #
187
+ # @example
188
+ # tagcloud(tags).each do |tag, weight|
189
+ # style = "font-size: %0.2fem" % weight
190
+ # %a{:style => style, :href => Rs(tag)}= h(tag)
191
+ # end
192
+ #
193
+ def tagcloud(tags, min = 0.5, max = 1.5)
194
+ result = {}
195
+ total = tags.size.to_f
196
+ diff = max - min
197
+
198
+ tags.uniq.each do |tag|
199
+ count = tags.respond_to?(:count) ? tags.count(tag) : tags.select{|t| t==tag }.size
200
+ result[tag] = ((count / total) * diff) + min
201
+ end
202
+
203
+ result
204
+ end
205
+ end # Formatting
206
+ end # Helper
207
+ end # Ramaze