roda 2.28.0 → 2.29.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG +46 -0
  3. data/README.rdoc +25 -7
  4. data/doc/release_notes/2.29.0.txt +156 -0
  5. data/lib/roda.rb +25 -3
  6. data/lib/roda/plugins/_erubis_escaping.rb +2 -0
  7. data/lib/roda/plugins/_symbol_regexp_matchers.rb +22 -0
  8. data/lib/roda/plugins/assets.rb +3 -2
  9. data/lib/roda/plugins/branch_locals.rb +74 -0
  10. data/lib/roda/plugins/caching.rb +15 -7
  11. data/lib/roda/plugins/chunked.rb +10 -7
  12. data/lib/roda/plugins/content_for.rb +4 -1
  13. data/lib/roda/plugins/drop_body.rb +3 -2
  14. data/lib/roda/plugins/error_email.rb +3 -2
  15. data/lib/roda/plugins/error_mail.rb +3 -2
  16. data/lib/roda/plugins/head.rb +2 -1
  17. data/lib/roda/plugins/header_matchers.rb +3 -0
  18. data/lib/roda/plugins/heartbeat.rb +3 -2
  19. data/lib/roda/plugins/json.rb +5 -3
  20. data/lib/roda/plugins/json_parser.rb +3 -2
  21. data/lib/roda/plugins/mailer.rb +3 -3
  22. data/lib/roda/plugins/match_affix.rb +6 -0
  23. data/lib/roda/plugins/multi_route.rb +3 -1
  24. data/lib/roda/plugins/padrino_render.rb +3 -2
  25. data/lib/roda/plugins/params_capturing.rb +3 -3
  26. data/lib/roda/plugins/partials.rb +3 -3
  27. data/lib/roda/plugins/path.rb +4 -2
  28. data/lib/roda/plugins/path_rewriter.rb +2 -2
  29. data/lib/roda/plugins/per_thread_caching.rb +2 -0
  30. data/lib/roda/plugins/placeholder_string_matchers.rb +42 -0
  31. data/lib/roda/plugins/precompile_templates.rb +3 -2
  32. data/lib/roda/plugins/render.rb +86 -37
  33. data/lib/roda/plugins/render_each.rb +2 -1
  34. data/lib/roda/plugins/render_locals.rb +102 -0
  35. data/lib/roda/plugins/run_append_slash.rb +2 -1
  36. data/lib/roda/plugins/run_handler.rb +2 -1
  37. data/lib/roda/plugins/sinatra_helpers.rb +4 -4
  38. data/lib/roda/plugins/static_path_info.rb +2 -0
  39. data/lib/roda/plugins/static_routing.rb +1 -1
  40. data/lib/roda/plugins/streaming.rb +9 -4
  41. data/lib/roda/plugins/symbol_matchers.rb +23 -20
  42. data/lib/roda/plugins/view_options.rb +63 -28
  43. data/lib/roda/plugins/view_subdirs.rb +1 -0
  44. data/lib/roda/plugins/websockets.rb +2 -0
  45. data/lib/roda/version.rb +1 -1
  46. data/spec/composition_spec.rb +2 -2
  47. data/spec/matchers_spec.rb +6 -5
  48. data/spec/plugin/_erubis_escaping_spec.rb +5 -5
  49. data/spec/plugin/backtracking_array_spec.rb +0 -2
  50. data/spec/plugin/branch_locals_spec.rb +88 -0
  51. data/spec/plugin/content_for_spec.rb +8 -2
  52. data/spec/plugin/halt_spec.rb +8 -0
  53. data/spec/plugin/header_matchers_spec.rb +20 -5
  54. data/spec/plugin/multi_route_spec.rb +1 -1
  55. data/spec/plugin/named_templates_spec.rb +2 -2
  56. data/spec/plugin/params_capturing_spec.rb +1 -1
  57. data/spec/plugin/per_thread_caching_spec.rb +1 -1
  58. data/spec/plugin/placeholder_string_matchers_spec.rb +159 -0
  59. data/spec/plugin/render_locals_spec.rb +114 -0
  60. data/spec/plugin/render_spec.rb +83 -8
  61. data/spec/plugin/streaming_spec.rb +104 -4
  62. data/spec/plugin/symbol_matchers_spec.rb +1 -1
  63. data/spec/plugin/view_options_spec.rb +83 -7
  64. data/spec/plugin/websockets_spec.rb +7 -8
  65. data/spec/spec_helper.rb +22 -2
  66. metadata +11 -2
