aboutsummaryrefslogtreecommitdiffstats
path: root/actionpack
diff options
context:
space:
mode:
authorYehuda Katz + Carl Lerche <ykatz+clerche@engineyard.com>2009-04-30 15:13:40 -0700
committerYehuda Katz + Carl Lerche <ykatz+clerche@engineyard.com>2009-05-01 17:31:02 -0700
commit4ee3e5b094463383891789f484e927b19fccc744 (patch)
tree4595acf5dc068ebad2f796992d12659d65460337 /actionpack
parentd58b57a3caf4ad434c2be4f63eecd9a1921c7c4a (diff)
downloadrails-4ee3e5b094463383891789f484e927b19fccc744.tar.gz
rails-4ee3e5b094463383891789f484e927b19fccc744.tar.bz2
rails-4ee3e5b094463383891789f484e927b19fccc744.zip
Ported over the concept of public instance methods on controller child classes as callable action methods
Diffstat (limited to 'actionpack')
-rw-r--r--actionpack/lib/action_controller/abstract/base.rb48
-rw-r--r--actionpack/lib/action_controller/new_base/base.rb14
-rw-r--r--actionpack/test/controller/render_test.rb7
-rw-r--r--actionpack/test/new_base/render_test.rb10
-rw-r--r--actionpack/test/new_base/test_helper.rb10
5 files changed, 69 insertions, 20 deletions
diff --git a/actionpack/lib/action_controller/abstract/base.rb b/actionpack/lib/action_controller/abstract/base.rb
index a87a490a2d..3b85ba5565 100644
--- a/actionpack/lib/action_controller/abstract/base.rb
+++ b/actionpack/lib/action_controller/abstract/base.rb
@@ -4,13 +4,44 @@ module AbstractController
attr_internal :response_body
attr_internal :response_obj
attr_internal :action_name
-
- def self.process(action)
- new.process(action)
+
+ class << self
+ attr_reader :abstract
+
+ def abstract!
+ @abstract = true
+ end
+
+ alias_method :abstract?, :abstract
+
+ def internal_methods
+ controller = self
+ controller = controller.superclass until controller.abstract?
+ controller.public_instance_methods(true)
+ end
+
+ def process(action)
+ new.process(action)
+ end
+
+ def hidden_actions
+ []
+ end
+
+ def action_methods
+ @action_methods ||=
+ # All public instance methods of this class, including ancestors
+ public_instance_methods(true).map { |m| m.to_sym }.to_set -
+ # Except for public instance methods of Base and its ancestors
+ internal_methods.map { |m| m.to_sym } +
+ # Be sure to include shadowed public instance methods of this class
+ public_instance_methods(false).map { |m| m.to_sym } -
+ # And always exclude explicitly hidden actions
+ hidden_actions
+ end
end
- def self.inherited(klass)
- end
+ abstract!
def initialize
self.response_obj = {}
@@ -29,6 +60,10 @@ module AbstractController
private
+ def action_methods
+ self.class.action_methods
+ end
+
# It is possible for respond_to?(action_name) to be false and
# respond_to?(:action_missing) to be false if respond_to_action?
# is overridden in a subclass. For instance, ActionController::Base
@@ -45,8 +80,7 @@ module AbstractController
# you must handle it by also overriding process_action and
# handling the case.
def respond_to_action?(action_name)
- respond_to?(action_name) || respond_to?(:action_missing, true)
+ action_methods.include?(action_name) || respond_to?(:action_missing, true)
end
-
end
end \ No newline at end of file
diff --git a/actionpack/lib/action_controller/new_base/base.rb b/actionpack/lib/action_controller/new_base/base.rb
index 9f7a148b3c..00d161289e 100644
--- a/actionpack/lib/action_controller/new_base/base.rb
+++ b/actionpack/lib/action_controller/new_base/base.rb
@@ -1,5 +1,6 @@
module ActionController
class Http < AbstractController::Base
+ abstract!
# :api: public
attr_internal :request, :response, :params
@@ -19,18 +20,15 @@ module ActionController
# :api: public
def controller_path() self.class.controller_path end
-
- # :api: private
- def self.action_methods
- @action_names ||= Set.new(self.public_instance_methods - self::CORE_METHODS)
+
+ # :api: private
+ def self.internal_methods
+ ActionController::Http.public_instance_methods(true)
end
# :api: private
def self.action_names() action_methods end
- # :api: private
- def action_methods() self.class.action_names end
-
# :api: private
def action_names() action_methods end
@@ -44,7 +42,7 @@ module ActionController
def call(env)
@_request = ActionDispatch::Request.new(env)
@_response = ActionDispatch::Response.new
- process(@_request.parameters[:action])
+ process(@_request.parameters[:action].to_sym)
@_response.body = response_body
@_response.prepare!
self
diff --git a/actionpack/test/controller/render_test.rb b/actionpack/test/controller/render_test.rb
index d4a18a673c..e6b2ee7e9f 100644
--- a/actionpack/test/controller/render_test.rb
+++ b/actionpack/test/controller/render_test.rb
@@ -4,6 +4,7 @@ require 'pathname'
module Fun
class GamesController < ActionController::Base
+ # :ported:
def hello_world
end
end
@@ -116,6 +117,7 @@ class TestController < ActionController::Base
render :text => "hello #{@person}"
end
+ # :ported:
def render_action_hello_world
render :action => "hello_world"
end
@@ -839,17 +841,20 @@ class RenderTest < ActionController::TestCase
assert_equal "hello david", @response.body
end
+ # :ported:
def test_render_action
get :render_action_hello_world
assert_template "test/hello_world"
end
+ # :ported:
def test_render_action_hello_world_as_string
get :render_action_hello_world_as_string
assert_equal "Hello world!", @response.body
assert_template "test/hello_world"
end
+ # :ported:
def test_render_action_with_symbol
get :render_action_hello_world_with_symbol
assert_template "test/hello_world"
@@ -949,6 +954,7 @@ class RenderTest < ActionController::TestCase
assert_equal 'application/json', @response.content_type
end
+ # :ported:
def test_render_custom_code
get :render_custom_code
assert_response 404
@@ -1082,6 +1088,7 @@ class RenderTest < ActionController::TestCase
assert_template "test/hello_world"
end
+ # :ported:
def test_nested_rendering
@controller = Fun::GamesController.new
get :hello_world
diff --git a/actionpack/test/new_base/render_test.rb b/actionpack/test/new_base/render_test.rb
index 93bc8d854c..bc7203f294 100644
--- a/actionpack/test/new_base/render_test.rb
+++ b/actionpack/test/new_base/render_test.rb
@@ -35,4 +35,14 @@ module Render
end
end
end
+
+ class TestRenderObjectMethod < SimpleRouteCase
+ describe "Methods on Object are not actions"
+
+ test "raises an exception" do
+ assert_raises(AbstractController::ActionNotFound) do
+ get "/render/blank_render/clone"
+ end
+ end
+ end
end \ No newline at end of file
diff --git a/actionpack/test/new_base/test_helper.rb b/actionpack/test/new_base/test_helper.rb
index 03af5a66a6..d58b83cf7b 100644
--- a/actionpack/test/new_base/test_helper.rb
+++ b/actionpack/test/new_base/test_helper.rb
@@ -34,6 +34,8 @@ end
module ActionController
class Base2 < Http
+ abstract!
+
use AbstractController::Callbacks
use AbstractController::Helpers
use AbstractController::Logger
@@ -80,15 +82,13 @@ module ActionController
end
def respond_to_action?(action_name)
- super || view_paths.find_by_parts(action_name, {:formats => formats, :locales => [I18n.locale]}, controller_path)
+ super || view_paths.find_by_parts?(action_name.to_s, {:formats => formats, :locales => [I18n.locale]}, controller_path)
end
-
- # append_view_path File.join(File.dirname(__FILE__), '..', 'fixtures')
-
- CORE_METHODS = self.public_instance_methods
end
class CompatibleBase2 < Base2
+ abstract!
+
use ActionController::Rails2Compatibility
end
end