diff options
Diffstat (limited to 'actionpack/lib')
58 files changed, 262 insertions, 189 deletions
diff --git a/actionpack/lib/abstract_controller/base.rb b/actionpack/lib/abstract_controller/base.rb index dc79820a82..bca850c0c0 100644 --- a/actionpack/lib/abstract_controller/base.rb +++ b/actionpack/lib/abstract_controller/base.rb @@ -1,4 +1,4 @@ -require "abstract_controller/error" +require_relative "error" require "active_support/configurable" require "active_support/descendants_tracker" require "active_support/core_ext/module/anonymous" diff --git a/actionpack/lib/abstract_controller/callbacks.rb b/actionpack/lib/abstract_controller/callbacks.rb index ba7dec6083..e4400e8704 100644 --- a/actionpack/lib/abstract_controller/callbacks.rb +++ b/actionpack/lib/abstract_controller/callbacks.rb @@ -29,7 +29,7 @@ module AbstractController included do define_callbacks :process_action, - terminator: ->(controller, result_lambda) { result_lambda.call if result_lambda.is_a?(Proc); controller.performed? }, + terminator: ->(controller, result_lambda) { result_lambda.call; controller.performed? }, skip_after_callbacks_if_terminated: true end diff --git a/actionpack/lib/abstract_controller/rendering.rb b/actionpack/lib/abstract_controller/rendering.rb index 54af938a93..1c87739d42 100644 --- a/actionpack/lib/abstract_controller/rendering.rb +++ b/actionpack/lib/abstract_controller/rendering.rb @@ -1,4 +1,4 @@ -require "abstract_controller/error" +require_relative "error" require "action_view" require "action_view/view_paths" require "set" diff --git a/actionpack/lib/abstract_controller/translation.rb b/actionpack/lib/abstract_controller/translation.rb index 9e3858802a..e4ac95df50 100644 --- a/actionpack/lib/abstract_controller/translation.rb +++ b/actionpack/lib/abstract_controller/translation.rb @@ -13,7 +13,7 @@ module AbstractController path = controller_path.tr("/", ".") defaults = [:"#{path}#{key}"] defaults << options[:default] if options[:default] - options[:default] = defaults + options[:default] = defaults.flatten key = "#{path}.#{action_name}#{key}" end I18n.translate(key, options) diff --git a/actionpack/lib/action_controller.rb b/actionpack/lib/action_controller.rb index 50f20aa789..4e2d67954f 100644 --- a/actionpack/lib/action_controller.rb +++ b/actionpack/lib/action_controller.rb @@ -1,8 +1,8 @@ require "active_support/rails" require "abstract_controller" require "action_dispatch" -require "action_controller/metal/live" -require "action_controller/metal/strong_parameters" +require_relative "action_controller/metal/live" +require_relative "action_controller/metal/strong_parameters" module ActionController extend ActiveSupport::Autoload diff --git a/actionpack/lib/action_controller/api.rb b/actionpack/lib/action_controller/api.rb index 94698df730..2bfa65021d 100644 --- a/actionpack/lib/action_controller/api.rb +++ b/actionpack/lib/action_controller/api.rb @@ -1,6 +1,6 @@ require "action_view" require "action_controller" -require "action_controller/log_subscriber" +require_relative "log_subscriber" module ActionController # API Controller is a lightweight version of <tt>ActionController::Base</tt>, diff --git a/actionpack/lib/action_controller/base.rb b/actionpack/lib/action_controller/base.rb index 8c2b111f89..6e195fa359 100644 --- a/actionpack/lib/action_controller/base.rb +++ b/actionpack/lib/action_controller/base.rb @@ -1,6 +1,6 @@ require "action_view" -require "action_controller/log_subscriber" -require "action_controller/metal/params_wrapper" +require_relative "log_subscriber" +require_relative "metal/params_wrapper" module ActionController # Action Controllers are the core of a web request in \Rails. They are made up of one or more actions that are executed diff --git a/actionpack/lib/action_controller/log_subscriber.rb b/actionpack/lib/action_controller/log_subscriber.rb index d00fcbcd13..5d75393897 100644 --- a/actionpack/lib/action_controller/log_subscriber.rb +++ b/actionpack/lib/action_controller/log_subscriber.rb @@ -24,7 +24,7 @@ module ActionController exception_class_name = payload[:exception].first status = ActionDispatch::ExceptionWrapper.status_code_for_exception(exception_class_name) end - message = "Completed #{status} #{Rack::Utils::HTTP_STATUS_CODES[status]} in #{event.duration.round}ms" + message = "Completed #{status} #{Rack::Utils::HTTP_STATUS_CODES[status]} in #{event.duration.round}ms".dup message << " (#{additions.join(" | ".freeze)})" unless additions.empty? message << "\n\n" if defined?(Rails.env) && Rails.env.development? diff --git a/actionpack/lib/action_controller/metal/data_streaming.rb b/actionpack/lib/action_controller/metal/data_streaming.rb index 731e03e2fc..3dbdd4a1b6 100644 --- a/actionpack/lib/action_controller/metal/data_streaming.rb +++ b/actionpack/lib/action_controller/metal/data_streaming.rb @@ -1,4 +1,4 @@ -require "action_controller/metal/exceptions" +require_relative "exceptions" module ActionController #:nodoc: # Methods for sending arbitrary data and for streaming files to the browser, diff --git a/actionpack/lib/action_controller/metal/params_wrapper.rb b/actionpack/lib/action_controller/metal/params_wrapper.rb index 68881b8402..818af549eb 100644 --- a/actionpack/lib/action_controller/metal/params_wrapper.rb +++ b/actionpack/lib/action_controller/metal/params_wrapper.rb @@ -232,12 +232,7 @@ module ActionController # by the metal call stack. def process_action(*args) if _wrapper_enabled? - if request.parameters[_wrapper_key].present? - wrapped_hash = _extract_parameters(request.parameters) - else - wrapped_hash = _wrap_parameters request.request_parameters - end - + wrapped_hash = _wrap_parameters request.request_parameters wrapped_keys = request.request_parameters.keys wrapped_filtered_hash = _wrap_parameters request.filtered_parameters.slice(*wrapped_keys) @@ -282,7 +277,7 @@ module ActionController return false unless request.has_content_type? ref = request.content_mime_type.ref - _wrapper_formats.include?(ref) && _wrapper_key && !request.request_parameters[_wrapper_key] + _wrapper_formats.include?(ref) && _wrapper_key && !request.parameters.key?(_wrapper_key) end end end diff --git a/actionpack/lib/action_controller/metal/request_forgery_protection.rb b/actionpack/lib/action_controller/metal/request_forgery_protection.rb index 5051c02a62..4468cbb2fc 100644 --- a/actionpack/lib/action_controller/metal/request_forgery_protection.rb +++ b/actionpack/lib/action_controller/metal/request_forgery_protection.rb @@ -1,5 +1,5 @@ require "rack/session/abstract/id" -require "action_controller/metal/exceptions" +require_relative "exceptions" require "active_support/security_utils" module ActionController #:nodoc: diff --git a/actionpack/lib/action_controller/metal/strong_parameters.rb b/actionpack/lib/action_controller/metal/strong_parameters.rb index 20330b5091..a1b8b7cd6e 100644 --- a/actionpack/lib/action_controller/metal/strong_parameters.rb +++ b/actionpack/lib/action_controller/metal/strong_parameters.rb @@ -119,8 +119,7 @@ module ActionController # params[:key] # => "value" # params["key"] # => "value" class Parameters - cattr_accessor :permit_all_parameters, instance_accessor: false - self.permit_all_parameters = false + cattr_accessor :permit_all_parameters, instance_accessor: false, default: false cattr_accessor :action_on_unpermitted_parameters, instance_accessor: false @@ -181,6 +180,14 @@ module ActionController # Returns a new array of the keys of the parameters. ## + # :method: to_s + # + # :call-seq: + # to_s() + # + # Returns the content of the parameters as a string. + + ## # :method: value? # # :call-seq: @@ -196,7 +203,7 @@ module ActionController # # Returns a new array of the values of the parameters. delegate :keys, :key?, :has_key?, :values, :has_value?, :value?, :empty?, :include?, - :as_json, to: :@parameters + :as_json, :to_s, to: :@parameters # By default, never raise an UnpermittedParameters exception if these # params are present. The default includes both 'controller' and 'action' @@ -205,8 +212,7 @@ module ActionController # config. For instance: # # config.always_permitted_parameters = %w( controller action format ) - cattr_accessor :always_permitted_parameters - self.always_permitted_parameters = %w( controller action ) + cattr_accessor :always_permitted_parameters, default: %w( controller action ) # Returns a new instance of <tt>ActionController::Parameters</tt>. # Also, sets the +permitted+ attribute to the default value of @@ -247,7 +253,7 @@ module ActionController # oddity: "Heavy stone crab" # }) # params.to_h - # # => ActionController::UnfilteredParameters: unable to convert unfiltered parameters to hash + # # => ActionController::UnfilteredParameters: unable to convert unpermitted parameters to hash # # safe_params = params.permit(:name) # safe_params.to_h # => {"name"=>"Senjougahara Hitagi"} @@ -267,7 +273,7 @@ module ActionController # oddity: "Heavy stone crab" # }) # params.to_hash - # # => ActionController::UnfilteredParameters: unable to convert unfiltered parameters to hash + # # => ActionController::UnfilteredParameters: unable to convert unpermitted parameters to hash # # safe_params = params.permit(:name) # safe_params.to_hash # => {"name"=>"Senjougahara Hitagi"} @@ -283,6 +289,10 @@ module ActionController # nationality: "Danish" # }) # params.to_query + # # => ActionController::UnfilteredParameters: unable to convert unpermitted parameters to hash + # + # safe_params = params.permit(:name, :nationality) + # safe_params.to_query # # => "name=David&nationality=Danish" # # An optional namespace can be passed to enclose key names: @@ -291,7 +301,8 @@ module ActionController # name: "David", # nationality: "Danish" # }) - # params.to_query("user") + # safe_params = params.permit(:name, :nationality) + # safe_params.to_query("user") # # => "user%5Bname%5D=David&user%5Bnationality%5D=Danish" # # The string pairs "key=value" that conform the query string diff --git a/actionpack/lib/action_controller/railtie.rb b/actionpack/lib/action_controller/railtie.rb index fadfc8de60..31db7518f1 100644 --- a/actionpack/lib/action_controller/railtie.rb +++ b/actionpack/lib/action_controller/railtie.rb @@ -2,7 +2,7 @@ require "rails" require "action_controller" require "action_dispatch/railtie" require "abstract_controller/railties/routes_helpers" -require "action_controller/railties/helpers" +require_relative "railties/helpers" require "action_view/railtie" module ActionController @@ -22,13 +22,15 @@ module ActionController initializer "action_controller.parameters_config" do |app| options = app.config.action_controller - ActionController::Parameters.permit_all_parameters = options.delete(:permit_all_parameters) { false } - if app.config.action_controller[:always_permitted_parameters] - ActionController::Parameters.always_permitted_parameters = - app.config.action_controller.delete(:always_permitted_parameters) - end - ActionController::Parameters.action_on_unpermitted_parameters = options.delete(:action_on_unpermitted_parameters) do - (Rails.env.test? || Rails.env.development?) ? :log : false + ActiveSupport.on_load(:action_controller) do + ActionController::Parameters.permit_all_parameters = options.delete(:permit_all_parameters) { false } + if app.config.action_controller[:always_permitted_parameters] + ActionController::Parameters.always_permitted_parameters = + app.config.action_controller.delete(:always_permitted_parameters) + end + ActionController::Parameters.action_on_unpermitted_parameters = options.delete(:action_on_unpermitted_parameters) do + (Rails.env.test? || Rails.env.development?) ? :log : false + end end end diff --git a/actionpack/lib/action_controller/test_case.rb b/actionpack/lib/action_controller/test_case.rb index bc42d50205..9d8240e46d 100644 --- a/actionpack/lib/action_controller/test_case.rb +++ b/actionpack/lib/action_controller/test_case.rb @@ -4,7 +4,7 @@ require "active_support/core_ext/object/to_query" require "active_support/core_ext/module/anonymous" require "active_support/core_ext/hash/keys" require "active_support/testing/constant_lookup" -require "action_controller/template_assertions" +require_relative "template_assertions" require "rails-dom-testing" module ActionController diff --git a/actionpack/lib/action_dispatch/http/filter_parameters.rb b/actionpack/lib/action_dispatch/http/filter_parameters.rb index e584b84d92..eb6761d067 100644 --- a/actionpack/lib/action_dispatch/http/filter_parameters.rb +++ b/actionpack/lib/action_dispatch/http/filter_parameters.rb @@ -1,4 +1,4 @@ -require "action_dispatch/http/parameter_filter" +require_relative "parameter_filter" module ActionDispatch module Http @@ -74,7 +74,7 @@ module ActionDispatch PAIR_RE = %r{(#{KV_RE})=(#{KV_RE})} def filtered_query_string # :doc: query_string.gsub(PAIR_RE) do |_| - parameter_filter.filter([[$1, $2]]).first.join("=") + parameter_filter.filter($1 => $2).first.join("=") end end end diff --git a/actionpack/lib/action_dispatch/http/mime_negotiation.rb b/actionpack/lib/action_dispatch/http/mime_negotiation.rb index 19f89edbc1..5994a01c78 100644 --- a/actionpack/lib/action_dispatch/http/mime_negotiation.rb +++ b/actionpack/lib/action_dispatch/http/mime_negotiation.rb @@ -6,8 +6,7 @@ module ActionDispatch extend ActiveSupport::Concern included do - mattr_accessor :ignore_accept_header - self.ignore_accept_header = false + mattr_accessor :ignore_accept_header, default: false end # The MIME type of the HTTP request, such as Mime[:xml]. diff --git a/actionpack/lib/action_dispatch/http/mime_type.rb b/actionpack/lib/action_dispatch/http/mime_type.rb index 74a3afab44..5a0f661d99 100644 --- a/actionpack/lib/action_dispatch/http/mime_type.rb +++ b/actionpack/lib/action_dispatch/http/mime_type.rb @@ -337,4 +337,4 @@ module Mime end end -require "action_dispatch/http/mime_types" +require_relative "mime_types" diff --git a/actionpack/lib/action_dispatch/http/parameter_filter.rb b/actionpack/lib/action_dispatch/http/parameter_filter.rb index 889f55a52a..1d2b4b902b 100644 --- a/actionpack/lib/action_dispatch/http/parameter_filter.rb +++ b/actionpack/lib/action_dispatch/http/parameter_filter.rb @@ -54,7 +54,7 @@ module ActionDispatch end def call(original_params, parents = []) - filtered_params = {} + filtered_params = original_params.class.new original_params.each do |key, value| parents.push(key) if deep_regexps diff --git a/actionpack/lib/action_dispatch/http/request.rb b/actionpack/lib/action_dispatch/http/request.rb index 6d42404a98..914163f219 100644 --- a/actionpack/lib/action_dispatch/http/request.rb +++ b/actionpack/lib/action_dispatch/http/request.rb @@ -1,15 +1,16 @@ +# frozen_string_literal: true require "stringio" require "active_support/inflector" -require "action_dispatch/http/headers" +require_relative "headers" require "action_controller/metal/exceptions" require "rack/request" -require "action_dispatch/http/cache" -require "action_dispatch/http/mime_negotiation" -require "action_dispatch/http/parameters" -require "action_dispatch/http/filter_parameters" -require "action_dispatch/http/upload" -require "action_dispatch/http/url" +require_relative "cache" +require_relative "mime_negotiation" +require_relative "parameters" +require_relative "filter_parameters" +require_relative "upload" +require_relative "url" require "active_support/core_ext/array/conversions" module ActionDispatch diff --git a/actionpack/lib/action_dispatch/http/response.rb b/actionpack/lib/action_dispatch/http/response.rb index 2ee52eeb48..eab663e2e0 100644 --- a/actionpack/lib/action_dispatch/http/response.rb +++ b/actionpack/lib/action_dispatch/http/response.rb @@ -1,6 +1,6 @@ require "active_support/core_ext/module/attribute_accessors" -require "action_dispatch/http/filter_redirect" -require "action_dispatch/http/cache" +require_relative "filter_redirect" +require_relative "cache" require "monitor" module ActionDispatch # :nodoc: @@ -81,8 +81,8 @@ module ActionDispatch # :nodoc: LOCATION = "Location".freeze NO_CONTENT_CODES = [100, 101, 102, 204, 205, 304] - cattr_accessor(:default_charset) { "utf-8" } - cattr_accessor(:default_headers) + cattr_accessor :default_charset, default: "utf-8" + cattr_accessor :default_headers include Rack::Response::Helpers # Aliasing these off because AD::Http::Cache::Response defines them. @@ -103,7 +103,7 @@ module ActionDispatch # :nodoc: def body @str_body ||= begin - buf = "" + buf = "".dup each { |chunk| buf << chunk } buf end diff --git a/actionpack/lib/action_dispatch/http/url.rb b/actionpack/lib/action_dispatch/http/url.rb index b6be48a48b..28672e2a1a 100644 --- a/actionpack/lib/action_dispatch/http/url.rb +++ b/actionpack/lib/action_dispatch/http/url.rb @@ -1,3 +1,4 @@ +# frozen_string_literal: true require "active_support/core_ext/module/attribute_accessors" module ActionDispatch @@ -7,8 +8,7 @@ module ActionDispatch HOST_REGEXP = /(^[^:]+:\/\/)?(\[[^\]]+\]|[^:]+)(?::(\d+$))?/ PROTOCOL_REGEXP = /^([^:]+)(:)?(\/\/)?$/ - mattr_accessor :tld_length - self.tld_length = 1 + mattr_accessor :tld_length, default: 1 class << self # Returns the domain part of a host given the domain level. @@ -156,7 +156,7 @@ module ActionDispatch subdomain = options.fetch :subdomain, true domain = options[:domain] - host = "" + host = "".dup if subdomain == true return _host if domain.nil? diff --git a/actionpack/lib/action_dispatch/journey.rb b/actionpack/lib/action_dispatch/journey.rb index d1cfc51f3e..222cbf4584 100644 --- a/actionpack/lib/action_dispatch/journey.rb +++ b/actionpack/lib/action_dispatch/journey.rb @@ -1,5 +1,5 @@ -require "action_dispatch/journey/router" -require "action_dispatch/journey/gtg/builder" -require "action_dispatch/journey/gtg/simulator" -require "action_dispatch/journey/nfa/builder" -require "action_dispatch/journey/nfa/simulator" +require_relative "journey/router" +require_relative "journey/gtg/builder" +require_relative "journey/gtg/simulator" +require_relative "journey/nfa/builder" +require_relative "journey/nfa/simulator" diff --git a/actionpack/lib/action_dispatch/journey/formatter.rb b/actionpack/lib/action_dispatch/journey/formatter.rb index 326f4e52f9..119811d8ea 100644 --- a/actionpack/lib/action_dispatch/journey/formatter.rb +++ b/actionpack/lib/action_dispatch/journey/formatter.rb @@ -1,3 +1,4 @@ +# frozen_string_literal: true require "action_controller/metal/exceptions" module ActionDispatch @@ -48,7 +49,7 @@ module ActionDispatch unmatched_keys = (missing_keys || []) & constraints.keys missing_keys = (missing_keys || []) - unmatched_keys - message = "No route matches #{Hash[constraints.sort_by { |k, v| k.to_s }].inspect}" + message = "No route matches #{Hash[constraints.sort_by { |k, v| k.to_s }].inspect}".dup message << ", missing required keys: #{missing_keys.sort.inspect}" if missing_keys && !missing_keys.empty? message << ", possible unmatched constraints: #{unmatched_keys.sort.inspect}" if unmatched_keys && !unmatched_keys.empty? diff --git a/actionpack/lib/action_dispatch/journey/gtg/builder.rb b/actionpack/lib/action_dispatch/journey/gtg/builder.rb index 0f8bed89bf..b1132ef17c 100644 --- a/actionpack/lib/action_dispatch/journey/gtg/builder.rb +++ b/actionpack/lib/action_dispatch/journey/gtg/builder.rb @@ -1,4 +1,4 @@ -require "action_dispatch/journey/gtg/transition_table" +require_relative "transition_table" module ActionDispatch module Journey # :nodoc: diff --git a/actionpack/lib/action_dispatch/journey/gtg/transition_table.rb b/actionpack/lib/action_dispatch/journey/gtg/transition_table.rb index 45aff287b1..278e4f0e11 100644 --- a/actionpack/lib/action_dispatch/journey/gtg/transition_table.rb +++ b/actionpack/lib/action_dispatch/journey/gtg/transition_table.rb @@ -1,4 +1,4 @@ -require "action_dispatch/journey/nfa/dot" +require_relative "../nfa/dot" module ActionDispatch module Journey # :nodoc: diff --git a/actionpack/lib/action_dispatch/journey/nfa/builder.rb b/actionpack/lib/action_dispatch/journey/nfa/builder.rb index 532f765094..5b628d8cef 100644 --- a/actionpack/lib/action_dispatch/journey/nfa/builder.rb +++ b/actionpack/lib/action_dispatch/journey/nfa/builder.rb @@ -1,5 +1,5 @@ -require "action_dispatch/journey/nfa/transition_table" -require "action_dispatch/journey/gtg/transition_table" +require_relative "transition_table" +require_relative "../gtg/transition_table" module ActionDispatch module Journey # :nodoc: diff --git a/actionpack/lib/action_dispatch/journey/nfa/transition_table.rb b/actionpack/lib/action_dispatch/journey/nfa/transition_table.rb index 543a670da0..d18243545b 100644 --- a/actionpack/lib/action_dispatch/journey/nfa/transition_table.rb +++ b/actionpack/lib/action_dispatch/journey/nfa/transition_table.rb @@ -1,4 +1,4 @@ -require "action_dispatch/journey/nfa/dot" +require_relative "dot" module ActionDispatch module Journey # :nodoc: diff --git a/actionpack/lib/action_dispatch/journey/nodes/node.rb b/actionpack/lib/action_dispatch/journey/nodes/node.rb index 0d874a84c9..97acad6995 100644 --- a/actionpack/lib/action_dispatch/journey/nodes/node.rb +++ b/actionpack/lib/action_dispatch/journey/nodes/node.rb @@ -1,4 +1,4 @@ -require "action_dispatch/journey/visitors" +require_relative "../visitors" module ActionDispatch module Journey # :nodoc: diff --git a/actionpack/lib/action_dispatch/journey/parser.rb b/actionpack/lib/action_dispatch/journey/parser.rb index e002755bcf..6ddfe96098 100644 --- a/actionpack/lib/action_dispatch/journey/parser.rb +++ b/actionpack/lib/action_dispatch/journey/parser.rb @@ -8,7 +8,7 @@ require 'racc/parser.rb' # :stopdoc: -require "action_dispatch/journey/parser_extras" +require_relative "parser_extras" module ActionDispatch module Journey class Parser < Racc::Parser diff --git a/actionpack/lib/action_dispatch/journey/parser.y b/actionpack/lib/action_dispatch/journey/parser.y index f9b1a7a958..850c84ea1a 100644 --- a/actionpack/lib/action_dispatch/journey/parser.y +++ b/actionpack/lib/action_dispatch/journey/parser.y @@ -47,4 +47,4 @@ end ---- header # :stopdoc: -require "action_dispatch/journey/parser_extras" +require_relative "parser_extras" diff --git a/actionpack/lib/action_dispatch/journey/parser_extras.rb b/actionpack/lib/action_dispatch/journey/parser_extras.rb index 4c7e82d93c..d26f0e121f 100644 --- a/actionpack/lib/action_dispatch/journey/parser_extras.rb +++ b/actionpack/lib/action_dispatch/journey/parser_extras.rb @@ -1,5 +1,5 @@ -require "action_dispatch/journey/scanner" -require "action_dispatch/journey/nodes/node" +require_relative "scanner" +require_relative "nodes/node" module ActionDispatch # :stopdoc: diff --git a/actionpack/lib/action_dispatch/journey/router.rb b/actionpack/lib/action_dispatch/journey/router.rb index d55e1399e4..85f4aade55 100644 --- a/actionpack/lib/action_dispatch/journey/router.rb +++ b/actionpack/lib/action_dispatch/journey/router.rb @@ -1,14 +1,14 @@ -require "action_dispatch/journey/router/utils" -require "action_dispatch/journey/routes" -require "action_dispatch/journey/formatter" +require_relative "router/utils" +require_relative "routes" +require_relative "formatter" before = $-w $-w = false -require "action_dispatch/journey/parser" +require_relative "parser" $-w = before -require "action_dispatch/journey/route" -require "action_dispatch/journey/path/pattern" +require_relative "route" +require_relative "path/pattern" module ActionDispatch module Journey # :nodoc: diff --git a/actionpack/lib/action_dispatch/journey/router/utils.rb b/actionpack/lib/action_dispatch/journey/router/utils.rb index 6d400f3364..1ac86d10d6 100644 --- a/actionpack/lib/action_dispatch/journey/router/utils.rb +++ b/actionpack/lib/action_dispatch/journey/router/utils.rb @@ -14,11 +14,11 @@ module ActionDispatch # normalize_path("/%ab") # => "/%AB" def self.normalize_path(path) encoding = path.encoding - path = "/#{path}" + path = "/#{path}".dup path.squeeze!("/".freeze) path.sub!(%r{/+\Z}, "".freeze) path.gsub!(/(%[a-f0-9]{2})/) { $1.upcase } - path = "/" if path == "".freeze + path = "/".dup if path == "".freeze path.force_encoding(encoding) path end @@ -29,7 +29,7 @@ module ActionDispatch ENCODE = "%%%02X".freeze US_ASCII = Encoding::US_ASCII UTF_8 = Encoding::UTF_8 - EMPTY = "".force_encoding(US_ASCII).freeze + EMPTY = "".dup.force_encoding(US_ASCII).freeze DEC2HEX = (0..255).to_a.map { |i| ENCODE % i }.map { |s| s.force_encoding(US_ASCII) } ALPHA = "a-zA-Z".freeze diff --git a/actionpack/lib/action_dispatch/journey/visitors.rb b/actionpack/lib/action_dispatch/journey/visitors.rb index 335797f4b9..12b96afb24 100644 --- a/actionpack/lib/action_dispatch/journey/visitors.rb +++ b/actionpack/lib/action_dispatch/journey/visitors.rb @@ -1,3 +1,4 @@ +# frozen_string_literal: true module ActionDispatch # :stopdoc: module Journey @@ -175,7 +176,7 @@ module ActionDispatch last_child = node.children.last node.children.inject(seed) { |s, c| string = visit(c, s) - string << "|".freeze unless last_child == c + string << "|" unless last_child == c string } end @@ -185,7 +186,7 @@ module ActionDispatch end def visit_GROUP(node, seed) - visit(node.left, seed << "(".freeze) << ")".freeze + visit(node.left, seed.dup << "(") << ")" end INSTANCE = new diff --git a/actionpack/lib/action_dispatch/middleware/cookies.rb b/actionpack/lib/action_dispatch/middleware/cookies.rb index c0dda1bba5..533925ebe1 100644 --- a/actionpack/lib/action_dispatch/middleware/cookies.rb +++ b/actionpack/lib/action_dispatch/middleware/cookies.rb @@ -432,8 +432,7 @@ module ActionDispatch end end - mattr_accessor :always_write_cookie - self.always_write_cookie = false + mattr_accessor :always_write_cookie, default: false private @@ -631,7 +630,7 @@ module ActionDispatch secret = key_generator.generate_key(request.encrypted_cookie_salt || "")[0, ActiveSupport::MessageEncryptor.key_len] sign_secret = key_generator.generate_key(request.encrypted_signed_cookie_salt || "") - @legacy_encryptor = ActiveSupport::MessageEncryptor.new(secret, sign_secret, digest: digest, serializer: ActiveSupport::MessageEncryptor::NullSerializer) + @legacy_encryptor = ActiveSupport::MessageEncryptor.new(secret, sign_secret, cipher: "aes-256-cbc", digest: digest, serializer: ActiveSupport::MessageEncryptor::NullSerializer) end def decrypt_and_verify_legacy_encrypted_message(name, signed_message) diff --git a/actionpack/lib/action_dispatch/middleware/debug_exceptions.rb b/actionpack/lib/action_dispatch/middleware/debug_exceptions.rb index 336a775880..18852b0a57 100644 --- a/actionpack/lib/action_dispatch/middleware/debug_exceptions.rb +++ b/actionpack/lib/action_dispatch/middleware/debug_exceptions.rb @@ -1,6 +1,7 @@ -require "action_dispatch/http/request" -require "action_dispatch/middleware/exception_wrapper" -require "action_dispatch/routing/inspector" +# frozen_string_literal: true +require_relative "../http/request" +require_relative "exception_wrapper" +require_relative "../routing/inspector" require "action_view" require "action_view/base" @@ -21,7 +22,7 @@ module ActionDispatch if clean_params.empty? "None" else - PP.pp(clean_params, "", 200) + PP.pp(clean_params, "".dup, 200) end end diff --git a/actionpack/lib/action_dispatch/middleware/exception_wrapper.rb b/actionpack/lib/action_dispatch/middleware/exception_wrapper.rb index 397f0a8b92..08b4541d24 100644 --- a/actionpack/lib/action_dispatch/middleware/exception_wrapper.rb +++ b/actionpack/lib/action_dispatch/middleware/exception_wrapper.rb @@ -3,9 +3,7 @@ require "rack/utils" module ActionDispatch class ExceptionWrapper - cattr_accessor :rescue_responses - @@rescue_responses = Hash.new(:internal_server_error) - @@rescue_responses.merge!( + cattr_accessor :rescue_responses, default: Hash.new(:internal_server_error).merge!( "ActionController::RoutingError" => :not_found, "AbstractController::ActionNotFound" => :not_found, "ActionController::MethodNotAllowed" => :method_not_allowed, @@ -21,9 +19,7 @@ module ActionDispatch "Rack::QueryParser::InvalidParameterError" => :bad_request ) - cattr_accessor :rescue_templates - @@rescue_templates = Hash.new("diagnostics") - @@rescue_templates.merge!( + cattr_accessor :rescue_templates, default: Hash.new("diagnostics").merge!( "ActionView::MissingTemplate" => "missing_template", "ActionController::RoutingError" => "routing_error", "AbstractController::ActionNotFound" => "unknown_action", diff --git a/actionpack/lib/action_dispatch/middleware/session/abstract_store.rb b/actionpack/lib/action_dispatch/middleware/session/abstract_store.rb index 21ccf5a097..31979fa576 100644 --- a/actionpack/lib/action_dispatch/middleware/session/abstract_store.rb +++ b/actionpack/lib/action_dispatch/middleware/session/abstract_store.rb @@ -1,8 +1,8 @@ require "rack/utils" require "rack/request" require "rack/session/abstract/id" -require "action_dispatch/middleware/cookies" -require "action_dispatch/request/session" +require_relative "../cookies" +require_relative "../../request/session" module ActionDispatch module Session diff --git a/actionpack/lib/action_dispatch/middleware/session/cache_store.rb b/actionpack/lib/action_dispatch/middleware/session/cache_store.rb index 71274bc13a..4babeb6354 100644 --- a/actionpack/lib/action_dispatch/middleware/session/cache_store.rb +++ b/actionpack/lib/action_dispatch/middleware/session/cache_store.rb @@ -1,4 +1,4 @@ -require "action_dispatch/middleware/session/abstract_store" +require_relative "abstract_store" module ActionDispatch module Session diff --git a/actionpack/lib/action_dispatch/middleware/session/cookie_store.rb b/actionpack/lib/action_dispatch/middleware/session/cookie_store.rb index 57d325a9d8..496f221617 100644 --- a/actionpack/lib/action_dispatch/middleware/session/cookie_store.rb +++ b/actionpack/lib/action_dispatch/middleware/session/cookie_store.rb @@ -1,5 +1,5 @@ require "active_support/core_ext/hash/keys" -require "action_dispatch/middleware/session/abstract_store" +require_relative "abstract_store" require "rack/session/cookie" module ActionDispatch diff --git a/actionpack/lib/action_dispatch/middleware/session/mem_cache_store.rb b/actionpack/lib/action_dispatch/middleware/session/mem_cache_store.rb index ee2b1f26ad..bc2b1c9b12 100644 --- a/actionpack/lib/action_dispatch/middleware/session/mem_cache_store.rb +++ b/actionpack/lib/action_dispatch/middleware/session/mem_cache_store.rb @@ -1,4 +1,4 @@ -require "action_dispatch/middleware/session/abstract_store" +require_relative "abstract_store" begin require "rack/session/dalli" rescue LoadError => e diff --git a/actionpack/lib/action_dispatch/middleware/show_exceptions.rb b/actionpack/lib/action_dispatch/middleware/show_exceptions.rb index 5a99714ec2..db84ff48e9 100644 --- a/actionpack/lib/action_dispatch/middleware/show_exceptions.rb +++ b/actionpack/lib/action_dispatch/middleware/show_exceptions.rb @@ -1,5 +1,5 @@ -require "action_dispatch/http/request" -require "action_dispatch/middleware/exception_wrapper" +require_relative "../http/request" +require_relative "exception_wrapper" module ActionDispatch # This middleware rescues any exception returned by the application diff --git a/actionpack/lib/action_dispatch/middleware/ssl.rb b/actionpack/lib/action_dispatch/middleware/ssl.rb index 557721c301..e79404c993 100644 --- a/actionpack/lib/action_dispatch/middleware/ssl.rb +++ b/actionpack/lib/action_dispatch/middleware/ssl.rb @@ -1,3 +1,4 @@ +# frozen_string_literal: true module ActionDispatch # This middleware is added to the stack when `config.force_ssl = true`, and is passed # the options set in `config.ssl_options`. It does three jobs to enforce secure HTTP @@ -94,7 +95,7 @@ module ActionDispatch # http://tools.ietf.org/html/rfc6797#section-6.1 def build_hsts_header(hsts) - value = "max-age=#{hsts[:expires].to_i}" + value = "max-age=#{hsts[:expires].to_i}".dup value << "; includeSubDomains" if hsts[:subdomains] value << "; preload" if hsts[:preload] value @@ -133,7 +134,7 @@ module ActionDispatch host = @redirect[:host] || request.host port = @redirect[:port] || request.port - location = "https://#{host}" + location = "https://#{host}".dup location << ":#{port}" if port != 80 && port != 443 location << request.fullpath location diff --git a/actionpack/lib/action_dispatch/middleware/static.rb b/actionpack/lib/action_dispatch/middleware/static.rb index 5d10129d21..6f4a97da3e 100644 --- a/actionpack/lib/action_dispatch/middleware/static.rb +++ b/actionpack/lib/action_dispatch/middleware/static.rb @@ -1,3 +1,4 @@ +# frozen_string_literal: true require "rack/utils" require "active_support/core_ext/uri" @@ -6,11 +7,11 @@ module ActionDispatch # When initialized, it can accept optional HTTP headers, which will be set # when a response containing a file's contents is delivered. # - # This middleware will render the file specified in `env["PATH_INFO"]` + # This middleware will render the file specified in <tt>env["PATH_INFO"]</tt> # where the base path is in the +root+ directory. For example, if the +root+ - # is set to `public/`, then a request with `env["PATH_INFO"]` of - # `assets/application.js` will return a response with the contents of a file - # located at `public/assets/application.js` if the file exists. If the file + # is set to +public/+, then a request with <tt>env["PATH_INFO"]</tt> of + # +assets/application.js+ will return a response with the contents of a file + # located at +public/assets/application.js+ if the file exists. If the file # does not exist, a 404 "File not Found" response will be returned. class FileHandler def initialize(root, index: "index", headers: {}) @@ -23,8 +24,8 @@ module ActionDispatch # correct read permissions, the return value is a URI-escaped string # representing the filename. Otherwise, false is returned. # - # Used by the `Static` class to check the existence of a valid file - # in the server's `public/` directory (see Static#call). + # Used by the +Static+ class to check the existence of a valid file + # in the server's +public/+ directory (see Static#call). def match?(path) path = ::Rack::Utils.unescape_path path return false unless ::Rack::Utils.valid_path? path @@ -33,7 +34,7 @@ module ActionDispatch paths = [path, "#{path}#{ext}", "#{path}/#{@index}#{ext}"] if match = paths.detect { |p| - path = File.join(@root, p.force_encoding(Encoding::UTF_8)) + path = File.join(@root, p.dup.force_encoding(Encoding::UTF_8)) begin File.file?(path) && File.readable?(path) rescue SystemCallError @@ -99,7 +100,7 @@ module ActionDispatch # This middleware will attempt to return the contents of a file's body from # disk in the response. If a file is not found on disk, the request will be # delegated to the application stack. This middleware is commonly initialized - # to serve assets from a server's `public/` directory. + # to serve assets from a server's +public/+ directory. # # This middleware verifies the path to ensure that only files # living in the root directory can be rendered. A request cannot diff --git a/actionpack/lib/action_dispatch/request/utils.rb b/actionpack/lib/action_dispatch/request/utils.rb index 3615e4b1d8..4f79c4c21e 100644 --- a/actionpack/lib/action_dispatch/request/utils.rb +++ b/actionpack/lib/action_dispatch/request/utils.rb @@ -1,8 +1,7 @@ module ActionDispatch class Request class Utils # :nodoc: - mattr_accessor :perform_deep_munge - self.perform_deep_munge = true + mattr_accessor :perform_deep_munge, default: true def self.each_param_value(params, &block) case params diff --git a/actionpack/lib/action_dispatch/routing/mapper.rb b/actionpack/lib/action_dispatch/routing/mapper.rb index 74904e3d45..057ff07fcf 100644 --- a/actionpack/lib/action_dispatch/routing/mapper.rb +++ b/actionpack/lib/action_dispatch/routing/mapper.rb @@ -1,9 +1,10 @@ +# frozen_string_literal: true require "active_support/core_ext/hash/slice" require "active_support/core_ext/enumerable" require "active_support/core_ext/array/extract_options" require "active_support/core_ext/regexp" -require "action_dispatch/routing/redirection" -require "action_dispatch/routing/endpoint" +require_relative "redirection" +require_relative "endpoint" module ActionDispatch module Routing @@ -306,7 +307,7 @@ module ActionDispatch def check_controller_and_action(path_params, controller, action) hash = check_part(:controller, controller, path_params, {}) do |part| translate_controller(part) { - message = "'#{part}' is not a supported controller name. This can lead to potential routing problems." + message = "'#{part}' is not a supported controller name. This can lead to potential routing problems.".dup message << " See http://guides.rubyonrails.org/routing.html#specifying-a-controller-to-use" raise ArgumentError, message @@ -652,18 +653,25 @@ module ActionDispatch def define_generate_prefix(app, name) _route = @set.named_routes.get name _routes = @set - app.routes.define_mounted_helper(name) + + script_namer = ->(options) do + prefix_options = options.slice(*_route.segment_keys) + prefix_options[:relative_url_root] = "".freeze + # We must actually delete prefix segment keys to avoid passing them to next url_for. + _route.segment_keys.each { |k| options.delete(k) } + _routes.url_helpers.send("#{name}_path", prefix_options) + end + + app.routes.define_mounted_helper(name, script_namer) + app.routes.extend Module.new { def optimize_routes_generation?; false; end + define_method :find_script_name do |options| if options.key? :script_name super(options) else - prefix_options = options.slice(*_route.segment_keys) - prefix_options[:relative_url_root] = "".freeze - # We must actually delete prefix segment keys to avoid passing them to next url_for. - _route.segment_keys.each { |k| options.delete(k) } - _routes.url_helpers.send("#{name}_path", prefix_options) + script_namer.call(options) end end } @@ -1837,7 +1845,7 @@ module ActionDispatch path_types.fetch(String, []).each do |_path| route_options = options.dup if _path && option_path - raise ArgumentError, "Ambigous route definition. Both :path and the route path where specified as strings." + raise ArgumentError, "Ambiguous route definition. Both :path and the route path where specified as strings." end to = get_to_from_path(_path, to, route_options[:action]) decomposed_match(_path, controller, route_options, _path, to, via, formatted, anchor, options_constraints) @@ -2038,8 +2046,8 @@ module ActionDispatch # { controller: "pages", action: "index", subdomain: "www" } # end # - # The return value from the block passed to `direct` must be a valid set of - # arguments for `url_for` which will actually build the URL string. This can + # The return value from the block passed to +direct+ must be a valid set of + # arguments for +url_for+ which will actually build the URL string. This can # be one of the following: # # * A string, which is treated as a generated URL @@ -2058,17 +2066,17 @@ module ActionDispatch # [ :products, options.merge(params.permit(:page, :size).to_h.symbolize_keys) ] # end # - # In this instance the `params` object comes from the context in which the the + # In this instance the +params+ object comes from the context in which the the # block is executed, e.g. generating a URL inside a controller action or a view. # If the block is executed where there isn't a params object such as this: # # Rails.application.routes.url_helpers.browse_path # - # then it will raise a `NameError`. Because of this you need to be aware of the + # then it will raise a +NameError+. Because of this you need to be aware of the # context in which you will use your custom URL helper when defining it. # - # NOTE: The `direct` method can't be used inside of a scope block such as - # `namespace` or `scope` and will raise an error if it detects that it is. + # NOTE: The +direct+ method can't be used inside of a scope block such as + # +namespace+ or +scope+ and will raise an error if it detects that it is. def direct(name, options = {}, &block) unless @scope.root? raise RuntimeError, "The direct method can't be used inside a routes scope block" @@ -2078,8 +2086,8 @@ module ActionDispatch end # Define custom polymorphic mappings of models to URLs. This alters the - # behavior of `polymorphic_url` and consequently the behavior of - # `link_to` and `form_for` when passed a model instance, e.g: + # behavior of +polymorphic_url+ and consequently the behavior of + # +link_to+ and +form_for+ when passed a model instance, e.g: # # resource :basket # @@ -2087,8 +2095,8 @@ module ActionDispatch # [:basket] # end # - # This will now generate "/basket" when a `Basket` instance is passed to - # `link_to` or `form_for` instead of the standard "/baskets/:id". + # This will now generate "/basket" when a +Basket+ instance is passed to + # +link_to+ or +form_for+ instead of the standard "/baskets/:id". # # NOTE: This custom behavior only applies to simple polymorphic URLs where # a single model instance is passed and not more complicated forms, e.g: @@ -2105,7 +2113,7 @@ module ActionDispatch # link_to "Profile", @current_user # link_to "Profile", [:admin, @current_user] # - # The first `link_to` will generate "/profile" but the second will generate + # The first +link_to+ will generate "/profile" but the second will generate # the standard polymorphic URL of "/admin/users/1". # # You can pass options to a polymorphic mapping - the arity for the block @@ -2116,11 +2124,11 @@ module ActionDispatch # end # # This generates the URL "/basket#items" because when the last item in an - # array passed to `polymorphic_url` is a hash then it's treated as options + # array passed to +polymorphic_url+ is a hash then it's treated as options # to the URL helper that gets called. # - # NOTE: The `resolve` method can't be used inside of a scope block such as - # `namespace` or `scope` and will raise an error if it detects that it is. + # NOTE: The +resolve+ method can't be used inside of a scope block such as + # +namespace+ or +scope+ and will raise an error if it detects that it is. def resolve(*args, &block) unless @scope.root? raise RuntimeError, "The resolve method can't be used inside a routes scope block" diff --git a/actionpack/lib/action_dispatch/routing/redirection.rb b/actionpack/lib/action_dispatch/routing/redirection.rb index 3bcb341758..6396b5031d 100644 --- a/actionpack/lib/action_dispatch/routing/redirection.rb +++ b/actionpack/lib/action_dispatch/routing/redirection.rb @@ -1,9 +1,9 @@ -require "action_dispatch/http/request" +require_relative "../http/request" require "active_support/core_ext/uri" require "active_support/core_ext/array/extract_options" require "rack/utils" require "action_controller/metal/exceptions" -require "action_dispatch/routing/endpoint" +require_relative "endpoint" module ActionDispatch module Routing diff --git a/actionpack/lib/action_dispatch/routing/route_set.rb b/actionpack/lib/action_dispatch/routing/route_set.rb index e1f9fc9ecc..3f15257ed6 100644 --- a/actionpack/lib/action_dispatch/routing/route_set.rb +++ b/actionpack/lib/action_dispatch/routing/route_set.rb @@ -1,11 +1,12 @@ -require "action_dispatch/journey" +# frozen_string_literal: true +require_relative "../journey" require "active_support/core_ext/object/to_query" require "active_support/core_ext/hash/slice" require "active_support/core_ext/module/remove_method" require "active_support/core_ext/array/extract_options" require "action_controller/metal/exceptions" -require "action_dispatch/http/request" -require "action_dispatch/routing/endpoint" +require_relative "../http/request" +require_relative "endpoint" module ActionDispatch module Routing @@ -73,7 +74,6 @@ module ActionDispatch @routes = {} @path_helpers = Set.new @url_helpers = Set.new - @custom_helpers = Set.new @url_helpers_module = Module.new @path_helpers_module = Module.new end @@ -96,23 +96,9 @@ module ActionDispatch @url_helpers_module.send :remove_method, helper end - @custom_helpers.each do |helper| - path_name = :"#{helper}_path" - url_name = :"#{helper}_url" - - if @path_helpers_module.method_defined?(path_name) - @path_helpers_module.send :remove_method, path_name - end - - if @url_helpers_module.method_defined?(url_name) - @url_helpers_module.send :remove_method, url_name - end - end - @routes.clear @path_helpers.clear @url_helpers.clear - @custom_helpers.clear end def add(name, route) @@ -158,21 +144,29 @@ module ActionDispatch routes.length end + # Given a +name+, defines name_path and name_url helpers. + # Used by 'direct', 'resolve', and 'polymorphic' route helpers. def add_url_helper(name, defaults, &block) - @custom_helpers << name helper = CustomUrlHelper.new(name, defaults, &block) + path_name = :"#{name}_path" + url_name = :"#{name}_url" @path_helpers_module.module_eval do - define_method(:"#{name}_path") do |*args| + define_method(path_name) do |*args| helper.call(self, args, true) end end @url_helpers_module.module_eval do - define_method(:"#{name}_url") do |*args| + define_method(url_name) do |*args| helper.call(self, args, false) end end + + @path_helpers << path_name + @url_helpers << url_name + + self end class UrlHelper @@ -240,7 +234,7 @@ module ActionDispatch missing_keys << missing_key } constraints = Hash[@route.requirements.merge(params).sort_by { |k, v| k.to_s }] - message = "No route matches #{constraints.inspect}" + message = "No route matches #{constraints.inspect}".dup message << ", missing required keys: #{missing_keys.sort.inspect}" raise ActionController::UrlGenerationError, message @@ -279,6 +273,8 @@ module ActionDispatch if args.size < path_params_size path_params -= controller_options.keys path_params -= result.keys + else + path_params = path_params.dup end inner_options.each_key do |key| path_params.delete(key) @@ -454,7 +450,7 @@ module ActionDispatch MountedHelpers end - def define_mounted_helper(name) + def define_mounted_helper(name, script_namer = nil) return if MountedHelpers.method_defined?(name) routes = self @@ -462,7 +458,7 @@ module ActionDispatch MountedHelpers.class_eval do define_method "_#{name}" do - RoutesProxy.new(routes, _routes_context, helpers) + RoutesProxy.new(routes, _routes_context, helpers, script_namer) end end diff --git a/actionpack/lib/action_dispatch/routing/routes_proxy.rb b/actionpack/lib/action_dispatch/routing/routes_proxy.rb index c1423f770f..7a6c2e95d8 100644 --- a/actionpack/lib/action_dispatch/routing/routes_proxy.rb +++ b/actionpack/lib/action_dispatch/routing/routes_proxy.rb @@ -8,9 +8,10 @@ module ActionDispatch attr_accessor :scope, :routes alias :_routes :routes - def initialize(routes, scope, helpers) + def initialize(routes, scope, helpers, script_namer = nil) @routes, @scope = routes, scope @helpers = helpers + @script_namer = script_namer end def url_options @@ -29,7 +30,9 @@ module ActionDispatch self.class.class_eval <<-RUBY, __FILE__, __LINE__ + 1 def #{method}(*args) options = args.extract_options! - args << url_options.merge((options || {}).symbolize_keys) + options = url_options.merge((options || {}).symbolize_keys) + options.reverse_merge!(script_name: @script_namer.call(options)) if @script_namer + args << options @helpers.#{method}(*args) end RUBY diff --git a/actionpack/lib/action_dispatch/system_test_case.rb b/actionpack/lib/action_dispatch/system_test_case.rb index 98fdb36c91..23ce8d5a92 100644 --- a/actionpack/lib/action_dispatch/system_test_case.rb +++ b/actionpack/lib/action_dispatch/system_test_case.rb @@ -1,10 +1,11 @@ require "capybara/dsl" require "capybara/minitest" require "action_controller" -require "action_dispatch/system_testing/driver" -require "action_dispatch/system_testing/server" -require "action_dispatch/system_testing/test_helpers/screenshot_helper" -require "action_dispatch/system_testing/test_helpers/setup_and_teardown" +require_relative "system_testing/driver" +require_relative "system_testing/server" +require_relative "system_testing/test_helpers/screenshot_helper" +require_relative "system_testing/test_helpers/setup_and_teardown" +require_relative "system_testing/test_helpers/undef_methods" module ActionDispatch # = System Testing @@ -66,14 +67,18 @@ module ActionDispatch # # To use a headless driver, like Poltergeist, update your Gemfile to use # Poltergeist instead of Selenium and then declare the driver name in the - # +application_system_test_case.rb+ file. In this case you would leave out the +:using+ - # option because the driver is headless. + # +application_system_test_case.rb+ file. In this case, you would leave out + # the +:using+ option because the driver is headless, but you can still use + # +:screen_size+ to change the size of the browser screen, also you can use + # +:options+ to pass options supported by the driver. Please refer to your + # driver documentation to learn about supported options. # # require "test_helper" # require "capybara/poltergeist" # # class ApplicationSystemTestCase < ActionDispatch::SystemTestCase - # driven_by :poltergeist + # driven_by :poltergeist, screen_size: [1400, 1400], options: + # { js_errors: true } # end # # Because <tt>ActionDispatch::SystemTestCase</tt> is a shim between Capybara @@ -84,6 +89,7 @@ module ActionDispatch include Capybara::Minitest::Assertions include SystemTesting::TestHelpers::SetupAndTeardown include SystemTesting::TestHelpers::ScreenshotHelper + include SystemTesting::TestHelpers::UndefMethods def initialize(*) # :nodoc: super diff --git a/actionpack/lib/action_dispatch/system_testing/driver.rb b/actionpack/lib/action_dispatch/system_testing/driver.rb index 5cf17883f7..81e6f0fc80 100644 --- a/actionpack/lib/action_dispatch/system_testing/driver.rb +++ b/actionpack/lib/action_dispatch/system_testing/driver.rb @@ -9,23 +9,42 @@ module ActionDispatch end def use - register if selenium? + register if registerable? + setup end private - def selenium? - @name == :selenium + def registerable? + [:selenium, :poltergeist, :webkit].include?(@name) end def register Capybara.register_driver @name do |app| - Capybara::Selenium::Driver.new(app, { browser: @browser }.merge(@options)).tap do |driver| - driver.browser.manage.window.size = Selenium::WebDriver::Dimension.new(*@screen_size) + case @name + when :selenium then register_selenium(app) + when :poltergeist then register_poltergeist(app) + when :webkit then register_webkit(app) end end end + def register_selenium(app) + Capybara::Selenium::Driver.new(app, { browser: @browser }.merge(@options)).tap do |driver| + driver.browser.manage.window.size = Selenium::WebDriver::Dimension.new(*@screen_size) + end + end + + def register_poltergeist(app) + Capybara::Poltergeist::Driver.new(app, @options.merge(window_size: @screen_size)) + end + + def register_webkit(app) + Capybara::Webkit::Driver.new(app, Capybara::Webkit::Configuration.to_hash.merge(@options)).tap do |driver| + driver.resize_window(*@screen_size) + end + end + def setup Capybara.current_driver = @name end diff --git a/actionpack/lib/action_dispatch/system_testing/server.rb b/actionpack/lib/action_dispatch/system_testing/server.rb index 4a214ef713..89ca6944d9 100644 --- a/actionpack/lib/action_dispatch/system_testing/server.rb +++ b/actionpack/lib/action_dispatch/system_testing/server.rb @@ -3,6 +3,12 @@ require "rack/handler/puma" module ActionDispatch module SystemTesting class Server # :nodoc: + class << self + attr_accessor :silence_puma + end + + self.silence_puma = false + def run register setup @@ -11,7 +17,12 @@ module ActionDispatch private def register Capybara.register_server :rails_puma do |app, port, host| - Rack::Handler::Puma.run(app, Port: port, Threads: "0:1") + Rack::Handler::Puma.run( + app, + Port: port, + Threads: "0:1", + Silent: self.class.silence_puma + ) end end diff --git a/actionpack/lib/action_dispatch/system_testing/test_helpers/undef_methods.rb b/actionpack/lib/action_dispatch/system_testing/test_helpers/undef_methods.rb new file mode 100644 index 0000000000..2d3f4662d7 --- /dev/null +++ b/actionpack/lib/action_dispatch/system_testing/test_helpers/undef_methods.rb @@ -0,0 +1,24 @@ +module ActionDispatch + module SystemTesting + module TestHelpers + module UndefMethods # :nodoc: + extend ActiveSupport::Concern + included do + METHODS = %i(get post put patch delete).freeze + + METHODS.each do |verb| + undef_method verb + end + + def method_missing(method, *args, &block) + if METHODS.include?(method) + raise NoMethodError + else + super + end + end + end + end + end + end +end diff --git a/actionpack/lib/action_dispatch/testing/assertions/response.rb b/actionpack/lib/action_dispatch/testing/assertions/response.rb index 1baf979ac9..749f2eab57 100644 --- a/actionpack/lib/action_dispatch/testing/assertions/response.rb +++ b/actionpack/lib/action_dispatch/testing/assertions/response.rb @@ -79,7 +79,7 @@ module ActionDispatch def generate_response_message(expected, actual = @response.response_code) "Expected response to be a <#{code_with_name(expected)}>,"\ " but was a <#{code_with_name(actual)}>" - .concat(location_if_redirected).concat(response_body_if_short) + .dup.concat(location_if_redirected).concat(response_body_if_short) end def response_body_if_short diff --git a/actionpack/lib/action_dispatch/testing/integration.rb b/actionpack/lib/action_dispatch/testing/integration.rb index 2416c58817..beba4e3c36 100644 --- a/actionpack/lib/action_dispatch/testing/integration.rb +++ b/actionpack/lib/action_dispatch/testing/integration.rb @@ -5,7 +5,7 @@ require "active_support/core_ext/object/try" require "rack/test" require "minitest" -require "action_dispatch/testing/request_encoder" +require_relative "request_encoder" module ActionDispatch module Integration #:nodoc: @@ -338,8 +338,7 @@ module ActionDispatch @integration_session = nil end - %w(get post patch put head delete cookies assigns - xml_http_request xhr get_via_redirect post_via_redirect).each do |method| + %w(get post patch put head delete cookies assigns follow_redirect!).each do |method| define_method(method) do |*args| # reset the html_document variable, except for cookies/assigns calls unless method == "cookies" || method == "assigns" diff --git a/actionpack/lib/action_dispatch/testing/test_process.rb b/actionpack/lib/action_dispatch/testing/test_process.rb index 0282eb15c3..8061ac2e3b 100644 --- a/actionpack/lib/action_dispatch/testing/test_process.rb +++ b/actionpack/lib/action_dispatch/testing/test_process.rb @@ -1,5 +1,5 @@ -require "action_dispatch/middleware/cookies" -require "action_dispatch/middleware/flash" +require_relative "../middleware/cookies" +require_relative "../middleware/flash" module ActionDispatch module TestProcess diff --git a/actionpack/lib/action_dispatch/testing/test_response.rb b/actionpack/lib/action_dispatch/testing/test_response.rb index 5c89f9c75e..2a1a9ffce9 100644 --- a/actionpack/lib/action_dispatch/testing/test_response.rb +++ b/actionpack/lib/action_dispatch/testing/test_response.rb @@ -1,4 +1,4 @@ -require "action_dispatch/testing/request_encoder" +require_relative "request_encoder" module ActionDispatch # Integration test methods such as ActionDispatch::Integration::Session#get diff --git a/actionpack/lib/action_pack.rb b/actionpack/lib/action_pack.rb index eec622e085..6a74baff09 100644 --- a/actionpack/lib/action_pack.rb +++ b/actionpack/lib/action_pack.rb @@ -21,4 +21,4 @@ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. #++ -require "action_pack/version" +require_relative "action_pack/version" |