@@ -70,6 +70,7 @@ class Roda
70
70
  # OTHER DEALINGS IN THE SOFTWARE.
71
71
  module Caching
72
72
  OPTS = {}.freeze
73
+ RodaPlugins.deprecate_constant(self, :OPTS)
73
74
 
74
75
  module RequestMethods
75
76
  LAST_MODIFIED = 'Last-Modified'.freeze
@@ -130,7 +131,7 @@ class Roda
130
131
  #
131
132
  # When the current request includes an If-Match header with a
132
133
  # etag that doesn't match, immediately returns a response with a 412 status.
133
- def etag(value, opts=OPTS)
134
+ def etag(value, opts=RodaPlugins::OPTS)
134
135
  # Before touching this code, please double check RFC 2616 14.24 and 14.26.
135
136
  weak = opts[:weak]
136
137
  new_resource = opts.fetch(:new_resource){post?}
@@ -174,12 +175,19 @@ class Roda
174
175
 
175
176
  module ResponseMethods
176
177
  UNDERSCORE = '_'.freeze
178
+ RodaPlugins.deprecate_constant(self, :UNDERSCORE)
177
179
  DASH = '-'.freeze
180
+ RodaPlugins.deprecate_constant(self, :DASH)
178
181
  COMMA = ', '.freeze
182
+ RodaPlugins.deprecate_constant(self, :COMMA)
179
183
  CACHE_CONTROL = 'Cache-Control'.freeze
184
+ RodaPlugins.deprecate_constant(self, :CACHE_CONTROL)
180
185
  EXPIRES = 'Expires'.freeze
186
+ RodaPlugins.deprecate_constant(self, :EXPIRES)
181
187
  CONTENT_TYPE = 'Content-Type'.freeze
188
+ RodaPlugins.deprecate_constant(self, :CONTENT_TYPE)
182
189
  CONTENT_LENGTH = 'Content-Length'.freeze
190
+ RodaPlugins.deprecate_constant(self, :CONTENT_LENGTH)
183
191
 
184
192
  # Specify response freshness policy for using the Cache-Control header.
185
193
  # Options can can any non-value directives (:public, :private, :no_cache,
@@ -195,20 +203,20 @@ class Roda
195
203
  values = []
196
204
  opts.each do |k, v|
197
205
  next unless v
198
- k = k.to_s.tr(UNDERSCORE, DASH)
206
+ k = k.to_s.tr('_', '-')
199
207
  values << (v == true ? k : "#{k}=#{v}")
200
208
  end
201
209
 
202
- self[CACHE_CONTROL] = values.join(COMMA) unless values.empty?
210
+ self['Cache-Control'] = values.join(', ') unless values.empty?
203
211
  end
204
212
 
205
213
  # Set Cache-Control header with the max_age given. max_age should
206
214
  # be an integer number of seconds that the current request should be
207
215
  # cached for. Also sets the Expires header, useful if you have
208
216
  # HTTP 1.0 clients (Cache-Control is an HTTP 1.1 header).
209
- def expires(max_age, opts=OPTS)
217
+ def expires(max_age, opts=RodaPlugins::OPTS)
210
218
  cache_control(Hash[opts].merge!(:max_age=>max_age))
211
- self[EXPIRES] = (Time.now + max_age).httpdate
219
+ self['Expires'] = (Time.now + max_age).httpdate
212
220
  end
213
221
 
214
222
  # Remove Content-Type and Content-Length for 304 responses.
@@ -216,8 +224,8 @@ class Roda
216
224
  a = super
217
225
  if a[0] == 304
218
226
  h = a[1]
