diff options
Diffstat (limited to 'actionpack/test')
39 files changed, 521 insertions, 193 deletions
diff --git a/actionpack/test/abstract/callbacks_test.rb b/actionpack/test/abstract/callbacks_test.rb index fdc09bd951..4512ea27b3 100644 --- a/actionpack/test/abstract/callbacks_test.rb +++ b/actionpack/test/abstract/callbacks_test.rb @@ -154,7 +154,7 @@ module AbstractController test "when :except is specified, an after action is not triggered on that action" do @controller.process(:index) - assert !@controller.instance_variable_defined?("@authenticated") + assert_not @controller.instance_variable_defined?("@authenticated") end end @@ -198,7 +198,7 @@ module AbstractController test "when :except is specified with an array, an after action is not triggered on that action" do @controller.process(:index) - assert !@controller.instance_variable_defined?("@authenticated") + assert_not @controller.instance_variable_defined?("@authenticated") end end diff --git a/actionpack/test/controller/action_pack_assertions_test.rb b/actionpack/test/controller/action_pack_assertions_test.rb index 504c77b8ef..763df3a776 100644 --- a/actionpack/test/controller/action_pack_assertions_test.rb +++ b/actionpack/test/controller/action_pack_assertions_test.rb @@ -290,13 +290,13 @@ class ActionPackAssertionsControllerTest < ActionController::TestCase def test_template_objects_exist process :assign_this - assert !@controller.instance_variable_defined?(:"@hi") + assert_not @controller.instance_variable_defined?(:"@hi") assert @controller.instance_variable_get(:"@howdy") end def test_template_objects_missing process :nothing - assert !@controller.instance_variable_defined?(:@howdy) + assert_not @controller.instance_variable_defined?(:@howdy) end def test_empty_flash @@ -366,7 +366,7 @@ class ActionPackAssertionsControllerTest < ActionController::TestCase process :redirect_external assert_predicate @response, :redirect? assert_match(/rubyonrails/, @response.redirect_url) - assert !/perloffrails/.match(@response.redirect_url) + assert_no_match(/perloffrails/, @response.redirect_url) end def test_redirection diff --git a/actionpack/test/controller/api/force_ssl_test.rb b/actionpack/test/controller/api/force_ssl_test.rb index 07459c3753..8191578eb0 100644 --- a/actionpack/test/controller/api/force_ssl_test.rb +++ b/actionpack/test/controller/api/force_ssl_test.rb @@ -3,7 +3,9 @@ require "abstract_unit" class ForceSSLApiController < ActionController::API - force_ssl + ActiveSupport::Deprecation.silence do + force_ssl + end def one; end def two diff --git a/actionpack/test/controller/caching_test.rb b/actionpack/test/controller/caching_test.rb index 8b596083d5..6fe036dd15 100644 --- a/actionpack/test/controller/caching_test.rb +++ b/actionpack/test/controller/caching_test.rb @@ -94,14 +94,14 @@ class FragmentCachingTest < ActionController::TestCase def test_fragment_exist_with_caching_enabled @store.write("views/name", "value") assert @controller.fragment_exist?("name") - assert !@controller.fragment_exist?("other_name") + assert_not @controller.fragment_exist?("other_name") end def test_fragment_exist_with_caching_disabled @controller.perform_caching = false @store.write("views/name", "value") - assert !@controller.fragment_exist?("name") - assert !@controller.fragment_exist?("other_name") + assert_not @controller.fragment_exist?("name") + assert_not @controller.fragment_exist?("other_name") end def test_write_fragment_with_caching_enabled @@ -144,7 +144,7 @@ class FragmentCachingTest < ActionController::TestCase buffer = "generated till now -> ".html_safe buffer << view_context.send(:fragment_for, "expensive") { fragment_computed = true } - assert !fragment_computed + assert_not fragment_computed assert_equal "generated till now -> fragment content", buffer end @@ -173,6 +173,9 @@ class FunctionalCachingController < CachingController end end + def xml_fragment_cached_with_html_partial + end + def formatted_fragment_cached respond_to do |format| format.html @@ -308,6 +311,11 @@ CACHED @store.read("views/functional_caching/formatted_fragment_cached_with_variant:#{template_digest("functional_caching/formatted_fragment_cached_with_variant")}/fragment") end + def test_fragment_caching_with_html_partials_in_xml + get :xml_fragment_cached_with_html_partial, format: "*/*" + assert_response :success + end + private def template_digest(name) ActionView::Digestor.digest(name: name, finder: @controller.lookup_context) diff --git a/actionpack/test/controller/filters_test.rb b/actionpack/test/controller/filters_test.rb index 2b16a555bb..425a6e25cc 100644 --- a/actionpack/test/controller/filters_test.rb +++ b/actionpack/test/controller/filters_test.rb @@ -787,7 +787,7 @@ class FilterTest < ActionController::TestCase assert_equal %w( ensure_login find_user ), @controller.instance_variable_get(:@ran_filter) test_process(ConditionalSkippingController, "login") - assert !@controller.instance_variable_defined?("@ran_after_action") + assert_not @controller.instance_variable_defined?("@ran_after_action") test_process(ConditionalSkippingController, "change_password") assert_equal %w( clean_up ), @controller.instance_variable_get("@ran_after_action") end diff --git a/actionpack/test/controller/flash_hash_test.rb b/actionpack/test/controller/flash_hash_test.rb index 6c3ac26de1..e3ec5bb7fc 100644 --- a/actionpack/test/controller/flash_hash_test.rb +++ b/actionpack/test/controller/flash_hash_test.rb @@ -44,7 +44,7 @@ module ActionDispatch @hash["foo"] = "bar" @hash.delete "foo" - assert !@hash.key?("foo") + assert_not @hash.key?("foo") assert_nil @hash["foo"] end @@ -53,7 +53,7 @@ module ActionDispatch assert_equal({ "foo" => "bar" }, @hash.to_hash) @hash.to_hash["zomg"] = "aaron" - assert !@hash.key?("zomg") + assert_not @hash.key?("zomg") assert_equal({ "foo" => "bar" }, @hash.to_hash) end diff --git a/actionpack/test/controller/force_ssl_test.rb b/actionpack/test/controller/force_ssl_test.rb index 84ac1fda3c..7f59f6acaf 100644 --- a/actionpack/test/controller/force_ssl_test.rb +++ b/actionpack/test/controller/force_ssl_test.rb @@ -13,19 +13,23 @@ class ForceSSLController < ActionController::Base end class ForceSSLControllerLevel < ForceSSLController - force_ssl + ActiveSupport::Deprecation.silence do + force_ssl + end end class ForceSSLCustomOptions < ForceSSLController - force_ssl host: "secure.example.com", only: :redirect_host - force_ssl port: 8443, only: :redirect_port - force_ssl subdomain: "secure", only: :redirect_subdomain - force_ssl domain: "secure.com", only: :redirect_domain - force_ssl path: "/foo", only: :redirect_path - force_ssl status: :found, only: :redirect_status - force_ssl flash: { message: "Foo, Bar!" }, only: :redirect_flash - force_ssl alert: "Foo, Bar!", only: :redirect_alert - force_ssl notice: "Foo, Bar!", only: :redirect_notice + ActiveSupport::Deprecation.silence do + force_ssl host: "secure.example.com", only: :redirect_host + force_ssl port: 8443, only: :redirect_port + force_ssl subdomain: "secure", only: :redirect_subdomain + force_ssl domain: "secure.com", only: :redirect_domain + force_ssl path: "/foo", only: :redirect_path + force_ssl status: :found, only: :redirect_status + force_ssl flash: { message: "Foo, Bar!" }, only: :redirect_flash + force_ssl alert: "Foo, Bar!", only: :redirect_alert + force_ssl notice: "Foo, Bar!", only: :redirect_notice + end def force_ssl_action render plain: action_name @@ -55,15 +59,21 @@ class ForceSSLCustomOptions < ForceSSLController end class ForceSSLOnlyAction < ForceSSLController - force_ssl only: :cheeseburger + ActiveSupport::Deprecation.silence do + force_ssl only: :cheeseburger + end end class ForceSSLExceptAction < ForceSSLController - force_ssl except: :banana + ActiveSupport::Deprecation.silence do + force_ssl except: :banana + end end class ForceSSLIfCondition < ForceSSLController - force_ssl if: :use_force_ssl? + ActiveSupport::Deprecation.silence do + force_ssl if: :use_force_ssl? + end def use_force_ssl? action_name == "cheeseburger" @@ -71,7 +81,9 @@ class ForceSSLIfCondition < ForceSSLController end class ForceSSLFlash < ForceSSLController - force_ssl except: [:banana, :set_flash, :use_flash] + ActiveSupport::Deprecation.silence do + force_ssl except: [:banana, :set_flash, :use_flash] + end def set_flash flash["that"] = "hello" diff --git a/actionpack/test/controller/http_digest_authentication_test.rb b/actionpack/test/controller/http_digest_authentication_test.rb index 76ff784926..3f211cd60d 100644 --- a/actionpack/test/controller/http_digest_authentication_test.rb +++ b/actionpack/test/controller/http_digest_authentication_test.rb @@ -9,7 +9,7 @@ class HttpDigestAuthenticationTest < ActionController::TestCase before_action :authenticate_with_request, only: :display USERS = { "lifo" => "world", "pretty" => "please", - "dhh" => ::Digest::MD5::hexdigest(["dhh", "SuperSecret", "secret"].join(":")) } + "dhh" => ::Digest::MD5.hexdigest(["dhh", "SuperSecret", "secret"].join(":")) } def index render plain: "Hello Secret" @@ -181,9 +181,10 @@ class HttpDigestAuthenticationTest < ActionController::TestCase end test "authentication request with password stored as ha1 digest hash" do - @request.env["HTTP_AUTHORIZATION"] = encode_credentials(username: "dhh", - password: ::Digest::MD5::hexdigest(["dhh", "SuperSecret", "secret"].join(":")), - password_is_ha1: true) + @request.env["HTTP_AUTHORIZATION"] = encode_credentials( + username: "dhh", + password: ::Digest::MD5.hexdigest(["dhh", "SuperSecret", "secret"].join(":")), + password_is_ha1: true) get :display assert_response :success @@ -201,7 +202,7 @@ class HttpDigestAuthenticationTest < ActionController::TestCase test "validate_digest_response should fail with nil returning password_procedure" do @request.env["HTTP_AUTHORIZATION"] = encode_credentials(username: nil, password: nil) - assert !ActionController::HttpAuthentication::Digest.validate_digest_response(@request, "SuperSecret") { nil } + assert_not ActionController::HttpAuthentication::Digest.validate_digest_response(@request, "SuperSecret") { nil } end test "authentication request with request-uri ending in '/'" do diff --git a/actionpack/test/controller/integration_test.rb b/actionpack/test/controller/integration_test.rb index a685f5868e..9cdf04b886 100644 --- a/actionpack/test/controller/integration_test.rb +++ b/actionpack/test/controller/integration_test.rb @@ -135,7 +135,7 @@ class IntegrationTestTest < ActiveSupport::TestCase session1 = @test.open_session { |sess| } session2 = @test.open_session # implicit session - assert !session1.equal?(session2) + assert_not session1.equal?(session2) end # RSpec mixes Matchers (which has a #method_missing) into @@ -345,7 +345,7 @@ class IntegrationProcessTest < ActionDispatch::IntegrationTest follow_redirect! assert_response :ok - refute_same previous_html_document, html_document + assert_not_same previous_html_document, html_document end end @@ -375,7 +375,7 @@ class IntegrationProcessTest < ActionDispatch::IntegrationTest a = open_session b = open_session - refute_same(a.integration_session, b.integration_session) + assert_not_same(a.integration_session, b.integration_session) end def test_get_with_query_string diff --git a/actionpack/test/controller/mime/respond_to_test.rb b/actionpack/test/controller/mime/respond_to_test.rb index f9ffd5f54c..771eccb29b 100644 --- a/actionpack/test/controller/mime/respond_to_test.rb +++ b/actionpack/test/controller/mime/respond_to_test.rb @@ -658,13 +658,13 @@ class RespondToControllerTest < ActionController::TestCase end def test_variant_without_implicit_rendering_from_browser - assert_raises(ActionController::UnknownFormat) do + assert_raises(ActionController::MissingExactTemplate) do get :variant_without_implicit_template_rendering, params: { v: :does_not_matter } end end def test_variant_variant_not_set_and_without_implicit_rendering_from_browser - assert_raises(ActionController::UnknownFormat) do + assert_raises(ActionController::MissingExactTemplate) do get :variant_without_implicit_template_rendering end end diff --git a/actionpack/test/controller/parameters/accessors_test.rb b/actionpack/test/controller/parameters/accessors_test.rb index 7bcf8c380d..674b2c6266 100644 --- a/actionpack/test/controller/parameters/accessors_test.rb +++ b/actionpack/test/controller/parameters/accessors_test.rb @@ -2,7 +2,6 @@ require "abstract_unit" require "action_controller/metal/strong_parameters" -require "active_support/core_ext/hash/transform_values" class ParametersAccessorsTest < ActiveSupport::TestCase setup do @@ -273,23 +272,24 @@ class ParametersAccessorsTest < ActiveSupport::TestCase assert_match(/permitted: true/, @params.inspect) end - if Hash.method_defined?(:dig) - test "#dig delegates the dig method to its values" do - assert_equal "David", @params.dig(:person, :name, :first) - assert_equal "Chicago", @params.dig(:person, :addresses, 0, :city) - end + test "#dig delegates the dig method to its values" do + assert_equal "David", @params.dig(:person, :name, :first) + assert_equal "Chicago", @params.dig(:person, :addresses, 0, :city) + end - test "#dig converts hashes to parameters" do - assert_kind_of ActionController::Parameters, @params.dig(:person) - assert_kind_of ActionController::Parameters, @params.dig(:person, :addresses, 0) - assert @params.dig(:person, :addresses).all? do |value| - value.is_a?(ActionController::Parameters) - end - end - else - test "ActionController::Parameters does not respond to #dig on Ruby 2.2" do - assert_not ActionController::Parameters.method_defined?(:dig) - assert_not_respond_to @params, :dig + test "#dig converts hashes to parameters" do + assert_kind_of ActionController::Parameters, @params.dig(:person) + assert_kind_of ActionController::Parameters, @params.dig(:person, :addresses, 0) + assert @params.dig(:person, :addresses).all? do |value| + value.is_a?(ActionController::Parameters) end end + + test "mutating #dig return value mutates underlying parameters" do + @params.dig(:person, :name)[:first] = "Bill" + assert_equal "Bill", @params.dig(:person, :name, :first) + + @params.dig(:person, :addresses)[0] = { city: "Boston", state: "Massachusetts" } + assert_equal "Boston", @params.dig(:person, :addresses, 0, :city) + end end diff --git a/actionpack/test/controller/parameters/mutators_test.rb b/actionpack/test/controller/parameters/mutators_test.rb index 4d9fea7188..312b1e5b27 100644 --- a/actionpack/test/controller/parameters/mutators_test.rb +++ b/actionpack/test/controller/parameters/mutators_test.rb @@ -2,7 +2,6 @@ require "abstract_unit" require "action_controller/metal/strong_parameters" -require "active_support/core_ext/hash/transform_values" class ParametersMutatorsTest < ActiveSupport::TestCase setup do diff --git a/actionpack/test/controller/parameters/parameters_permit_test.rb b/actionpack/test/controller/parameters/parameters_permit_test.rb index 295f3a03ef..34b9ac0ab8 100644 --- a/actionpack/test/controller/parameters/parameters_permit_test.rb +++ b/actionpack/test/controller/parameters/parameters_permit_test.rb @@ -136,7 +136,7 @@ class ParametersPermitTest < ActiveSupport::TestCase test "key: it is not assigned if not present in params" do params = ActionController::Parameters.new(name: "Joe") permitted = params.permit(:id) - assert !permitted.has_key?(:id) + assert_not permitted.has_key?(:id) end test "key to empty array: empty arrays pass" do @@ -309,7 +309,7 @@ class ParametersPermitTest < ActiveSupport::TestCase merged_params = @params.reverse_merge(default_params) assert_equal "1234", merged_params[:id] - refute_predicate merged_params[:person], :empty? + assert_not_predicate merged_params[:person], :empty? end test "#with_defaults is an alias of reverse_merge" do @@ -317,11 +317,11 @@ class ParametersPermitTest < ActiveSupport::TestCase merged_params = @params.with_defaults(default_params) assert_equal "1234", merged_params[:id] - refute_predicate merged_params[:person], :empty? + assert_not_predicate merged_params[:person], :empty? end test "not permitted is sticky beyond reverse_merge" do - refute_predicate @params.reverse_merge(a: "b"), :permitted? + assert_not_predicate @params.reverse_merge(a: "b"), :permitted? end test "permitted is sticky beyond reverse_merge" do @@ -334,7 +334,7 @@ class ParametersPermitTest < ActiveSupport::TestCase @params.reverse_merge!(default_params) assert_equal "1234", @params[:id] - refute_predicate @params[:person], :empty? + assert_not_predicate @params[:person], :empty? end test "#with_defaults! is an alias of reverse_merge!" do @@ -342,7 +342,7 @@ class ParametersPermitTest < ActiveSupport::TestCase @params.with_defaults!(default_params) assert_equal "1234", @params[:id] - refute_predicate @params[:person], :empty? + assert_not_predicate @params[:person], :empty? end test "modifying the parameters" do @@ -353,12 +353,15 @@ class ParametersPermitTest < ActiveSupport::TestCase assert_equal "Jonas", @params[:person][:family][:brother] end - test "permit is recursive" do + test "permit! is recursive" do + @params[:nested_array] = [[{ x: 2, y: 3 }, { x: 21, y: 42 }]] @params.permit! assert_predicate @params, :permitted? assert_predicate @params[:person], :permitted? assert_predicate @params[:person][:name], :permitted? assert_predicate @params[:person][:addresses][0], :permitted? + assert_predicate @params[:nested_array][0][0], :permitted? + assert_predicate @params[:nested_array][0][1], :permitted? end test "permitted takes a default value when Parameters.permit_all_parameters is set" do diff --git a/actionpack/test/controller/parameters/serialization_test.rb b/actionpack/test/controller/parameters/serialization_test.rb index 7809d0f357..7708c8e4fe 100644 --- a/actionpack/test/controller/parameters/serialization_test.rb +++ b/actionpack/test/controller/parameters/serialization_test.rb @@ -2,7 +2,6 @@ require "abstract_unit" require "action_controller/metal/strong_parameters" -require "active_support/core_ext/string/strip" class ParametersSerializationTest < ActiveSupport::TestCase setup do @@ -31,7 +30,7 @@ class ParametersSerializationTest < ActiveSupport::TestCase end test "yaml backwardscompatible with psych 2.0.8 format" do - params = YAML.load <<-end_of_yaml.strip_heredoc + params = YAML.load <<~end_of_yaml --- !ruby/hash:ActionController::Parameters key: :value end_of_yaml @@ -41,7 +40,7 @@ class ParametersSerializationTest < ActiveSupport::TestCase end test "yaml backwardscompatible with psych 2.0.9+ format" do - params = YAML.load(<<-end_of_yaml.strip_heredoc) + params = YAML.load(<<~end_of_yaml) --- !ruby/hash-with-ivars:ActionController::Parameters elements: key: :value diff --git a/actionpack/test/controller/render_test.rb b/actionpack/test/controller/render_test.rb index fc21543049..24c5761e41 100644 --- a/actionpack/test/controller/render_test.rb +++ b/actionpack/test/controller/render_test.rb @@ -650,7 +650,7 @@ class ImplicitRenderTest < ActionController::TestCase tests ImplicitRenderTestController def test_implicit_no_content_response_as_browser - assert_raises(ActionController::UnknownFormat) do + assert_raises(ActionController::MissingExactTemplate) do get :empty_action end end diff --git a/actionpack/test/controller/routing_test.rb b/actionpack/test/controller/routing_test.rb index ec939e946a..259f3b8855 100644 --- a/actionpack/test/controller/routing_test.rb +++ b/actionpack/test/controller/routing_test.rb @@ -23,7 +23,7 @@ class UriReservedCharactersRoutingTest < ActiveSupport::TestCase end safe, unsafe = %w(: @ & = + $ , ;), %w(^ ? # [ ]) - hex = unsafe.map { |char| "%" + char.unpack("H2").first.upcase } + hex = unsafe.map { |char| "%" + char.unpack1("H2").upcase } @segment = "#{safe.join}#{unsafe.join}".freeze @escaped = "#{safe.join}#{hex.join}".freeze @@ -676,7 +676,7 @@ class LegacyRouteSetTests < ActiveSupport::TestCase token = "\321\202\320\265\320\272\321\201\321\202".dup # 'text' in Russian token.force_encoding(Encoding::BINARY) - escaped_token = CGI::escape(token) + escaped_token = CGI.escape(token) assert_equal "/page/" + escaped_token, url_for(rs, controller: "content", action: "show_page", id: token) assert_equal({ controller: "content", action: "show_page", id: token }, rs.recognize_path("/page/#{escaped_token}")) diff --git a/actionpack/test/controller/test_case_test.rb b/actionpack/test/controller/test_case_test.rb index 7d4850294d..e66c409786 100644 --- a/actionpack/test/controller/test_case_test.rb +++ b/actionpack/test/controller/test_case_test.rb @@ -681,6 +681,14 @@ XML assert_equal "baz", @request.filtered_parameters[:foo] end + def test_raw_post_reset_between_post_requests + post :no_op, params: { foo: "bar" } + assert_equal "foo=bar", @request.raw_post + + post :no_op, params: { foo: "baz" } + assert_equal "foo=baz", @request.raw_post + end + def test_path_is_kept_after_the_request get :test_params, params: { id: "foo" } assert_equal "/test_case_test/test/test_params/foo", @request.path @@ -740,6 +748,14 @@ XML assert_equal "application/json", @response.body end + def test_request_format_kwarg_doesnt_mutate_params + params = { foo: "bar" }.freeze + + assert_nothing_raised do + get :test_format, format: "json", params: params + end + end + def test_should_have_knowledge_of_client_side_cookie_state_even_if_they_are_not_set cookies["foo"] = "bar" get :no_op diff --git a/actionpack/test/dispatch/content_security_policy_test.rb b/actionpack/test/dispatch/content_security_policy_test.rb index 7c4a65a633..c4c7f53903 100644 --- a/actionpack/test/dispatch/content_security_policy_test.rb +++ b/actionpack/test/dispatch/content_security_policy_test.rb @@ -8,10 +8,10 @@ class ContentSecurityPolicyTest < ActiveSupport::TestCase end def test_build - assert_equal ";", @policy.build + assert_equal "", @policy.build @policy.script_src :self - assert_equal "script-src 'self';", @policy.build + assert_equal "script-src 'self'", @policy.build end def test_dup @@ -25,34 +25,40 @@ class ContentSecurityPolicyTest < ActiveSupport::TestCase def test_mappings @policy.script_src :data - assert_equal "script-src data:;", @policy.build + assert_equal "script-src data:", @policy.build @policy.script_src :mediastream - assert_equal "script-src mediastream:;", @policy.build + assert_equal "script-src mediastream:", @policy.build @policy.script_src :blob - assert_equal "script-src blob:;", @policy.build + assert_equal "script-src blob:", @policy.build @policy.script_src :filesystem - assert_equal "script-src filesystem:;", @policy.build + assert_equal "script-src filesystem:", @policy.build @policy.script_src :self - assert_equal "script-src 'self';", @policy.build + assert_equal "script-src 'self'", @policy.build @policy.script_src :unsafe_inline - assert_equal "script-src 'unsafe-inline';", @policy.build + assert_equal "script-src 'unsafe-inline'", @policy.build @policy.script_src :unsafe_eval - assert_equal "script-src 'unsafe-eval';", @policy.build + assert_equal "script-src 'unsafe-eval'", @policy.build @policy.script_src :none - assert_equal "script-src 'none';", @policy.build + assert_equal "script-src 'none'", @policy.build @policy.script_src :strict_dynamic - assert_equal "script-src 'strict-dynamic';", @policy.build + assert_equal "script-src 'strict-dynamic'", @policy.build + + @policy.script_src :ws + assert_equal "script-src ws:", @policy.build + + @policy.script_src :wss + assert_equal "script-src wss:", @policy.build @policy.script_src :none, :report_sample - assert_equal "script-src 'none' 'report-sample';", @policy.build + assert_equal "script-src 'none' 'report-sample'", @policy.build end def test_fetch_directives @@ -131,16 +137,16 @@ class ContentSecurityPolicyTest < ActiveSupport::TestCase def test_document_directives @policy.base_uri "https://example.com" - assert_match %r{base-uri https://example\.com;}, @policy.build + assert_match %r{base-uri https://example\.com}, @policy.build @policy.plugin_types "application/x-shockwave-flash" - assert_match %r{plugin-types application/x-shockwave-flash;}, @policy.build + assert_match %r{plugin-types application/x-shockwave-flash}, @policy.build @policy.sandbox - assert_match %r{sandbox;}, @policy.build + assert_match %r{sandbox}, @policy.build @policy.sandbox "allow-scripts", "allow-modals" - assert_match %r{sandbox allow-scripts allow-modals;}, @policy.build + assert_match %r{sandbox allow-scripts allow-modals}, @policy.build @policy.sandbox false assert_no_match %r{sandbox}, @policy.build @@ -148,35 +154,35 @@ class ContentSecurityPolicyTest < ActiveSupport::TestCase def test_navigation_directives @policy.form_action :self - assert_match %r{form-action 'self';}, @policy.build + assert_match %r{form-action 'self'}, @policy.build @policy.frame_ancestors :self - assert_match %r{frame-ancestors 'self';}, @policy.build + assert_match %r{frame-ancestors 'self'}, @policy.build end def test_reporting_directives @policy.report_uri "/violations" - assert_match %r{report-uri /violations;}, @policy.build + assert_match %r{report-uri /violations}, @policy.build end def test_other_directives @policy.block_all_mixed_content - assert_match %r{block-all-mixed-content;}, @policy.build + assert_match %r{block-all-mixed-content}, @policy.build @policy.block_all_mixed_content false assert_no_match %r{block-all-mixed-content}, @policy.build @policy.require_sri_for :script, :style - assert_match %r{require-sri-for script style;}, @policy.build + assert_match %r{require-sri-for script style}, @policy.build @policy.require_sri_for "script", "style" - assert_match %r{require-sri-for script style;}, @policy.build + assert_match %r{require-sri-for script style}, @policy.build @policy.require_sri_for assert_no_match %r{require-sri-for}, @policy.build @policy.upgrade_insecure_requests - assert_match %r{upgrade-insecure-requests;}, @policy.build + assert_match %r{upgrade-insecure-requests}, @policy.build @policy.upgrade_insecure_requests false assert_no_match %r{upgrade-insecure-requests}, @policy.build @@ -184,26 +190,28 @@ class ContentSecurityPolicyTest < ActiveSupport::TestCase def test_multiple_sources @policy.script_src :self, :https - assert_equal "script-src 'self' https:;", @policy.build + assert_equal "script-src 'self' https:", @policy.build end def test_multiple_directives @policy.script_src :self, :https @policy.style_src :self, :https - assert_equal "script-src 'self' https:; style-src 'self' https:;", @policy.build + assert_equal "script-src 'self' https:; style-src 'self' https:", @policy.build end def test_dynamic_directives - request = Struct.new(:host).new("www.example.com") + request = ActionDispatch::Request.new("HTTP_HOST" => "www.example.com") controller = Struct.new(:request).new(request) @policy.script_src -> { request.host } - assert_equal "script-src www.example.com;", @policy.build(controller) + assert_equal "script-src www.example.com", @policy.build(controller) end def test_mixed_static_and_dynamic_directives @policy.script_src :self, -> { "foo.com" }, "bar.com" - assert_equal "script-src 'self' foo.com bar.com;", @policy.build(Object.new) + request = ActionDispatch::Request.new({}) + controller = Struct.new(:request).new(request) + assert_equal "script-src 'self' foo.com bar.com", @policy.build(controller) end def test_invalid_directive_source @@ -235,6 +243,73 @@ class ContentSecurityPolicyTest < ActiveSupport::TestCase end end +class DefaultContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest + class PolicyController < ActionController::Base + def index + head :ok + end + end + + ROUTES = ActionDispatch::Routing::RouteSet.new + ROUTES.draw do + scope module: "default_content_security_policy_integration_test" do + get "/", to: "policy#index" + end + end + + POLICY = ActionDispatch::ContentSecurityPolicy.new do |p| + p.default_src :self + p.script_src :https + end + + class PolicyConfigMiddleware + def initialize(app) + @app = app + end + + def call(env) + env["action_dispatch.content_security_policy"] = POLICY + env["action_dispatch.content_security_policy_nonce_generator"] = proc { "iyhD0Yc0W+c=" } + env["action_dispatch.content_security_policy_report_only"] = false + env["action_dispatch.show_exceptions"] = false + + @app.call(env) + end + end + + APP = build_app(ROUTES) do |middleware| + middleware.use PolicyConfigMiddleware + middleware.use ActionDispatch::ContentSecurityPolicy::Middleware + end + + def app + APP + end + + def test_adds_nonce_to_script_src_content_security_policy_only_once + get "/" + get "/" + assert_policy "default-src 'self'; script-src https: 'nonce-iyhD0Yc0W+c='" + end + + private + + def assert_policy(expected, report_only: false) + assert_response :success + + if report_only + expected_header = "Content-Security-Policy-Report-Only" + unexpected_header = "Content-Security-Policy" + else + expected_header = "Content-Security-Policy" + unexpected_header = "Content-Security-Policy-Report-Only" + end + + assert_nil response.headers[unexpected_header] + assert_equal expected, response.headers[expected_header] + end +end + class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest class PolicyController < ActionController::Base content_security_policy only: :inline do |p| @@ -253,6 +328,13 @@ class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest p.report_uri "/violations" end + content_security_policy only: :script_src do |p| + p.default_src false + p.script_src :self + end + + content_security_policy(false, only: :no_policy) + content_security_policy_report_only only: :report_only def index @@ -271,6 +353,14 @@ class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest head :ok end + def script_src + head :ok + end + + def no_policy + head :ok + end + private def condition? params[:condition] == "true" @@ -284,6 +374,8 @@ class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest get "/inline", to: "policy#inline" get "/conditional", to: "policy#conditional" get "/report-only", to: "policy#report_only" + get "/script-src", to: "policy#script_src" + get "/no-policy", to: "policy#no_policy" end end @@ -298,6 +390,7 @@ class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest def call(env) env["action_dispatch.content_security_policy"] = POLICY + env["action_dispatch.content_security_policy_nonce_generator"] = proc { "iyhD0Yc0W+c=" } env["action_dispatch.content_security_policy_report_only"] = false env["action_dispatch.show_exceptions"] = false @@ -316,40 +409,40 @@ class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest def test_generates_content_security_policy_header get "/" - assert_policy "default-src 'self';" + assert_policy "default-src 'self'" end def test_generates_inline_content_security_policy get "/inline" - assert_policy "default-src https://example.com;" + assert_policy "default-src https://example.com" end def test_generates_conditional_content_security_policy get "/conditional", params: { condition: "true" } - assert_policy "default-src https://true.example.com;" + assert_policy "default-src https://true.example.com" get "/conditional", params: { condition: "false" } - assert_policy "default-src https://false.example.com;" + assert_policy "default-src https://false.example.com" end def test_generates_report_only_content_security_policy get "/report-only" - assert_policy "default-src 'self'; report-uri /violations;", report_only: true + assert_policy "default-src 'self'; report-uri /violations", report_only: true end - private + def test_adds_nonce_to_script_src_content_security_policy + get "/script-src" + assert_policy "script-src 'self' 'nonce-iyhD0Yc0W+c='" + end - def env_config - Rails.application.env_config - end + def test_generates_no_content_security_policy + get "/no-policy" - def content_security_policy - env_config["action_dispatch.content_security_policy"] - end + assert_nil response.headers["Content-Security-Policy"] + assert_nil response.headers["Content-Security-Policy-Report-Only"] + end - def content_security_policy=(policy) - env_config["action_dispatch.content_security_policy"] = policy - end + private def assert_policy(expected, report_only: false) assert_response :success @@ -366,3 +459,61 @@ class ContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest assert_equal expected, response.headers[expected_header] end end + +class DisabledContentSecurityPolicyIntegrationTest < ActionDispatch::IntegrationTest + class PolicyController < ActionController::Base + content_security_policy only: :inline do |p| + p.default_src "https://example.com" + end + + def index + head :ok + end + + def inline + head :ok + end + end + + ROUTES = ActionDispatch::Routing::RouteSet.new + ROUTES.draw do + scope module: "disabled_content_security_policy_integration_test" do + get "/", to: "policy#index" + get "/inline", to: "policy#inline" + end + end + + class PolicyConfigMiddleware + def initialize(app) + @app = app + end + + def call(env) + env["action_dispatch.content_security_policy"] = nil + env["action_dispatch.content_security_policy_nonce_generator"] = nil + env["action_dispatch.content_security_policy_report_only"] = false + env["action_dispatch.show_exceptions"] = false + + @app.call(env) + end + end + + APP = build_app(ROUTES) do |middleware| + middleware.use PolicyConfigMiddleware + middleware.use ActionDispatch::ContentSecurityPolicy::Middleware + end + + def app + APP + end + + def test_generates_no_content_security_policy_by_default + get "/" + assert_nil response.headers["Content-Security-Policy"] + end + + def test_generates_content_security_policy_header_when_globally_disabled + get "/inline" + assert_equal "default-src https://example.com", response.headers["Content-Security-Policy"] + end +end diff --git a/actionpack/test/dispatch/cookies_test.rb b/actionpack/test/dispatch/cookies_test.rb index 94cff10fe4..aba778fad6 100644 --- a/actionpack/test/dispatch/cookies_test.rb +++ b/actionpack/test/dispatch/cookies_test.rb @@ -65,8 +65,8 @@ class CookieJarTest < ActiveSupport::TestCase end def test_key_methods - assert !request.cookie_jar.key?(:foo) - assert !request.cookie_jar.has_key?("foo") + assert_not request.cookie_jar.key?(:foo) + assert_not request.cookie_jar.has_key?("foo") request.cookie_jar[:foo] = :bar assert request.cookie_jar.key?(:foo) diff --git a/actionpack/test/dispatch/debug_exceptions_test.rb b/actionpack/test/dispatch/debug_exceptions_test.rb index 60acba0616..045567ff83 100644 --- a/actionpack/test/dispatch/debug_exceptions_test.rb +++ b/actionpack/test/dispatch/debug_exceptions_test.rb @@ -3,6 +3,8 @@ require "abstract_unit" class DebugExceptionsTest < ActionDispatch::IntegrationTest + InterceptedErrorInstance = StandardError.new + class Boomer attr_accessor :closed @@ -36,6 +38,8 @@ class DebugExceptionsTest < ActionDispatch::IntegrationTest raise RuntimeError when %r{/method_not_allowed} raise ActionController::MethodNotAllowed + when %r{/intercepted_error} + raise InterceptedErrorInstance when %r{/unknown_http_method} raise ActionController::UnknownHttpMethod when %r{/not_implemented} @@ -76,9 +80,13 @@ class DebugExceptionsTest < ActionDispatch::IntegrationTest end end + Interceptor = proc { |request, exception| request.set_header("int", exception) } + BadInterceptor = proc { |request, exception| raise "bad" } RoutesApp = Struct.new(:routes).new(SharedTestRoutes) ProductionApp = ActionDispatch::DebugExceptions.new(Boomer.new(false), RoutesApp) DevelopmentApp = ActionDispatch::DebugExceptions.new(Boomer.new(true), RoutesApp) + InterceptedApp = ActionDispatch::DebugExceptions.new(Boomer.new(true), RoutesApp, :default, [Interceptor]) + BadInterceptedApp = ActionDispatch::DebugExceptions.new(Boomer.new(true), RoutesApp, :default, [BadInterceptor]) test "skip diagnosis if not showing detailed exceptions" do @app = ProductionApp @@ -499,4 +507,20 @@ class DebugExceptionsTest < ActionDispatch::IntegrationTest end end end + + test "invoke interceptors before rendering" do + @app = InterceptedApp + get "/intercepted_error", headers: { "action_dispatch.show_exceptions" => true } + + assert_equal InterceptedErrorInstance, request.get_header("int") + end + + test "bad interceptors doesn't debug exceptions" do + @app = BadInterceptedApp + + get "/puke", headers: { "action_dispatch.show_exceptions" => true } + + assert_response 500 + assert_match(/puke/, body) + end end diff --git a/actionpack/test/dispatch/executor_test.rb b/actionpack/test/dispatch/executor_test.rb index 8eb6450385..5b8be39b6d 100644 --- a/actionpack/test/dispatch/executor_test.rb +++ b/actionpack/test/dispatch/executor_test.rb @@ -81,7 +81,7 @@ class ExecutorTest < ActiveSupport::TestCase running = false body.close - assert !running + assert_not running end def test_complete_callbacks_are_called_on_close @@ -89,7 +89,7 @@ class ExecutorTest < ActiveSupport::TestCase executor.to_complete { completed = true } body = call_and_return_body - assert !completed + assert_not completed body.close assert completed @@ -116,7 +116,7 @@ class ExecutorTest < ActiveSupport::TestCase call_and_return_body.close assert result - assert !defined?(@in_shared_context) # it's not in the test itself + assert_not defined?(@in_shared_context) # it's not in the test itself end private diff --git a/actionpack/test/dispatch/mime_type_test.rb b/actionpack/test/dispatch/mime_type_test.rb index 6167ea46df..fa264417e1 100644 --- a/actionpack/test/dispatch/mime_type_test.rb +++ b/actionpack/test/dispatch/mime_type_test.rb @@ -180,8 +180,8 @@ class MimeTypeTest < ActiveSupport::TestCase assert Mime[:js] =~ "text/javascript" assert Mime[:js] =~ "application/javascript" assert Mime[:js] !~ "text/html" - assert !(Mime[:js] !~ "text/javascript") - assert !(Mime[:js] !~ "application/javascript") + assert_not (Mime[:js] !~ "text/javascript") + assert_not (Mime[:js] !~ "application/javascript") assert Mime[:html] =~ "application/xhtml+xml" end end diff --git a/actionpack/test/dispatch/reloader_test.rb b/actionpack/test/dispatch/reloader_test.rb index e529229fae..edc4cd62a3 100644 --- a/actionpack/test/dispatch/reloader_test.rb +++ b/actionpack/test/dispatch/reloader_test.rb @@ -115,7 +115,7 @@ class ReloaderTest < ActiveSupport::TestCase reloader.to_complete { completed = true } body = call_and_return_body - assert !completed + assert_not completed body.close assert completed @@ -129,7 +129,7 @@ class ReloaderTest < ActiveSupport::TestCase prepared = false body.close - assert !prepared + assert_not prepared end def test_complete_callbacks_are_called_on_exceptions diff --git a/actionpack/test/dispatch/request/session_test.rb b/actionpack/test/dispatch/request/session_test.rb index bf5a74e694..74da2fe7d3 100644 --- a/actionpack/test/dispatch/request/session_test.rb +++ b/actionpack/test/dispatch/request/session_test.rb @@ -118,6 +118,18 @@ module ActionDispatch end end + def test_dig + session = Session.create(store, req, {}) + session["one"] = { "two" => "3" } + + assert_equal "3", session.dig("one", "two") + assert_equal "3", session.dig(:one, "two") + + assert_nil session.dig("three", "two") + assert_nil session.dig("one", "three") + assert_nil session.dig("one", :two) + end + private def store Class.new { diff --git a/actionpack/test/dispatch/response_test.rb b/actionpack/test/dispatch/response_test.rb index 4c8d528507..6d87314e97 100644 --- a/actionpack/test/dispatch/response_test.rb +++ b/actionpack/test/dispatch/response_test.rb @@ -191,7 +191,7 @@ class ResponseTest < ActiveSupport::TestCase test "does not include Status header" do @response.status = "200 OK" _, headers, _ = @response.to_a - assert !headers.has_key?("Status") + assert_not headers.has_key?("Status") end test "response code" do diff --git a/actionpack/test/dispatch/routing/inspector_test.rb b/actionpack/test/dispatch/routing/inspector_test.rb index 438a918567..9150d5010b 100644 --- a/actionpack/test/dispatch/routing/inspector_test.rb +++ b/actionpack/test/dispatch/routing/inspector_test.rb @@ -3,6 +3,7 @@ require "abstract_unit" require "rails/engine" require "action_dispatch/routing/inspector" +require "io/console/size" class MountedRackApp def self.call(env) @@ -15,16 +16,10 @@ end module ActionDispatch module Routing class RoutesInspectorTest < ActiveSupport::TestCase - def setup + setup do @set = ActionDispatch::Routing::RouteSet.new end - def draw(options = nil, &block) - @set.draw(&block) - inspector = ActionDispatch::Routing::RoutesInspector.new(@set.routes) - inspector.format(ActionDispatch::Routing::ConsoleFormatter.new, options).split("\n") - end - def test_displaying_routes_for_engines engine = Class.new(Rails::Engine) do def self.inspect @@ -305,7 +300,7 @@ module ActionDispatch end def test_routes_can_be_filtered - output = draw("posts") do + output = draw(grep: "posts") do resources :articles resources :posts end @@ -321,8 +316,76 @@ module ActionDispatch " DELETE /posts/:id(.:format) posts#destroy"], output end + def test_routes_when_expanded + previous_console_winsize = IO.console.winsize + IO.console.winsize = [0, 23] + + engine = Class.new(Rails::Engine) do + def self.inspect + "Blog::Engine" + end + end + engine.routes.draw do + get "/cart", to: "cart#show" + end + + output = draw(formatter: ActionDispatch::Routing::ConsoleFormatter::Expanded.new) do + get "/custom/assets", to: "custom_assets#show" + get "/custom/furnitures", to: "custom_furnitures#show" + mount engine => "/blog", :as => "blog" + end + + assert_equal ["--[ Route 1 ]----------", + "Prefix | custom_assets", + "Verb | GET", + "URI | /custom/assets(.:format)", + "Controller#Action | custom_assets#show", + "--[ Route 2 ]----------", + "Prefix | custom_furnitures", + "Verb | GET", + "URI | /custom/furnitures(.:format)", + "Controller#Action | custom_furnitures#show", + "--[ Route 3 ]----------", + "Prefix | blog", + "Verb | ", + "URI | /blog", + "Controller#Action | Blog::Engine", + "", + "[ Routes for Blog::Engine ]", + "--[ Route 1 ]----------", + "Prefix | cart", + "Verb | GET", + "URI | /cart(.:format)", + "Controller#Action | cart#show"], output + ensure + IO.console.winsize = previous_console_winsize + end + + def test_no_routes_matched_filter_when_expanded + output = draw(grep: "rails/dummy", formatter: ActionDispatch::Routing::ConsoleFormatter::Expanded.new) do + get "photos/:id" => "photos#show", :id => /[A-Z]\d{5}/ + end + + assert_equal [ + "No routes were found for this grep pattern.", + "For more information about routes, see the Rails guide: http://guides.rubyonrails.org/routing.html." + ], output + end + + def test_not_routes_when_expanded + output = draw(grep: "rails/dummy", formatter: ActionDispatch::Routing::ConsoleFormatter::Expanded.new) {} + + assert_equal [ + "You don't have any routes defined!", + "", + "Please add some routes in config/routes.rb.", + "", + "For more information about routes, see the Rails guide: http://guides.rubyonrails.org/routing.html." + ], output + end + def test_routes_can_be_filtered_with_namespaced_controllers - output = draw("admin/posts") do + output = draw(grep: "admin/posts") do resources :articles namespace :admin do resources :posts @@ -370,24 +433,24 @@ module ActionDispatch end assert_equal [ - "No routes were found for this controller", + "No routes were found for this controller.", "For more information about routes, see the Rails guide: http://guides.rubyonrails.org/routing.html." ], output end def test_no_routes_matched_filter - output = draw("rails/dummy") do + output = draw(grep: "rails/dummy") do get "photos/:id" => "photos#show", :id => /[A-Z]\d{5}/ end assert_equal [ - "No routes were found for this controller", + "No routes were found for this grep pattern.", "For more information about routes, see the Rails guide: http://guides.rubyonrails.org/routing.html." ], output end def test_no_routes_were_defined - output = draw("Rails::DummyController") {} + output = draw(grep: "Rails::DummyController") {} assert_equal [ "You don't have any routes defined!", @@ -420,6 +483,13 @@ module ActionDispatch "custom_assets GET /custom/assets(.:format) custom_assets#show", ], output end + + private + def draw(formatter: ActionDispatch::Routing::ConsoleFormatter::Sheet.new, **options, &block) + @set.draw(&block) + inspector = ActionDispatch::Routing::RoutesInspector.new(@set.routes) + inspector.format(formatter, options).split("\n") + end end end end diff --git a/actionpack/test/dispatch/routing_test.rb b/actionpack/test/dispatch/routing_test.rb index 4222eb4eb7..dd6adcbfd1 100644 --- a/actionpack/test/dispatch/routing_test.rb +++ b/actionpack/test/dispatch/routing_test.rb @@ -3166,7 +3166,7 @@ class TestRoutingMapper < ActionDispatch::IntegrationTest end end - assert !respond_to?(:routes_no_collision_path) + assert_not respond_to?(:routes_no_collision_path) end def test_controller_name_with_leading_slash_raise_error @@ -4500,7 +4500,7 @@ class TestPortConstraints < ActionDispatch::IntegrationTest get "/integer", to: ok, constraints: { port: 8080 } get "/string", to: ok, constraints: { port: "8080" } - get "/array", to: ok, constraints: { port: [8080] } + get "/array/:idx", to: ok, constraints: { port: [8080], idx: %w[first last] } get "/regexp", to: ok, constraints: { port: /8080/ } end end @@ -4529,7 +4529,10 @@ class TestPortConstraints < ActionDispatch::IntegrationTest get "http://www.example.com/array" assert_response :not_found - get "http://www.example.com:8080/array" + get "http://www.example.com:8080/array/middle" + assert_response :not_found + + get "http://www.example.com:8080/array/first" assert_response :success end diff --git a/actionpack/test/dispatch/ssl_test.rb b/actionpack/test/dispatch/ssl_test.rb index 8ac9502af9..baf46e7c7e 100644 --- a/actionpack/test/dispatch/ssl_test.rb +++ b/actionpack/test/dispatch/ssl_test.rb @@ -98,8 +98,8 @@ class RedirectSSLTest < SSLTest end class StrictTransportSecurityTest < SSLTest - EXPECTED = "max-age=15552000" - EXPECTED_WITH_SUBDOMAINS = "max-age=15552000; includeSubDomains" + EXPECTED = "max-age=31536000" + EXPECTED_WITH_SUBDOMAINS = "max-age=31536000; includeSubDomains" def assert_hsts(expected, url: "https://example.org", hsts: { subdomains: true }, headers: {}) self.app = build_app ssl_options: { hsts: hsts }, headers: headers @@ -208,6 +208,14 @@ class SecureCookiesTest < SSLTest assert_cookies(*DEFAULT.split("\n")) end + def test_cookies_as_not_secure_with_exclude + excluding = { exclude: -> request { request.domain =~ /example/ } } + get headers: { "Set-Cookie" => DEFAULT }, ssl_options: { redirect: excluding } + + assert_cookies(*DEFAULT.split("\n")) + assert_response :ok + end + def test_no_cookies get assert_nil response.headers["Set-Cookie"] diff --git a/actionpack/test/dispatch/static_test.rb b/actionpack/test/dispatch/static_test.rb index 0bdff68692..6b69cd9999 100644 --- a/actionpack/test/dispatch/static_test.rb +++ b/actionpack/test/dispatch/static_test.rb @@ -71,7 +71,16 @@ module StaticTests end def test_served_static_file_with_non_english_filename - assert_html "means hello in Japanese\n", get("/foo/#{Rack::Utils.escape("こんにちは.html")}") + assert_html "means hello in Japanese\n", get("/foo/%E3%81%93%E3%82%93%E3%81%AB%E3%81%A1%E3%81%AF.html") + end + + def test_served_gzipped_static_file_with_non_english_filename + response = get("/foo/%E3%81%95%E3%82%88%E3%81%86%E3%81%AA%E3%82%89.html", "HTTP_ACCEPT_ENCODING" => "gzip") + + assert_gzip "/foo/さようなら.html", response + assert_equal "text/html", response.headers["Content-Type"] + assert_equal "Accept-Encoding", response.headers["Vary"] + assert_equal "gzip", response.headers["Content-Encoding"] end def test_serves_static_file_with_exclamation_mark_in_filename diff --git a/actionpack/test/dispatch/system_testing/screenshot_helper_test.rb b/actionpack/test/dispatch/system_testing/screenshot_helper_test.rb index 264844fc7d..de79c05657 100644 --- a/actionpack/test/dispatch/system_testing/screenshot_helper_test.rb +++ b/actionpack/test/dispatch/system_testing/screenshot_helper_test.rb @@ -9,7 +9,7 @@ class ScreenshotHelperTest < ActiveSupport::TestCase new_test = DrivenBySeleniumWithChrome.new("x") Rails.stub :root, Pathname.getwd do - assert_equal "tmp/screenshots/x.png", new_test.send(:image_path) + assert_equal Rails.root.join("tmp/screenshots/x.png").to_s, new_test.send(:image_path) end end @@ -18,7 +18,7 @@ class ScreenshotHelperTest < ActiveSupport::TestCase Rails.stub :root, Pathname.getwd do new_test.stub :passed?, false do - assert_equal "tmp/screenshots/failures_x.png", new_test.send(:image_path) + assert_equal Rails.root.join("tmp/screenshots/failures_x.png").to_s, new_test.send(:image_path) end end end @@ -29,7 +29,7 @@ class ScreenshotHelperTest < ActiveSupport::TestCase Rails.stub :root, Pathname.getwd do new_test.stub :passed?, false do new_test.stub :skipped?, true do - assert_equal "tmp/screenshots/x.png", new_test.send(:image_path) + assert_equal Rails.root.join("tmp/screenshots/x.png").to_s, new_test.send(:image_path) end end end @@ -59,11 +59,11 @@ class ScreenshotHelperTest < ActiveSupport::TestCase end end - test "image path returns the relative path from current directory" do + test "image path returns the absolute path from root" do new_test = DrivenBySeleniumWithChrome.new("x") Rails.stub :root, Pathname.getwd.join("..") do - assert_equal "../tmp/screenshots/x.png", new_test.send(:image_path) + assert_equal Rails.root.join("tmp/screenshots/x.png").to_s, new_test.send(:image_path) end end end diff --git a/actionpack/test/dispatch/system_testing/server_test.rb b/actionpack/test/dispatch/system_testing/server_test.rb index 95e411faf4..740e90a4da 100644 --- a/actionpack/test/dispatch/system_testing/server_test.rb +++ b/actionpack/test/dispatch/system_testing/server_test.rb @@ -17,7 +17,7 @@ class ServerTest < ActiveSupport::TestCase test "server is changed from `default` to `puma`" do Capybara.server = :default ActionDispatch::SystemTesting::Server.new.run - refute_equal Capybara.server, Capybara.servers[:default] + assert_not_equal Capybara.server, Capybara.servers[:default] end test "server is not changed to `puma` when is different than default" do diff --git a/actionpack/test/fixtures/functional_caching/_formatted_partial.html.erb b/actionpack/test/fixtures/functional_caching/_formatted_partial.html.erb new file mode 100644 index 0000000000..aad73c0d6b --- /dev/null +++ b/actionpack/test/fixtures/functional_caching/_formatted_partial.html.erb @@ -0,0 +1 @@ +<p>Hello!</p> diff --git a/actionpack/test/fixtures/functional_caching/xml_fragment_cached_with_html_partial.xml.builder b/actionpack/test/fixtures/functional_caching/xml_fragment_cached_with_html_partial.xml.builder new file mode 100644 index 0000000000..2bdda3af18 --- /dev/null +++ b/actionpack/test/fixtures/functional_caching/xml_fragment_cached_with_html_partial.xml.builder @@ -0,0 +1,5 @@ +cache do + xml.title "Hello!" +end + +xml.body cdata_section(render("formatted_partial")) diff --git a/actionpack/test/fixtures/public/foo/さようなら.html b/actionpack/test/fixtures/public/foo/さようなら.html new file mode 100644 index 0000000000..627bb2469f --- /dev/null +++ b/actionpack/test/fixtures/public/foo/さようなら.html @@ -0,0 +1 @@ +means goodbye in Japanese diff --git a/actionpack/test/fixtures/public/foo/さようなら.html.gz b/actionpack/test/fixtures/public/foo/さようなら.html.gz Binary files differnew file mode 100644 index 0000000000..4f484cfe86 --- /dev/null +++ b/actionpack/test/fixtures/public/foo/さようなら.html.gz diff --git a/actionpack/test/fixtures/公共/foo/さようなら.html b/actionpack/test/fixtures/公共/foo/さようなら.html new file mode 100644 index 0000000000..627bb2469f --- /dev/null +++ b/actionpack/test/fixtures/公共/foo/さようなら.html @@ -0,0 +1 @@ +means goodbye in Japanese diff --git a/actionpack/test/fixtures/公共/foo/さようなら.html.gz b/actionpack/test/fixtures/公共/foo/さようなら.html.gz Binary files differnew file mode 100644 index 0000000000..4f484cfe86 --- /dev/null +++ b/actionpack/test/fixtures/公共/foo/さようなら.html.gz diff --git a/actionpack/test/journey/route/definition/scanner_test.rb b/actionpack/test/journey/route/definition/scanner_test.rb index 070886c7df..bcbe4388c3 100644 --- a/actionpack/test/journey/route/definition/scanner_test.rb +++ b/actionpack/test/journey/route/definition/scanner_test.rb @@ -10,61 +10,64 @@ module ActionDispatch @scanner = Scanner.new end - # /page/:id(/:action)(.:format) - def test_tokens - [ - ["/", [[:SLASH, "/"]]], - ["*omg", [[:STAR, "*omg"]]], - ["/page", [[:SLASH, "/"], [:LITERAL, "page"]]], - ["/page!", [[:SLASH, "/"], [:LITERAL, "page!"]]], - ["/page$", [[:SLASH, "/"], [:LITERAL, "page$"]]], - ["/page&", [[:SLASH, "/"], [:LITERAL, "page&"]]], - ["/page'", [[:SLASH, "/"], [:LITERAL, "page'"]]], - ["/page*", [[:SLASH, "/"], [:LITERAL, "page*"]]], - ["/page+", [[:SLASH, "/"], [:LITERAL, "page+"]]], - ["/page,", [[:SLASH, "/"], [:LITERAL, "page,"]]], - ["/page;", [[:SLASH, "/"], [:LITERAL, "page;"]]], - ["/page=", [[:SLASH, "/"], [:LITERAL, "page="]]], - ["/page@", [[:SLASH, "/"], [:LITERAL, "page@"]]], - ['/page\:', [[:SLASH, "/"], [:LITERAL, "page:"]]], - ['/page\(', [[:SLASH, "/"], [:LITERAL, "page("]]], - ['/page\)', [[:SLASH, "/"], [:LITERAL, "page)"]]], - ["/~page", [[:SLASH, "/"], [:LITERAL, "~page"]]], - ["/pa-ge", [[:SLASH, "/"], [:LITERAL, "pa-ge"]]], - ["/:page", [[:SLASH, "/"], [:SYMBOL, ":page"]]], - ["/(:page)", [ + CASES = [ + ["/", [[:SLASH, "/"]]], + ["*omg", [[:STAR, "*omg"]]], + ["/page", [[:SLASH, "/"], [:LITERAL, "page"]]], + ["/page!", [[:SLASH, "/"], [:LITERAL, "page!"]]], + ["/page$", [[:SLASH, "/"], [:LITERAL, "page$"]]], + ["/page&", [[:SLASH, "/"], [:LITERAL, "page&"]]], + ["/page'", [[:SLASH, "/"], [:LITERAL, "page'"]]], + ["/page*", [[:SLASH, "/"], [:LITERAL, "page*"]]], + ["/page+", [[:SLASH, "/"], [:LITERAL, "page+"]]], + ["/page,", [[:SLASH, "/"], [:LITERAL, "page,"]]], + ["/page;", [[:SLASH, "/"], [:LITERAL, "page;"]]], + ["/page=", [[:SLASH, "/"], [:LITERAL, "page="]]], + ["/page@", [[:SLASH, "/"], [:LITERAL, "page@"]]], + ['/page\:', [[:SLASH, "/"], [:LITERAL, "page:"]]], + ['/page\(', [[:SLASH, "/"], [:LITERAL, "page("]]], + ['/page\)', [[:SLASH, "/"], [:LITERAL, "page)"]]], + ["/~page", [[:SLASH, "/"], [:LITERAL, "~page"]]], + ["/pa-ge", [[:SLASH, "/"], [:LITERAL, "pa-ge"]]], + ["/:page", [[:SLASH, "/"], [:SYMBOL, ":page"]]], + ["/(:page)", [ + [:SLASH, "/"], + [:LPAREN, "("], + [:SYMBOL, ":page"], + [:RPAREN, ")"], + ]], + ["(/:action)", [ + [:LPAREN, "("], [:SLASH, "/"], + [:SYMBOL, ":action"], + [:RPAREN, ")"], + ]], + ["(())", [[:LPAREN, "("], + [:LPAREN, "("], [:RPAREN, ")"], [:RPAREN, ")"]]], + ["(.:format)", [ [:LPAREN, "("], - [:SYMBOL, ":page"], + [:DOT, "."], + [:SYMBOL, ":format"], [:RPAREN, ")"], ]], - ["(/:action)", [ - [:LPAREN, "("], - [:SLASH, "/"], - [:SYMBOL, ":action"], - [:RPAREN, ")"], - ]], - ["(())", [[:LPAREN, "("], - [:LPAREN, "("], [:RPAREN, ")"], [:RPAREN, ")"]]], - ["(.:format)", [ - [:LPAREN, "("], - [:DOT, "."], - [:SYMBOL, ":format"], - [:RPAREN, ")"], - ]], - ].each do |str, expected| - @scanner.scan_setup str - assert_tokens expected, @scanner + ] + + CASES.each do |pattern, expected_tokens| + test "Scanning `#{pattern}`" do + @scanner.scan_setup pattern + assert_tokens expected_tokens, @scanner, pattern end end - def assert_tokens(tokens, scanner) - toks = [] - while tok = scanner.next_token - toks << tok + private + + def assert_tokens(expected_tokens, scanner, pattern) + actual_tokens = [] + while token = scanner.next_token + actual_tokens << token + end + assert_equal expected_tokens, actual_tokens, "Wrong tokens for `#{pattern}`" end - assert_equal tokens, toks - end end end end diff --git a/actionpack/test/tmp/.gitignore b/actionpack/test/tmp/.gitignore deleted file mode 100644 index e69de29bb2..0000000000 --- a/actionpack/test/tmp/.gitignore +++ /dev/null |