aboutsummaryrefslogtreecommitdiffstats
path: root/actionpack/lib/action_dispatch/journey/route.rb
diff options
context:
space:
mode:
Diffstat (limited to 'actionpack/lib/action_dispatch/journey/route.rb')
-rw-r--r--actionpack/lib/action_dispatch/journey/route.rb54
1 files changed, 48 insertions, 6 deletions
diff --git a/actionpack/lib/action_dispatch/journey/route.rb b/actionpack/lib/action_dispatch/journey/route.rb
index fa69ba776a..5d5fe4698d 100644
--- a/actionpack/lib/action_dispatch/journey/route.rb
+++ b/actionpack/lib/action_dispatch/journey/route.rb
@@ -8,9 +8,49 @@ module ActionDispatch
attr_accessor :precedence
- ANY = //
+ module VerbMatchers
+ VERBS = %w{ DELETE GET HEAD OPTIONS LINK PATCH POST PUT TRACE UNLINK }
+ VERBS.each do |v|
+ class_eval <<-eoc
+ class #{v}
+ def self.verb; name.split("::").last; end
+ def self.call(req); req.#{v.downcase}?; end
+ end
+ eoc
+ end
+
+ class Unknown
+ attr_reader :verb
+
+ def initialize(verb)
+ @verb = verb
+ end
+
+ def call(request); @verb === request.request_method; end
+ end
+
+ class All
+ def self.call(_); true; end
+ def self.verb; ''; end
+ end
+
+ VERB_TO_CLASS = VERBS.each_with_object({ :all => All }) do |verb, hash|
+ klass = const_get verb
+ hash[verb] = klass
+ hash[verb.downcase] = klass
+ hash[verb.downcase.to_sym] = klass
+ end
+
+ end
+
+ def self.verb_matcher(verb)
+ VerbMatchers::VERB_TO_CLASS.fetch(verb) do
+ VerbMatchers::Unknown.new verb.to_s.dasherize.upcase
+ end
+ end
+
def self.build(name, app, path, constraints, required_defaults, defaults)
- request_method_match = constraints.delete(:request_method) || ANY
+ request_method_match = verb_matcher(constraints.delete(:request_method)) || []
new name, app, path, constraints, required_defaults, defaults, request_method_match
end
@@ -121,18 +161,20 @@ module ActionDispatch
end
def requires_matching_verb?
- @request_method_match != ANY
+ !@request_method_match.all? { |x| x == VerbMatchers::All }
end
def verb
- @request_method_match
+ %r[^#{verbs.join('|')}$]
end
private
+ def verbs
+ @request_method_match.map(&:verb)
+ end
def match_verb(request)
- return true unless requires_matching_verb?
- verb === request.request_method
+ @request_method_match.any? { |m| m.call request }
end
end
end