219
- h.delete(CONTENT_TYPE)
220
- h.delete(CONTENT_LENGTH)
227
+ h.delete('Content-Type')
228
+ h.delete('Content-Length')
221
229
  end
222
230
  a
223
231
  end
@@ -146,7 +146,7 @@ class Roda
146
146
  # rotated.
147
147
  module Chunked
148
148
  OPTS = {}.freeze
149
-
149
+ RodaPlugins.deprecate_constant(self, :OPTS)
150
150
  HTTP_VERSION = 'HTTP_VERSION'.freeze
151
151
  RodaPlugins.deprecate_constant(self, :HTTP_VERSION)
152
152
  HTTP11 = "HTTP/1.1".freeze
@@ -157,14 +157,14 @@ class Roda
157
157
  RodaPlugins.deprecate_constant(self, :CHUNKED)
158
158
 
159
159
  # Depend on the render plugin
160
- def self.load_dependencies(app, opts=OPTS)
160
+ def self.load_dependencies(app, opts=RodaPlugins::OPTS)
161
161
  app.plugin :render
162
162
  end
163
163
 
164
164
  # Set plugin specific options. Options:
165
165
  # :chunk_by_default :: chunk all calls to view by default
166
166
  # :headers :: Set default additional headers to use when calling view
167
- def self.configure(app, opts=OPTS)
167
+ def self.configure(app, opts=RodaPlugins::OPTS)
168
168
  app.opts[:chunk_by_default] = opts[:chunk_by_default]
169
169
  if opts[:headers]
170
170
  app.opts[:chunk_headers] = (app.opts[:chunk_headers] || {}).merge(opts[:headers]).freeze
@@ -174,8 +174,11 @@ class Roda
174
174
  # Rack response body instance for chunked responses
175
175
  class Body
176
176
  CHUNK_SIZE = "%x\r\n".freeze
177
+ RodaPlugins.deprecate_constant(self, :CHUNK_SIZE)
177
178
  CRLF = "\r\n".freeze
179
+ RodaPlugins.deprecate_constant(self, :CRLF)
178
180
  FINISH = "0\r\n\r\n".freeze
181
+ RodaPlugins.deprecate_constant(self, :FINISH)
179
182
 
180
183
  # Save the scope of the current request handling.
181
184
  def initialize(scope)
@@ -190,12 +193,12 @@ class Roda
190
193
  def each
191
194
  @scope.each_chunk do |chunk|
192
195
  next if !chunk || chunk.empty?
193
- yield(CHUNK_SIZE % chunk.bytesize)
196
+ yield("%x\r\n" % chunk.bytesize)
194
197
  yield(chunk)
195
- yield(CRLF)
198
+ yield("\r\n")
196
199
  end
197
200
  ensure
198
- yield(FINISH)
201
+ yield("0\r\n\r\n")
199
202
  end
200
203
  end
201
204
 
@@ -218,7 +221,7 @@ class Roda
218
221
 
219
222
  # Render a response to the user in chunks. See Chunked for
220
223
  # an overview. If a block is given, it is passed to #delay.
221
- def chunked(template, opts=OPTS, &block)
224
+ def chunked(template, opts=RodaPlugins::OPTS, &block)
222
225
  unless defined?(@_chunked)
223
226
  @_chunked = env['HTTP_VERSION'] == "HTTP/1.1"
224
227
  end
@@ -44,7 +44,7 @@ class Roda
44
44
  # is called multiple times to set data. Overwrite is default, use
45
45
  # the :append option to append.
46
46
  def self.configure(app, opts = {})
47
- app.opts[:append_content_for] = opts.fetch(:append, false)
47
+ app.opts[:append_content_for] = opts.fetch(:append, nil)
48
48
  end
49
49
 
50
50
  module InstanceMethods
@@ -71,6 +71,9 @@ class Roda
71
71
  if append
72
72
  (@_content_for[key] ||= []) << value
73
73
  else
