aboutsummaryrefslogtreecommitdiffstats
path: root/actionpack/lib/action_dispatch/routing
diff options
context:
space:
mode:
Diffstat (limited to 'actionpack/lib/action_dispatch/routing')
-rw-r--r--actionpack/lib/action_dispatch/routing/mapper.rb22
-rw-r--r--actionpack/lib/action_dispatch/routing/route_set.rb78
2 files changed, 31 insertions, 69 deletions
diff --git a/actionpack/lib/action_dispatch/routing/mapper.rb b/actionpack/lib/action_dispatch/routing/mapper.rb
index 0afe1852f2..c3a9422ceb 100644
--- a/actionpack/lib/action_dispatch/routing/mapper.rb
+++ b/actionpack/lib/action_dispatch/routing/mapper.rb
@@ -150,9 +150,9 @@ module ActionDispatch
conditions,
required_defaults,
defaults,
- request_method)
+ request_method,
+ precedence)
- route.precedence = precedence
route
end
@@ -187,18 +187,16 @@ module ActionDispatch
def build_path(ast, requirements, anchor)
pattern = Journey::Path::Pattern.new(ast, requirements, JOINED_SEPARATORS, anchor)
- builder = Journey::GTG::Builder.new ast
-
# Get all the symbol nodes followed by literals that are not the
# dummy node.
- symbols = ast.grep(Journey::Nodes::Symbol).find_all { |n|
- builder.followpos(n).first.literal?
- }
+ symbols = ast.find_all { |n|
+ n.cat? && n.left.symbol? && n.right.cat? && n.right.left.literal?
+ }.map(&:left)
# Get all the symbol nodes preceded by literals.
- symbols.concat ast.find_all(&:literal?).map { |n|
- builder.followpos(n).first
- }.find_all(&:symbol?)
+ symbols.concat ast.find_all { |n|
+ n.cat? && n.left.literal? && n.right.cat? && n.right.left.symbol?
+ }.map { |n| n.right.left }
symbols.each { |x|
x.regexp = /(?:#{Regexp.union(x.regexp, '-')})+/
@@ -370,7 +368,7 @@ module ActionDispatch
end
def dispatcher(raise_on_name_error)
- @set.dispatcher raise_on_name_error
+ Routing::RouteSet::Dispatcher.new raise_on_name_error
end
end
@@ -637,7 +635,7 @@ module ActionDispatch
# Query if the following named route was already defined.
def has_named_route?(name)
- @set.named_routes.routes[name.to_sym]
+ @set.named_routes.key? name
end
private
diff --git a/actionpack/lib/action_dispatch/routing/route_set.rb b/actionpack/lib/action_dispatch/routing/route_set.rb
index 30e308119d..4e29476117 100644
--- a/actionpack/lib/action_dispatch/routing/route_set.rb
+++ b/actionpack/lib/action_dispatch/routing/route_set.rb
@@ -1,6 +1,5 @@
require 'action_dispatch/journey'
require 'forwardable'
-require 'thread_safe'
require 'active_support/concern'
require 'active_support/core_ext/object/to_query'
require 'active_support/core_ext/hash/slice'
@@ -23,49 +22,22 @@ module ActionDispatch
class Dispatcher < Routing::Endpoint
def initialize(raise_on_name_error)
@raise_on_name_error = raise_on_name_error
- @controller_class_names = ThreadSafe::Cache.new
end
def dispatcher?; true; end
def serve(req)
- req.check_path_parameters!
params = req.path_parameters
-
- prepare_params!(params)
-
- controller = controller(params, @raise_on_name_error) do
+ controller = req.controller_class do
return [404, {'X-Cascade' => 'pass'}, []]
end
-
dispatch(controller, params[:action], req)
- end
-
- def prepare_params!(params)
- normalize_controller!(params)
- merge_default_action!(params)
- end
-
- # If this is a default_controller (i.e. a controller specified by the user)
- # we should raise an error in case it's not found, because it usually means
- # a user error. However, if the controller was retrieved through a dynamic
- # segment, as in :controller(/:action), we should simply return nil and
- # delegate the control back to Rack cascade. Besides, if this is not a default
- # controller, it means we should respect the @scope[:module] parameter.
- def controller(params, raise_on_name_error=true)
- controller_reference params.fetch(:controller) { yield }
rescue NameError => e
- raise ActionController::RoutingError, e.message, e.backtrace if raise_on_name_error
- yield
- end
-
- protected
-
- attr_reader :controller_class_names
-
- def controller_reference(controller_param)
- const_name = controller_class_names[controller_param] ||= "#{controller_param.camelize}Controller"
- ActiveSupport::Dependencies.constantize(const_name)
+ if @raise_on_name_error
+ raise ActionController::RoutingError, e.message, e.backtrace
+ else
+ return [404, {'X-Cascade' => 'pass'}, []]
+ end
end
private
@@ -73,14 +45,6 @@ module ActionDispatch
def dispatch(controller, action, req)
controller.action(action).call(req.env)
end
-
- def normalize_controller!(params)
- params[:controller] = params[:controller].underscore if params.key?(:controller)
- end
-
- def merge_default_action!(params)
- params[:action] ||= 'index'
- end
end
# A NamedRouteCollection instance is a collection of named routes, and also
@@ -89,6 +53,7 @@ module ActionDispatch
class NamedRouteCollection
include Enumerable
attr_reader :routes, :url_helpers_module, :path_helpers_module
+ private :routes
def initialize
@routes = {}
@@ -201,9 +166,9 @@ module ActionDispatch
private
def optimized_helper(args)
- params = parameterize_args(args) { |k|
+ params = parameterize_args(args) do
raise_generation_error(args)
- }
+ end
@route.format params
end
@@ -315,7 +280,7 @@ module ActionDispatch
attr_accessor :formatter, :set, :named_routes, :default_scope, :router
attr_accessor :disable_clear_and_finalize, :resources_path_names
- attr_accessor :default_url_options, :dispatcher_class
+ attr_accessor :default_url_options
attr_reader :env_key
alias :routes :set
@@ -358,7 +323,6 @@ module ActionDispatch
@set = Journey::Routes.new
@router = Journey::Router.new @set
@formatter = Journey::Formatter.new self
- @dispatcher_class = Routing::RouteSet::Dispatcher
end
def relative_url_root
@@ -373,6 +337,11 @@ module ActionDispatch
ActionDispatch::Request
end
+ def make_request(env)
+ request_class.new env
+ end
+ private :make_request
+
def draw(&block)
clear! unless @disable_clear_and_finalize
eval_block(block)
@@ -416,10 +385,6 @@ module ActionDispatch
@prepend.each { |blk| eval_block(blk) }
end
- def dispatcher(raise_on_name_error)
- dispatcher_class.new(raise_on_name_error)
- end
-
module MountedHelpers
extend ActiveSupport::Concern
include UrlFor
@@ -730,7 +695,7 @@ module ActionDispatch
end
def call(env)
- req = request_class.new(env)
+ req = make_request(env)
req.path_info = Journey::Router::Utils.normalize_path(req.path_info)
@router.serve(req)
end
@@ -746,7 +711,7 @@ module ActionDispatch
raise ActionController::RoutingError, e.message
end
- req = request_class.new(env)
+ req = make_request(env)
@router.recognize(req) do |route, params|
params.merge!(extras)
params.each do |key, value|
@@ -759,14 +724,13 @@ module ActionDispatch
req.path_parameters = old_params.merge params
app = route.app
if app.matches?(req) && app.dispatcher?
- dispatcher = app.app
-
- dispatcher.controller(params, false) do
+ begin
+ req.controller_class
+ rescue NameError
raise ActionController::RoutingError, "A route matches #{path.inspect}, but references missing controller: #{params[:controller].camelize}Controller"
end
- dispatcher.prepare_params!(params)
- return params
+ return req.path_parameters
end
end