roda 3.108.0 → 3.109.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.
- checksums.yaml +4 -4
- data/lib/roda/opts.rb +22 -0
- data/lib/roda/plugins/Integer_matcher_max.rb +1 -1
- data/lib/roda/plugins/_add_script_name.rb +14 -0
- data/lib/roda/plugins/_json.rb +22 -0
- data/lib/roda/plugins/_symbol_class_matchers.rb +6 -6
- data/lib/roda/plugins/additional_render_engines.rb +5 -1
- data/lib/roda/plugins/additional_view_directories.rb +5 -1
- data/lib/roda/plugins/assets.rb +7 -10
- data/lib/roda/plugins/autoload_hash_branches.rb +9 -3
- data/lib/roda/plugins/autoload_named_routes.rb +9 -3
- data/lib/roda/plugins/capture_erb.rb +5 -1
- data/lib/roda/plugins/chunked.rb +11 -5
- data/lib/roda/plugins/class_level_routing.rb +5 -3
- data/lib/roda/plugins/class_matchers.rb +3 -1
- data/lib/roda/plugins/common_logger.rb +7 -3
- data/lib/roda/plugins/conditional_sessions.rb +1 -1
- data/lib/roda/plugins/content_for.rb +5 -1
- data/lib/roda/plugins/content_security_policy.rb +6 -2
- data/lib/roda/plugins/cookie_flags.rb +6 -2
- data/lib/roda/plugins/cookies.rb +7 -3
- data/lib/roda/plugins/custom_block_results.rb +5 -3
- data/lib/roda/plugins/custom_matchers.rb +4 -2
- data/lib/roda/plugins/default_headers.rb +2 -5
- data/lib/roda/plugins/default_status.rb +1 -0
- data/lib/roda/plugins/each_part.rb +19 -23
- data/lib/roda/plugins/environments.rb +3 -7
- data/lib/roda/plugins/error_email.rb +9 -5
- data/lib/roda/plugins/error_handler.rb +5 -3
- data/lib/roda/plugins/error_mail.rb +6 -2
- data/lib/roda/plugins/hash_branch_view_subdir.rb +6 -4
- data/lib/roda/plugins/hash_branches.rb +7 -5
- data/lib/roda/plugins/hash_paths.rb +7 -5
- data/lib/roda/plugins/hash_public.rb +11 -7
- data/lib/roda/plugins/hash_public_cache.rb +9 -7
- data/lib/roda/plugins/hash_routes.rb +5 -3
- data/lib/roda/plugins/heartbeat.rb +6 -2
- data/lib/roda/plugins/hmac_paths.rb +9 -3
- data/lib/roda/plugins/hooks.rb +13 -10
- data/lib/roda/plugins/host_authorization.rb +7 -2
- data/lib/roda/plugins/host_routing.rb +7 -2
- data/lib/roda/plugins/invalid_request_body.rb +20 -4
- data/lib/roda/plugins/ip_from_header.rb +5 -1
- data/lib/roda/plugins/json.rb +10 -8
- data/lib/roda/plugins/json_parser.rb +26 -12
- data/lib/roda/plugins/mail_processor.rb +9 -6
- data/lib/roda/plugins/mailer.rb +5 -3
- data/lib/roda/plugins/match_affix.rb +6 -1
- data/lib/roda/plugins/match_hook_args.rb +7 -5
- data/lib/roda/plugins/middleware.rb +13 -7
- data/lib/roda/plugins/module_include.rb +1 -1
- data/lib/roda/plugins/multi_public.rb +6 -2
- data/lib/roda/plugins/multi_route.rb +1 -1
- data/lib/roda/plugins/multi_run.rb +13 -17
- data/lib/roda/plugins/named_routes.rb +8 -6
- data/lib/roda/plugins/named_templates.rb +5 -3
- data/lib/roda/plugins/path.rb +16 -14
- data/lib/roda/plugins/path_rewriter.rb +8 -5
- data/lib/roda/plugins/permissions_policy.rb +7 -3
- data/lib/roda/plugins/public.rb +11 -10
- data/lib/roda/plugins/recheck_precompiled_assets.rb +1 -1
- data/lib/roda/plugins/redirect_http_to_https.rb +6 -3
- data/lib/roda/plugins/render.rb +34 -49
- data/lib/roda/plugins/render_coverage.rb +6 -3
- data/lib/roda/plugins/render_locals.rb +12 -6
- data/lib/roda/plugins/request_aref.rb +1 -1
- data/lib/roda/plugins/response_content_type.rb +7 -3
- data/lib/roda/plugins/route_csrf.rb +7 -2
- data/lib/roda/plugins/run_append_slash.rb +5 -1
- data/lib/roda/plugins/sec_fetch_site_csrf.rb +6 -2
- data/lib/roda/plugins/sessions.rb +15 -11
- data/lib/roda/plugins/shape_friendly.rb +3 -1
- data/lib/roda/plugins/sinatra_helpers.rb +7 -3
- data/lib/roda/plugins/status_handler.rb +5 -3
- data/lib/roda/plugins/strip_path_prefix.rb +4 -2
- data/lib/roda/plugins/symbol_matchers.rb +3 -1
- data/lib/roda/plugins/symbol_views.rb +1 -1
- data/lib/roda/plugins/timestamp_public.rb +8 -4
- data/lib/roda/plugins/type_routing.rb +9 -5
- data/lib/roda/plugins/typecast_params.rb +2 -2
- data/lib/roda/plugins/typecast_params_sized_integers.rb +1 -1
- data/lib/roda/plugins/url_escape.rb +2 -14
- data/lib/roda/plugins.rb +10 -0
- data/lib/roda/version.rb +1 -1
- data/lib/roda.rb +25 -14
- metadata +6 -3
|
@@ -256,6 +256,11 @@ class Roda
|
|
|
256
256
|
end
|
|
257
257
|
end
|
|
258
258
|
|
|
259
|
+
module ClassMethods
|
|
260
|
+
RodaPlugins.opt_attr_reader(self, :absolute_redirects, name: :absolute_redirects?)
|
|
261
|
+
RodaPlugins.opt_attr_reader(self, :prefixed_redirects, name: :prefixed_redirects?)
|
|
262
|
+
end
|
|
263
|
+
|
|
259
264
|
module RequestMethods
|
|
260
265
|
# Alias for referrer
|
|
261
266
|
def back
|
|
@@ -285,9 +290,8 @@ class Roda
|
|
|
285
290
|
# If the absolute_redirects or :prefixed_redirects roda class options has been set, respect those
|
|
286
291
|
# and update the path.
|
|
287
292
|
def redirect(path=(no_add_script_name = true; default_redirect_path), status=default_redirect_status)
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
prefixed_redirects = no_add_script_name ? false : opts[:prefixed_redirects]
|
|
293
|
+
absolute_redirects = roda_class.absolute_redirects?
|
|
294
|
+
prefixed_redirects = no_add_script_name ? false : roda_class.prefixed_redirects?
|
|
291
295
|
path = uri(path, absolute_redirects, prefixed_redirects) if absolute_redirects || prefixed_redirects
|
|
292
296
|
super(path, status)
|
|
293
297
|
end
|
|
@@ -37,6 +37,8 @@ class Roda
|
|
|
37
37
|
end
|
|
38
38
|
|
|
39
39
|
module ClassMethods
|
|
40
|
+
RodaPlugins.opt_attr_reader(self, :status_handler, name: :status_handlers)
|
|
41
|
+
|
|
40
42
|
# Install the given block as a status handler for the given HTTP response code.
|
|
41
43
|
def status_handler(code, opts=OPTS, &block)
|
|
42
44
|
# For backwards compatibility, pass request argument if block accepts argument
|
|
@@ -54,7 +56,7 @@ class Roda
|
|
|
54
56
|
end
|
|
55
57
|
|
|
56
58
|
meth = define_roda_method(:"_roda_status_handler__#{code}", arity, &block)
|
|
57
|
-
|
|
59
|
+
status_handlers[code] = define_roda_method(:"_roda_status_handler_#{code}", 1) do |result|
|
|
58
60
|
res = @_response
|
|
59
61
|
res.status = result[0]
|
|
60
62
|
handle_headers.call(res.headers)
|
|
@@ -64,7 +66,7 @@ class Roda
|
|
|
64
66
|
|
|
65
67
|
# Freeze the hash of status handlers so that there can be no thread safety issues at runtime.
|
|
66
68
|
def freeze
|
|
67
|
-
|
|
69
|
+
status_handlers.freeze
|
|
68
70
|
super
|
|
69
71
|
end
|
|
70
72
|
end
|
|
@@ -74,7 +76,7 @@ class Roda
|
|
|
74
76
|
|
|
75
77
|
# If routing returns a response we have a handler for, call that handler.
|
|
76
78
|
def _roda_after_20__status_handler(result)
|
|
77
|
-
if result && (meth =
|
|
79
|
+
if result && (meth = self.class.status_handlers[result[0]]) && (v = result[2]).is_a?(Array) && v.empty?
|
|
78
80
|
send(meth, result)
|
|
79
81
|
end
|
|
80
82
|
end
|
|
@@ -21,9 +21,11 @@ class Roda
|
|
|
21
21
|
end
|
|
22
22
|
|
|
23
23
|
module ClassMethods
|
|
24
|
+
RodaPlugins.opt_attr_reader(self, :strip_path_prefix, name: :strip_path_prefix_regexp)
|
|
25
|
+
|
|
24
26
|
# Strip the path prefix from the gien path if it starts with the prefix.
|
|
25
|
-
def expand_path(path, root=
|
|
26
|
-
super.sub(
|
|
27
|
+
def expand_path(path, root=app_root)
|
|
28
|
+
super.sub(strip_path_prefix_regexp, '')
|
|
27
29
|
end
|
|
28
30
|
end
|
|
29
31
|
end
|
|
@@ -121,6 +121,8 @@ class Roda
|
|
|
121
121
|
end
|
|
122
122
|
|
|
123
123
|
module ClassMethods
|
|
124
|
+
RodaPlugins.opt_attr_reader(self, :symbol_matchers)
|
|
125
|
+
|
|
124
126
|
# Set the matcher and block to use for the given class.
|
|
125
127
|
# The matcher can be a regexp, registered symbol matcher, or registered class
|
|
126
128
|
# matcher (if using the class_matchers plugin).
|
|
@@ -141,7 +143,7 @@ class Roda
|
|
|
141
143
|
|
|
142
144
|
# Freeze the class_matchers hash when freezing the app.
|
|
143
145
|
def freeze
|
|
144
|
-
|
|
146
|
+
symbol_matchers.freeze
|
|
145
147
|
super
|
|
146
148
|
end
|
|
147
149
|
end
|
|
@@ -46,7 +46,11 @@ class Roda
|
|
|
46
46
|
#
|
|
47
47
|
# The options given are also passed to the public plugin.
|
|
48
48
|
def self.configure(app, opts=OPTS)
|
|
49
|
-
app.opts[:timestamp_public_prefix] = (opts[:prefix] || app.
|
|
49
|
+
app.opts[:timestamp_public_prefix] = (opts[:prefix] || app.timestamp_public_prefix || "static").dup.freeze
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
module ClassMethods
|
|
53
|
+
RodaPlugins.opt_attr_reader(self, :timestamp_public_prefix)
|
|
50
54
|
end
|
|
51
55
|
|
|
52
56
|
module InstanceMethods
|
|
@@ -54,8 +58,8 @@ class Roda
|
|
|
54
58
|
# This does not check the file is inside the directory for performance reasons,
|
|
55
59
|
# so this should not be called with untrusted input.
|
|
56
60
|
def timestamp_path(file)
|
|
57
|
-
mtime = File.mtime(File.join(
|
|
58
|
-
"/#{
|
|
61
|
+
mtime = File.mtime(File.join(self.class.public_root, file))
|
|
62
|
+
"/#{self.class.timestamp_public_prefix}/#{sprintf("%i%06i", mtime.to_i, mtime.usec)}/#{file}"
|
|
59
63
|
end
|
|
60
64
|
end
|
|
61
65
|
|
|
@@ -65,7 +69,7 @@ class Roda
|
|
|
65
69
|
# a integer segment for the timestamp, and this is a GET request.
|
|
66
70
|
def timestamp_public
|
|
67
71
|
if is_get?
|
|
68
|
-
on roda_class.
|
|
72
|
+
on roda_class.timestamp_public_prefix, Integer do |_|
|
|
69
73
|
public
|
|
70
74
|
end
|
|
71
75
|
end
|
|
@@ -110,7 +110,7 @@ class Roda
|
|
|
110
110
|
}.freeze
|
|
111
111
|
|
|
112
112
|
def self.configure(app, opts = {})
|
|
113
|
-
config = (app.
|
|
113
|
+
config = (app.type_routing_opts || CONFIGURATION).dup
|
|
114
114
|
[:use_extension, :use_header, :default_type].each do |key|
|
|
115
115
|
config[key] = opts[key] if opts.has_key?(key)
|
|
116
116
|
end
|
|
@@ -149,12 +149,16 @@ class Roda
|
|
|
149
149
|
app.opts[:type_routing] = config.freeze
|
|
150
150
|
end
|
|
151
151
|
|
|
152
|
+
module ClassMethods
|
|
153
|
+
RodaPlugins.opt_attr_reader(self, :type_routing, name: :type_routing_opts)
|
|
154
|
+
end
|
|
155
|
+
|
|
152
156
|
module RequestMethods
|
|
153
157
|
# Yields if the given +type+ matches the requested data type and halts
|
|
154
158
|
# the request afterwards, returning the result of the block.
|
|
155
159
|
def on_type(type, &block)
|
|
156
160
|
return unless type == requested_type
|
|
157
|
-
response[RodaResponseHeaders::CONTENT_TYPE] ||=
|
|
161
|
+
response[RodaResponseHeaders::CONTENT_TYPE] ||= roda_class.type_routing_opts[:types][type]
|
|
158
162
|
always(&block)
|
|
159
163
|
end
|
|
160
164
|
|
|
@@ -162,7 +166,7 @@ class Roda
|
|
|
162
166
|
def requested_type
|
|
163
167
|
return @requested_type if @requested_type
|
|
164
168
|
|
|
165
|
-
opts =
|
|
169
|
+
opts = roda_class.type_routing_opts
|
|
166
170
|
@requested_type = accept_response_type if opts[:use_header]
|
|
167
171
|
@requested_type ||= opts[:default_type]
|
|
168
172
|
end
|
|
@@ -182,7 +186,7 @@ class Roda
|
|
|
182
186
|
# Removes a trailing file extension from the path, and sets
|
|
183
187
|
# the requested type if so.
|
|
184
188
|
def _remaining_path(env)
|
|
185
|
-
opts =
|
|
189
|
+
opts = roda_class.type_routing_opts
|
|
186
190
|
path = super
|
|
187
191
|
|
|
188
192
|
if opts[:use_extension]
|
|
@@ -197,7 +201,7 @@ class Roda
|
|
|
197
201
|
|
|
198
202
|
# The response type indicated by the Accept request header.
|
|
199
203
|
def accept_response_type
|
|
200
|
-
mimes =
|
|
204
|
+
mimes = roda_class.type_routing_opts[:mimes]
|
|
201
205
|
response[RodaResponseHeaders::VARY] = (vary = response[RodaResponseHeaders::VARY]) ? "#{vary}, Accept" : 'Accept'
|
|
202
206
|
|
|
203
207
|
@env['HTTP_ACCEPT'].to_s.split(/\s*,\s*/).map do |part|
|
|
@@ -1122,7 +1122,7 @@ class Roda
|
|
|
1122
1122
|
# before processing them.
|
|
1123
1123
|
def self.configure(app, opts=OPTS, &block)
|
|
1124
1124
|
app.const_set(:TypecastParams, Class.new(RodaPlugins::TypecastParams::Params)) unless app.const_defined?(:TypecastParams)
|
|
1125
|
-
app::TypecastParams.class_eval(&block) if block
|
|
1125
|
+
app::TypecastParams.class_eval(&block) if block # RODA4: use class_exec
|
|
1126
1126
|
if opts[:strip] == :all
|
|
1127
1127
|
app::TypecastParams.send(:include, StringStripper)
|
|
1128
1128
|
end
|
|
@@ -1133,7 +1133,7 @@ class Roda
|
|
|
1133
1133
|
app::TypecastParams.send(:include, SkipBytesizeChecking)
|
|
1134
1134
|
end
|
|
1135
1135
|
if opts[:date_parse_input_handler]
|
|
1136
|
-
app::TypecastParams.
|
|
1136
|
+
app::TypecastParams.class_exec do
|
|
1137
1137
|
include DateParseInputHandler
|
|
1138
1138
|
define_method(:handle_date_parse_input, &opts[:date_parse_input_handler])
|
|
1139
1139
|
private :handle_date_parse_input
|
|
@@ -90,7 +90,7 @@ class Roda
|
|
|
90
90
|
end
|
|
91
91
|
|
|
92
92
|
if default = opts[:default_size]
|
|
93
|
-
app::TypecastParams.
|
|
93
|
+
app::TypecastParams.class_exec do
|
|
94
94
|
meths = ['', 'convert_', '_convert_array_', '_max_input_bytesize_for_', '_invalid_value_message_for_']
|
|
95
95
|
%w[int uint pos_int pos_uint Integer Integeru].each do |type|
|
|
96
96
|
meths.each do |prefix|
|
|
@@ -16,20 +16,8 @@ class Roda
|
|
|
16
16
|
# end
|
|
17
17
|
module UrlEscape
|
|
18
18
|
module InstanceMethods
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
define_method(:url_unescape, Rack::Utils.instance_method(:unescape))
|
|
22
|
-
# simplecov:disable
|
|
23
|
-
else
|
|
24
|
-
def url_escape(v)
|
|
25
|
-
Rack::Utils.escape(v)
|
|
26
|
-
end
|
|
27
|
-
|
|
28
|
-
def url_unescape(v)
|
|
29
|
-
Rack::Utils.unescape(v)
|
|
30
|
-
end
|
|
31
|
-
end
|
|
32
|
-
# simplecov:enable
|
|
19
|
+
define_method(:url_escape, Rack::Utils.instance_method(:escape))
|
|
20
|
+
define_method(:url_unescape, Rack::Utils.instance_method(:unescape))
|
|
33
21
|
end
|
|
34
22
|
end
|
|
35
23
|
|
data/lib/roda/plugins.rb
CHANGED
|
@@ -32,6 +32,16 @@ class Roda
|
|
|
32
32
|
plugin
|
|
33
33
|
end
|
|
34
34
|
|
|
35
|
+
# Define an attr_reader method for name that uses the instance variable
|
|
36
|
+
# <tt>@opt_*</tt>. Designed to be used with instance variables set via RodaOpts#[]=.
|
|
37
|
+
def self.opt_attr_reader(mod, key, name: key)
|
|
38
|
+
opt_name = :"opt_#{key}"
|
|
39
|
+
mod.send(:attr_reader, opt_name)
|
|
40
|
+
mod.send(:alias_method, name, opt_name)
|
|
41
|
+
mod.send(:remove_method, opt_name)
|
|
42
|
+
nil
|
|
43
|
+
end
|
|
44
|
+
|
|
35
45
|
# Register the given plugin with Roda, so that it can be loaded using #plugin
|
|
36
46
|
# with a symbol. Should be used by plugin files. Example:
|
|
37
47
|
#
|
data/lib/roda/version.rb
CHANGED
data/lib/roda.rb
CHANGED
|
@@ -5,6 +5,7 @@ require_relative "roda/request"
|
|
|
5
5
|
require_relative "roda/response"
|
|
6
6
|
require_relative "roda/plugins"
|
|
7
7
|
require_relative "roda/cache"
|
|
8
|
+
require_relative "roda/opts"
|
|
8
9
|
require_relative "roda/version"
|
|
9
10
|
|
|
10
11
|
# The main class for Roda. Roda is built completely out of plugins, with the
|
|
@@ -18,7 +19,8 @@ class Roda
|
|
|
18
19
|
@inherit_middleware = true
|
|
19
20
|
@middleware = []
|
|
20
21
|
@plugins = []
|
|
21
|
-
@opts =
|
|
22
|
+
@opts = RodaOpts.new
|
|
23
|
+
@opts.roda_class = self
|
|
22
24
|
@raw_route_block = nil
|
|
23
25
|
@route_block = nil
|
|
24
26
|
@rack_app_route_block = nil
|
|
@@ -30,6 +32,8 @@ class Roda
|
|
|
30
32
|
module Base
|
|
31
33
|
# Class methods for the Roda class.
|
|
32
34
|
module ClassMethods
|
|
35
|
+
RodaPlugins.opt_attr_reader(self, :root, name: :app_root)
|
|
36
|
+
|
|
33
37
|
# The rack application that this class uses.
|
|
34
38
|
def app
|
|
35
39
|
@app || build_rack_app
|
|
@@ -140,7 +144,7 @@ class Roda
|
|
|
140
144
|
# Fallback to instance_exec in this case.
|
|
141
145
|
b = block
|
|
142
146
|
block = if RUBY_VERSION >= '2.7'
|
|
143
|
-
|
|
147
|
+
lambda{|*a, **kw| instance_exec(*a, **kw, &b)} # Keyword arguments fallback
|
|
144
148
|
else
|
|
145
149
|
# simplecov:disable
|
|
146
150
|
lambda{|*a| instance_exec(*a, &b)} # Keyword arguments fallback
|
|
@@ -189,7 +193,7 @@ class Roda
|
|
|
189
193
|
end
|
|
190
194
|
|
|
191
195
|
# Expand the given path, using the root argument as the base directory.
|
|
192
|
-
def expand_path(path, root=
|
|
196
|
+
def expand_path(path, root=app_root)
|
|
193
197
|
::File.expand_path(path, root)
|
|
194
198
|
end
|
|
195
199
|
|
|
@@ -207,9 +211,9 @@ class Roda
|
|
|
207
211
|
# If the _roda_run_main_route instance method has not been overridden,
|
|
208
212
|
# make it an alias to _roda_main_route for performance
|
|
209
213
|
if instance_method(:_roda_run_main_route).owner == InstanceMethods
|
|
210
|
-
|
|
214
|
+
alias_method :_roda_run_main_route, :_roda_main_route
|
|
211
215
|
end
|
|
212
|
-
self::RodaResponse.
|
|
216
|
+
self::RodaResponse.class_exec do
|
|
213
217
|
if instance_method(:set_default_headers).owner == ResponseMethods &&
|
|
214
218
|
instance_method(:default_headers).owner == ResponseMethods
|
|
215
219
|
|
|
@@ -253,21 +257,28 @@ class Roda
|
|
|
253
257
|
def inherited(subclass)
|
|
254
258
|
raise RodaError, "Cannot subclass a frozen Roda class" if frozen?
|
|
255
259
|
|
|
256
|
-
# Mark current class as having been subclassed, as some optimizations
|
|
257
|
-
# depend on the class not being subclassed
|
|
258
|
-
opts[:subclassed] = true
|
|
259
|
-
|
|
260
260
|
super
|
|
261
261
|
subclass.instance_variable_set(:@inherit_middleware, @inherit_middleware)
|
|
262
262
|
subclass.instance_variable_set(:@middleware, @inherit_middleware ? @middleware.dup : [])
|
|
263
263
|
subclass.instance_variable_set(:@plugins, @plugins.dup)
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
264
|
+
|
|
265
|
+
opts = RodaOpts.new
|
|
266
|
+
opts.roda_class = subclass
|
|
267
|
+
@opts.each do |k,v|
|
|
268
|
+
opts[k] = if k == :subclassed
|
|
269
|
+
false
|
|
270
|
+
elsif (v.is_a?(Array) || v.is_a?(Hash)) && !v.frozen?
|
|
271
|
+
v.dup
|
|
272
|
+
else
|
|
273
|
+
v
|
|
269
274
|
end
|
|
270
275
|
end
|
|
276
|
+
subclass.instance_variable_set(:@opts, opts)
|
|
277
|
+
|
|
278
|
+
# Mark current class as having been subclassed, as some optimizations
|
|
279
|
+
# depend on the class not being subclassed
|
|
280
|
+
@opts[:subclassed] = true
|
|
281
|
+
|
|
271
282
|
if block = @raw_route_block
|
|
272
283
|
subclass.route(&block)
|
|
273
284
|
end
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: roda
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 3.
|
|
4
|
+
version: 3.109.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Jeremy Evans
|
|
@@ -159,11 +159,14 @@ files:
|
|
|
159
159
|
- MIT-LICENSE
|
|
160
160
|
- lib/roda.rb
|
|
161
161
|
- lib/roda/cache.rb
|
|
162
|
+
- lib/roda/opts.rb
|
|
162
163
|
- lib/roda/plugins.rb
|
|
163
164
|
- lib/roda/plugins/Integer_matcher_max.rb
|
|
165
|
+
- lib/roda/plugins/_add_script_name.rb
|
|
164
166
|
- lib/roda/plugins/_after_hook.rb
|
|
165
167
|
- lib/roda/plugins/_base64.rb
|
|
166
168
|
- lib/roda/plugins/_before_hook.rb
|
|
169
|
+
- lib/roda/plugins/_json.rb
|
|
167
170
|
- lib/roda/plugins/_optimized_matching.rb
|
|
168
171
|
- lib/roda/plugins/_symbol_class_matchers.rb
|
|
169
172
|
- lib/roda/plugins/_symbol_regexp_matchers.rb
|
|
@@ -334,14 +337,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
|
334
337
|
requirements:
|
|
335
338
|
- - ">="
|
|
336
339
|
- !ruby/object:Gem::Version
|
|
337
|
-
version:
|
|
340
|
+
version: '2.0'
|
|
338
341
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
339
342
|
requirements:
|
|
340
343
|
- - ">="
|
|
341
344
|
- !ruby/object:Gem::Version
|
|
342
345
|
version: '0'
|
|
343
346
|
requirements: []
|
|
344
|
-
rubygems_version: 4.0.
|
|
347
|
+
rubygems_version: 4.0.20
|
|
345
348
|
specification_version: 4
|
|
346
349
|
summary: Routing tree web toolkit
|
|
347
350
|
test_files: []
|