74
+ if @_content_for[key] && append.nil?
75
+ RodaPlugins.warn "Attempt to set content_for with same key. This currently overwrites the existing content_for for #{key}. In Roda 3, it will start appending to the existing content_for by default. Use the :append => false option to the content_for plugin to keep the existing behavior."
76
+ end
74
77
  @_content_for[key] = value
75
78
  end
76
79
  elsif @_content_for && (value = @_content_for[key])
@@ -11,8 +11,9 @@ class Roda
11
11
  module DropBody
12
12
  module ResponseMethods
13
13
  DROP_BODY_STATUSES = [100, 101, 102, 204, 205, 304].freeze
14
- EMPTY_BODY = [].freeze
15
14
 
15
+ EMPTY_BODY = [].freeze
16
+ RodaPlugins.deprecate_constant(self, :EMPTY_BODY)
16
17
  CONTENT_LENGTH = "Content-Length".freeze
17
18
  RodaPlugins.deprecate_constant(self, :CONTENT_LENGTH)
18
19
  CONTENT_TYPE = "Content-Type".freeze
@@ -24,7 +25,7 @@ class Roda
24
25
  def finish
25
26
  r = super
26
27
  if DROP_BODY_STATUSES.include?(r[0])
27
- r[2] = EMPTY_BODY
28
+ r[2] = EMPTY_ARRAY
28
29
  h = r[1]
29
30
  h.delete("Content-Length")
30
31
  h.delete("Content-Type")
@@ -38,8 +38,9 @@ class Roda
38
38
  # use an error reporting service instead of this plugin.
39
39
  module ErrorEmail
40
40
  OPTS = {}.freeze
41
+ RodaPlugins.deprecate_constant(self, :OPTS)
41
42
  DEFAULTS = {
42
- :headers=>OPTS,
43
+ :headers=>RodaPlugins::OPTS,
43
44
  :host=>'localhost',
44
45
  # :nocov:
45
46
  :emailer=>lambda{|h| Net::SMTP.start(h[:host]){|s| s.send_message(h[:message], h[:from], h[:to])}},
@@ -97,7 +98,7 @@ END
97
98
  }#.freeze # RODA3
98
99
 
99
100
  # Set default opts for plugin. See ErrorEmail module RDoc for options.
100
- def self.configure(app, opts=OPTS)
101
+ def self.configure(app, opts=RodaPlugins::OPTS)
101
102
  email_opts = app.opts[:error_email] ||= DEFAULTS
102
103
  email_opts = email_opts.merge(opts)
103
104
  email_opts[:headers] = email_opts[:headers].dup
@@ -37,10 +37,11 @@ class Roda
37
37
  # use an error reporting service instead of this plugin.
38
38
  module ErrorMail
39
39
  OPTS = {}.freeze
40
+ RodaPlugins.deprecate_constant(self, :OPTS)
40
41
 
41
42
  # Set default opts for plugin. See ErrorEmail module RDoc for options.
42
- def self.configure(app, opts=OPTS)
43
- app.opts[:error_mail] = email_opts = (app.opts[:error_mail] || OPTS).merge(opts).freeze
43
+ def self.configure(app, opts=RodaPlugins::OPTS)
44
+ app.opts[:error_mail] = email_opts = (app.opts[:error_mail] || RodaPlugins::OPTS).merge(opts).freeze
44
45
  unless email_opts[:to] && email_opts[:from]
45
46
  raise RodaError, "must provide :to and :from options to error_mail plugin"
46
47
  end
@@ -37,6 +37,7 @@ class Roda
37
37
  # may prevent search engine's from crawling your website.
38
38
  module Head
39
39
  EMPTY_ARRAY = [].freeze
40
+ RodaPlugins.deprecate_constant(self, :EMPTY_ARRAY)
40
41
 
41
42
  module InstanceMethods
42
43
  # Always use an empty response body for head requests, with a
@@ -44,7 +45,7 @@ class Roda
44
45
  def call(*)
45
46
  res = super
46
47
  if @_request.head?
47
- res[2] = EMPTY_ARRAY
48
+ res[2] = RodaPlugins::EMPTY_ARRAY
48
49
  end
49
50
  res
50
51
  end
