aboutsummaryrefslogtreecommitdiffstats
path: root/railties
diff options
context:
space:
mode:
Diffstat (limited to 'railties')
-rw-r--r--railties/CHANGELOG.md15
-rw-r--r--railties/lib/rails/generators/rails/app/app_generator.rb5
-rw-r--r--railties/lib/rails/generators/rails/app/templates/config/initializers/callback_terminator.rb4
-rw-r--r--railties/test/generators/app_generator_test.rb32
-rw-r--r--railties/test/railties/engine_test.rb15
5 files changed, 61 insertions, 10 deletions
diff --git a/railties/CHANGELOG.md b/railties/CHANGELOG.md
index 588cea8886..5367a4dd0e 100644
--- a/railties/CHANGELOG.md
+++ b/railties/CHANGELOG.md
@@ -1,3 +1,18 @@
+* Add `config/initializers/callback_terminator.rb`
+
+ Newly generated Rails apps have a new initializer called
+ `callback_terminator.rb` which sets the value of the configuration option
+ `config.active_support.halt_callback_chains_on_return_false` to `false`.
+
+ As a result, new Rails apps do not halt callback chains when a callback
+ returns `false`; only when they are explicitly halted with `throw(:abort)`.
+
+ The terminator is *not* added when running `rake rails:update`, so returning
+ `false` will still work on old apps ported to Rails 5, displaying a
+ deprecation warning to prompt users to update their code to the new syntax.
+
+ *claudiob*
+
* Generated fixtures won't use the id when generated with references attributes.
*Pablo Olmos de Aguilera Corradini*
diff --git a/railties/lib/rails/generators/rails/app/app_generator.rb b/railties/lib/rails/generators/rails/app/app_generator.rb
index 1ff1f970b5..0550bf113e 100644
--- a/railties/lib/rails/generators/rails/app/app_generator.rb
+++ b/railties/lib/rails/generators/rails/app/app_generator.rb
@@ -88,9 +88,14 @@ module Rails
def config_when_updating
cookie_serializer_config_exist = File.exist?('config/initializers/cookies_serializer.rb')
+ callback_terminator_config_exist = File.exist?('config/initializers/callback_terminator.rb')
config
+ unless callback_terminator_config_exist
+ remove_file 'config/initializers/callback_terminator.rb'
+ end
+
unless cookie_serializer_config_exist
gsub_file 'config/initializers/cookies_serializer.rb', /json/, 'marshal'
end
diff --git a/railties/lib/rails/generators/rails/app/templates/config/initializers/callback_terminator.rb b/railties/lib/rails/generators/rails/app/templates/config/initializers/callback_terminator.rb
new file mode 100644
index 0000000000..e63022da91
--- /dev/null
+++ b/railties/lib/rails/generators/rails/app/templates/config/initializers/callback_terminator.rb
@@ -0,0 +1,4 @@
+# Be sure to restart your server when you modify this file.
+
+# Do not halt callback chains when a callback returns false.
+Rails.application.config.active_support.halt_callback_chains_on_return_false = false
diff --git a/railties/test/generators/app_generator_test.rb b/railties/test/generators/app_generator_test.rb
index ac8f735cec..e30c9a7b2f 100644
--- a/railties/test/generators/app_generator_test.rb
+++ b/railties/test/generators/app_generator_test.rb
@@ -160,6 +160,38 @@ class AppGeneratorTest < Rails::Generators::TestCase
assert_file("#{app_root}/config/initializers/cookies_serializer.rb", /Rails\.application\.config\.action_dispatch\.cookies_serializer = :json/)
end
+ def test_rails_update_does_not_create_callback_terminator_initializer
+ app_root = File.join(destination_root, 'myapp')
+ run_generator [app_root]
+
+ FileUtils.rm("#{app_root}/config/initializers/callback_terminator.rb")
+
+ Rails.application.config.root = app_root
+ Rails.application.class.stubs(:name).returns("Myapp")
+ Rails.application.stubs(:is_a?).returns(Rails::Application)
+
+ generator = Rails::Generators::AppGenerator.new ["rails"], { with_dispatchers: true }, destination_root: app_root, shell: @shell
+ generator.send(:app_const)
+ quietly { generator.send(:update_config_files) }
+ assert_no_file "#{app_root}/config/initializers/callback_terminator.rb"
+ end
+
+ def test_rails_update_does_not_remove_callback_terminator_initializer_if_already_present
+ app_root = File.join(destination_root, 'myapp')
+ run_generator [app_root]
+
+ FileUtils.touch("#{app_root}/config/initializers/callback_terminator.rb")
+
+ Rails.application.config.root = app_root
+ Rails.application.class.stubs(:name).returns("Myapp")
+ Rails.application.stubs(:is_a?).returns(Rails::Application)
+
+ generator = Rails::Generators::AppGenerator.new ["rails"], { with_dispatchers: true }, destination_root: app_root, shell: @shell
+ generator.send(:app_const)
+ quietly { generator.send(:update_config_files) }
+ assert_file "#{app_root}/config/initializers/callback_terminator.rb"
+ end
+
def test_rails_update_set_the_cookie_serializer_to_marchal_if_it_is_not_already_configured
app_root = File.join(destination_root, 'myapp')
run_generator [app_root]
diff --git a/railties/test/railties/engine_test.rb b/railties/test/railties/engine_test.rb
index 91cdc60bd1..4ffcf64275 100644
--- a/railties/test/railties/engine_test.rb
+++ b/railties/test/railties/engine_test.rb
@@ -498,17 +498,12 @@ YAML
boot_rails
initializers = Rails.application.initializers.tsort
- index = initializers.index { |i| i.name == "dummy_initializer" }
- selection = initializers[(index-3)..(index)].map(&:name).map(&:to_s)
+ dummy_index = initializers.index { |i| i.name == "dummy_initializer" }
+ config_index = initializers.rindex { |i| i.name == :load_config_initializers }
+ stack_index = initializers.index { |i| i.name == :build_middleware_stack }
- assert_equal %w(
- load_config_initializers
- load_config_initializers
- engines_blank_point
- dummy_initializer
- ), selection
-
- assert index < initializers.index { |i| i.name == :build_middleware_stack }
+ assert config_index < dummy_index
+ assert dummy_index < stack_index
end
class Upcaser