aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--actionpack/CHANGELOG.md8
-rw-r--r--actionpack/lib/action_controller/metal/implicit_render.rb7
-rw-r--r--actionpack/test/controller/mime/respond_to_test.rb22
-rw-r--r--actionview/lib/action_view/lookup_context.rb2
4 files changed, 31 insertions, 8 deletions
diff --git a/actionpack/CHANGELOG.md b/actionpack/CHANGELOG.md
index 0ae96441ce..4ab0857a66 100644
--- a/actionpack/CHANGELOG.md
+++ b/actionpack/CHANGELOG.md
@@ -1,3 +1,11 @@
+* For actions with no corresponding templates, render `head :no_content`
+ instead of raising an error. This allows for slimmer API controller
+ methods that simply work, without needing further instructions.
+
+ See #19036.
+
+ *Stephen Bussey*
+
* Provide friendlier access to request variants.
request.variant = :phone
diff --git a/actionpack/lib/action_controller/metal/implicit_render.rb b/actionpack/lib/action_controller/metal/implicit_render.rb
index ae04b53825..99e96a9547 100644
--- a/actionpack/lib/action_controller/metal/implicit_render.rb
+++ b/actionpack/lib/action_controller/metal/implicit_render.rb
@@ -7,7 +7,12 @@ module ActionController
end
def default_render(*args)
- render(*args)
+ if template_exists?(action_name.to_s, _prefixes, variants: request.variant)
+ render(*args)
+ else
+ logger.info "No template found for #{self.class.name}\##{action_name}, rendering head :no_content"
+ head :no_content
+ end
end
def method_for_action(action_name)
diff --git a/actionpack/test/controller/mime/respond_to_test.rb b/actionpack/test/controller/mime/respond_to_test.rb
index 1f5f66dc80..21407f3966 100644
--- a/actionpack/test/controller/mime/respond_to_test.rb
+++ b/actionpack/test/controller/mime/respond_to_test.rb
@@ -608,19 +608,29 @@ class RespondToControllerTest < ActionController::TestCase
end
def test_invalid_variant
+ logger = ActiveSupport::LogSubscriber::TestHelper::MockLogger.new
+ old_logger, ActionController::Base.logger = ActionController::Base.logger, logger
+
@request.variant = :invalid
- assert_raises(ActionView::MissingTemplate) do
- get :variant_with_implicit_rendering
- end
+ get :variant_with_implicit_rendering
+ assert_response :no_content
+ assert_equal 1, logger.logged(:info).select{ |s| s =~ /No template found/ }.size, "Implicit head :no_content not logged"
+ ensure
+ ActionController::Base.logger = old_logger
end
def test_variant_not_set_regular_template_missing
- assert_raises(ActionView::MissingTemplate) do
- get :variant_with_implicit_rendering
- end
+ get :variant_with_implicit_rendering
+ assert_response :no_content
end
def test_variant_with_implicit_rendering
+ @request.variant = :implicit
+ get :variant_with_implicit_rendering
+ assert_response :no_content
+ end
+
+ def test_variant_with_implicit_template_rendering
@request.variant = :mobile
get :variant_with_implicit_rendering
assert_equal "text/html", @response.content_type
diff --git a/actionview/lib/action_view/lookup_context.rb b/actionview/lib/action_view/lookup_context.rb
index 36855ec3d0..4452dcfed5 100644
--- a/actionview/lib/action_view/lookup_context.rb
+++ b/actionview/lib/action_view/lookup_context.rb
@@ -126,7 +126,7 @@ module ActionView
@view_paths.find_all(*args_for_lookup(name, prefixes, partial, keys, options))
end
- def exists?(name, prefixes = [], partial = false, keys = [], options = {})
+ def exists?(name, prefixes = [], partial = false, keys = [], **options)
@view_paths.exists?(*args_for_lookup(name, prefixes, partial, keys, options))
end
alias :template_exists? :exists?