@@ -67,6 +67,8 @@ class Roda
67
67
 
68
68
  if roda_class.opts[:header_matcher_prefix]
69
69
  key = "HTTP_#{key}"
70
+ else
71
+ RodaPlugins.warn ":header matcher used without :header_matcher_prefix app option. Currently this looks for the #{key} header, but in Roda 3 it will look for the HTTP_#{key} header. You should set the :header_matcher_prefix app option and update your code if necessary to avoid this deprecation warning."
70
72
  end
71
73
 
72
74
  if v = @env[key]
@@ -82,6 +84,7 @@ class Roda
82
84
  @captures.concat(match.captures)
83
85
  end
84
86
  else
87
+ RodaPlugins.warn ":host matcher used with regexp value without :host_matcher_captures app option, no capturing will be done. Starting in Roda 3, the :host matcher will automatically capture if the value is a Regexp. Set :host_matcher_captures app option to enable capturing." if hostname.is_a?(Regexp)
85
88
  hostname === host
86
89
  end
87
90
  end
@@ -14,14 +14,15 @@ class Roda
14
14
  #
15
15
  # plugin :heartbeat, :path=>'/status'
16
16
  module Heartbeat
17
- OPTS = {}.freeze
18
17
  HEARTBEAT_RESPONSE = [200, {'Content-Type'=>'text/plain'}.freeze, ['OK'.freeze].freeze].freeze
19
18
 
19
+ OPTS = {}.freeze
20
+ RodaPlugins.deprecate_constant(self, :OPTS)
20
21
  PATH_INFO = 'PATH_INFO'.freeze
21
22
  RodaPlugins.deprecate_constant(self, :PATH_INFO)
22
23
 
23
24
  # Set the heartbeat path to the given path.
24
- def self.configure(app, opts=OPTS)
25
+ def self.configure(app, opts=RodaPlugins::OPTS)
25
26
  app.opts[:heartbeat_path] = (opts[:path] || app.opts[:heartbeat_path] || "/heartbeat").dup.freeze
26
27
  end
27
28
 
@@ -53,14 +53,15 @@ class Roda
53
53
  #
54
54
  # plugin :json, :content_type=>'application/xml'
55
55
  module Json
56
- OPTS = {}.freeze
57
56
  DEFAULT_SERIALIZER = :to_json.to_proc
58
57
 
58
+ OPTS = {}.freeze
59
+ RodaPlugins.deprecate_constant(self, :OPTS)
59
60
  DEFAULT_CONTENT_TYPE = 'application/json'.freeze
60
61
  RodaPlugins.deprecate_constant(self, :DEFAULT_CONTENT_TYPE)
61
62
 
62
63
  # Set the classes to automatically convert to JSON, and the serializer to use.
63
- def self.configure(app, opts=OPTS)
64
+ def self.configure(app, opts=RodaPlugins::OPTS)
64
65
  classes = opts[:classes] || [Array, Hash]
65
66
  app.opts[:json_result_classes] ||= []
66
67
  app.opts[:json_result_classes] += classes
@@ -83,6 +84,7 @@ class Roda
83
84
 
84
85
  module RequestMethods
85
86
  CONTENT_TYPE = 'Content-Type'.freeze
87
+ RodaPlugins.deprecate_constant(self, :CONTENT_TYPE)
86
88
 
87
89
  private
88
90
 
@@ -92,7 +94,7 @@ class Roda
92
94
  def block_result_body(result)
93
95
  case result
94
96
  when *roda_class.json_result_classes
95
- response[CONTENT_TYPE] ||= roda_class.opts[:json_result_content_type]
97
+ response['Content-Type'] ||= roda_class.opts[:json_result_content_type]
96
98
  convert_to_json(result)
97
99
  else
98
100
  super
@@ -11,10 +11,11 @@ class Roda
11
11
  # This only parses the request body as JSON if the Content-Type
12
12
  # header for the request includes "json".
13
13
  module JsonParser
14
- OPTS = {}.freeze
15
14
  DEFAULT_ERROR_HANDLER = proc{|r| r.halt [400, {}, []]}
16
15
  DEFAULT_PARSER = JSON.method(:parse)
17
16
 
17
+ OPTS = {}.freeze
18
+ RodaPlugins.deprecate_constant(self, :OPTS)
18
19
  JSON_PARAMS_KEY = "roda.json_params".freeze
19
20
  RodaPlugins.deprecate_constant(self, :JSON_PARAMS_KEY)
20
21
  INPUT_KEY = "rack.input".freeze
@@ -35,7 +36,7 @@ class Roda
35
36
  # :include_request :: If true, the parser will be called with the request
36
37
  # object as the second argument, so the parser needs
37
38
  # to respond to +call(str, request)+.
38
- def self.configure(app, opts=OPTS)
39
+ def self.configure(app, opts=RodaPlugins::OPTS)
39
40
  app.opts[:json_parser_error_handler] = opts[:error_handler] || app.opts[:json_parser_error_handler] || DEFAULT_ERROR_HANDLER
40
41
  app.opts[:json_parser_parser] = opts[:parser] || app.opts[:json_parser_parser] || DEFAULT_PARSER
41
42
  app.opts[:json_parser_include_request] = opts[:include_request] || app.opts[:json_parser_include_request]
@@ -111,7 +111,7 @@ class Roda
111
111
  # available in your email views.
112
112
  module Mailer
113
113
  OPTS = {}.freeze
114
-
114
+ RodaPlugins.deprecate_constant(self, :OPTS)
115
115
  REQUEST_METHOD = "REQUEST_METHOD".freeze
116
116
  RodaPlugins.deprecate_constant(self, :REQUEST_METHOD)
117
117
  PATH_INFO = "PATH_INFO".freeze
@@ -139,8 +139,8 @@ class Roda
139
139
 
140
140
  # Set the options for the mailer. Options:
141
141
  # :content_type :: The default content type for emails (default: text/plain)
142
- def self.configure(app, opts=OPTS)
143
- app.opts[:mailer] = (app.opts[:mailer]||{}).merge(opts).freeze
142
+ def self.configure(app, opts=RodaPlugins::OPTS)
143
+ app.opts[:mailer] = (app.opts[:mailer]||RodaPlugins::OPTS).merge(opts).freeze
144
144
  end
145
145
 
146
146
  module ClassMethods
@@ -25,12 +25,18 @@ class Roda
25
25
  #
26
26
  # will not modify the prefix and will change the suffix so that it consumes a trailing slash
27
27
  # at the end of the path only.
28
+ #
29
+ # This plugin automatically loads the placeholder_string_matchers plugin.
28
30
  module MatchAffix
29
31
  PREFIX = "/".freeze
30
32
  RodaPlugins.deprecate_constant(self, :PREFIX)
31
33
  SUFFIX = "(?=\/|\z)".freeze
32
34
  RodaPlugins.deprecate_constant(self, :SUFFIX)
33
35
 
36
+ def self.load_dependencies(app, _prefix, _suffix)
37
+ app.plugin :placeholder_string_matchers
38
+ end
39
+
34
40
  # Set the default prefix and suffix to use in match patterns, if a non-nil value
35
41
  # is given.
36
42
  def self.configure(app, prefix, suffix=nil)
@@ -150,7 +150,9 @@ class Roda
150
150
 
151
151
  # The names for the currently stored named routes
152
152
  def named_routes(namespace=nil)
153
- routes = opts[:namespaced_routes][namespace]
153
+ unless routes = opts[:namespaced_routes][namespace]
154
+ RodaPlugins.warn "Attempt to access multi_route namespace for which no routes have been defined: #{namespace}"
155
+ end
154
156
  routes ? routes.keys : []
155
157
  end
156
158
 
@@ -23,17 +23,18 @@ class Roda
23
23
  # Note that this plugin loads the :partials plugin.
24
24
  module PadrinoRender
25
25
  OPTS = {}.freeze
26
+ RodaPlugins.deprecate_constant(self, :OPTS)
26
27
 
27
28
  # Depend on the render plugin, since this overrides
28
29
  # some of its methods.
29
- def self.load_dependencies(app, opts=OPTS)
30
+ def self.load_dependencies(app, opts=RodaPlugins::OPTS)
30
31
  app.plugin :partials, opts
31
32
  end
32
33
 
33
34
  module InstanceMethods
34
35
  # Call view with the given arguments, so that render
35
36
  # uses a layout by default.
36
- def render(template, opts=OPTS)
37
+ def render(template, opts=RodaPlugins::OPTS)
37
38
  view(template, opts)
38
39
  end
39
40
  end
@@ -52,8 +52,8 @@ class Roda
52
52
  # strings and not symbols (<tt>r[]</tt> converts the argument
53
53
  # to a string before looking it up in +r.params+).
54
54
  #
55
- # This plugin will also handle string matchers if placeholders in
56
- # string matchers are supported.
55
+ # This plugin will also handle string matchers with placeholders if
56
+ # the placeholder_string_matchers plugin is loaded before this plugin.
57
57
  #
58
58
  # Also note that this plugin will not work correctly if you are using
59
59
  # the symbol_matchers plugin with custom symbol matching and are using
@@ -82,7 +82,7 @@ class Roda
82
82
  end
83
83
  else
84
84
  # :nocov:
85
-
85
+ # RODA3: Remove
86
86
  # Ruby 1.8 doesn't support positive lookbehind, so include the
87
87
  # colon in the scan, and strip it out later.
88
88
  STRING_PARAM_CAPTURE_RANGE = 1..-1
@@ -21,13 +21,13 @@ class Roda
21
21
  # Note that this plugin automatically loads the :render plugin.
22
22
  module Partials
23
23
  OPTS = {}.freeze
24
-
24
+ RodaPlugins.deprecate_constant(self, :OPTS)
25
25
  SLASH = '/'.freeze
26
26
  RodaPlugins.deprecate_constant(self, :SLASH)
27
27
 
28
28
  # Depend on the render plugin, since this overrides
29
29
  # some of its methods.
30
- def self.load_dependencies(app, opts=OPTS)
30
+ def self.load_dependencies(app, opts=RodaPlugins::OPTS)
31
31
  app.plugin :render, opts
32
32
  end
33
33
 
@@ -35,7 +35,7 @@ class Roda
35
35
  # Renders the given template without a layout, but
36
36
  # prefixes the template filename to use with an
37
37
  # underscore.
38
- def partial(template, opts=OPTS)
38
+ def partial(template, opts=RodaPlugins::OPTS)
39
39
  opts = parse_template_opts(template, opts)
40
40
  if opts[:template]
41
41
  template = opts[:template].split('/')
@@ -62,12 +62,14 @@ class Roda
62
62
  # a block to a block that is instance_execed.
63
63
  module Path
64
64
  DEFAULT_PORTS = {'http' => 80, 'https' => 443}.freeze
65
+
65
66
  OPTS = {}.freeze
67
+ RodaPlugins.deprecate_constant(self, :OPTS)
66
68
 
67
69
  # Initialize the path classes when loading the plugin. Options:
68
70
  # :by_name :: Register classes by name, which is friendlier when reloading code (defaults to
69
71
  # true in development mode)
70
- def self.configure(app, opts=OPTS)
72
+ def self.configure(app, opts=RodaPlugins::OPTS)
71
73
  app.instance_eval do
72
74
  self.opts[:path_class_by_name] = opts.fetch(:by_name, ENV['RACK_ENV'] == 'development')
73
75
  self.opts[:path_classes] ||= {}
@@ -90,7 +92,7 @@ class Roda
90
92
  end
91
93
 
92
94
  # Create a new instance method for the named path. See plugin module documentation for options.
93
- def path(name, path=nil, opts=OPTS, &block)
95
+ def path(name, path=nil, opts=RodaPlugins::OPTS, &block)
94
96
  if name.is_a?(Class)
95
97
  raise RodaError, "can't provide path or options when calling path with a class" unless path.nil? && opts.empty?
96
98
  raise RodaError, "must provide a block when calling path with a class" unless block