Permalink
Browse files

Add caution and restyle components

git-svn-id: http://svn-commit.rubyonrails.org/rails/trunk@3577 5ecf4fe2-1ee6-0310-87b1-e25e094e27de
  • Loading branch information...
1 parent 1377943 commit e90bbbdd837ffc83dccbd05528c4f1521e3956ee @dhh dhh committed Feb 12, 2006
View
2 actionpack/lib/action_controller/assertions.rb
@@ -302,7 +302,7 @@ def assert_dom_not_equal(expected, actual, message="")
end
# ensures that the passed record is valid by active record standards. returns the error messages if not
- def assert_valid(record)
+ def assert_valid(record)
clean_backtrace do
assert record.valid?, record.errors.full_messages.join("\n")
end
View
105 actionpack/lib/action_controller/components.rb
@@ -1,18 +1,18 @@
module ActionController #:nodoc:
- # Components allows you to call other actions for their rendered response while executing another action. You can either delegate
+ # Components allow you to call other actions for their rendered response while executing another action. You can either delegate
# the entire response rendering or you can mix a partial response in with your other content.
#
# class WeblogController < ActionController::Base
# # Performs a method and then lets hello_world output its render
# def delegate_action
# do_other_stuff_before_hello_world
- # render_component :controller => "greeter", :action => "hello_world", :params => { "person" => "david" }
+ # render_component :controller => "greeter", :action => "hello_world", :params => { :person => "david" }
# end
# end
#
# class GreeterController < ActionController::Base
# def hello_world
- # render_text "#{@params['person']} says, Hello World!"
+ # render :text => "#{params[:person]} says, Hello World!"
# end
# end
#
@@ -22,11 +22,18 @@ module ActionController #:nodoc:
# <%= render_component :controller => "greeter", :action => "hello_world" %>
#
# It is also possible to specify the controller as a class constant, bypassing the inflector
- # code to compute the controller class at runtime. Therefore,
+ # code to compute the controller class at runtime:
#
# <%= render_component :controller => GreeterController, :action => "hello_world" %>
- #
- # would work as well and be slightly faster.
+ #
+ # == When to use components
+ #
+ # Components should be used with care. They're significantly slower than simply splitting reusable parts into partials and
+ # conceptually more complicated. Don't use components as a way of separating concerns inside a single application. Instead,
+ # reserve components to those rare cases where you truly have reusable view and controller elements that can be employed
+ # across many applications at once.
+ #
+ # So to repeat: Components are a special-purpose approach that can often be replaced with better use of partials and filters.
module Components
def self.included(base) #:nodoc:
base.extend(ClassMethods)
@@ -51,6 +58,7 @@ module ClassMethods
def uses_component_template_root
path_of_calling_controller = File.dirname(caller[0].split(/:\d+:/).first)
path_of_controller_root = path_of_calling_controller.sub(/#{controller_path.split("/")[0..-2]}$/, "") # " (for ruby-mode)
+
self.template_root = path_of_controller_root
end
end
@@ -68,57 +76,60 @@ def render_component(options) #:doc:
def render_component_as_string(options) #:doc:
component_logging(options) do
response = component_response(options, false)
+
if redirected = response.redirected_to
- render_component_as_string redirected
+ render_component_as_string(redirected)
else
response.body
end
- end
+ end
end
-
+
private
- def component_response(options, reuse_response)
- c_class = component_class(options)
- c_request = request_for_component(c_class.controller_name, options)
- c_response = reuse_response ? @response : @response.dup
- c_class.process(c_request, c_response, self)
+ def component_response(options, reuse_response)
+ klass = component_class(options)
+ request = request_for_component(klass.controller_name, options)
+ response = reuse_response ? @response : @response.dup
+
+ klass.process(request, response, self)
+ end
+
+ # determine the controller class for the component request
+ def component_class(options)
+ if controller = options[:controller]
+ controller.is_a?(Class) ? controller : "#{controller.camelize}Controller".constantize
+ else
+ self.class
+ end
+ end
+
+ # Create a new request object based on the current request.
+ # The new request inherits the session from the current request,
+ # bypassing any session options set for the component controller's class
+ def request_for_component(controller_name, options)
+ request = @request.dup
+ request.session = @request.session
+
+ request.instance_variable_set(
+ :@parameters,
+ (options[:params] || {}).with_indifferent_access.regular_update(
+ "controller" => controller_name, "action" => options[:action], "id" => options[:id]
+ )
+ )
+
+ request
end
-
- # determine the controller class for the component request
- def component_class(options)
- if controller = options[:controller]
- if controller.is_a? Class
- controller
- else
- "#{controller.camelize}Controller".constantize
- end
+
+ def component_logging(options)
+ if logger
+ logger.info "Start rendering component (#{options.inspect}): "
+ result = yield
+ logger.info "\n\nEnd of component rendering"
+ result
else
- self.class
+ yield
end
end
-
- # Create a new request object based on the current request.
- # The new request inherits the session from the current request,
- # bypassing any session options set for the component controller's class
- def request_for_component(controller_name, options)
- sub_request = @request.dup
- sub_request.session = @request.session
- sub_request.instance_variable_set(:@parameters,
- (options[:params] || {}).with_indifferent_access.regular_update(
- "controller" => controller_name, "action" => options[:action], "id" => options[:id])
- )
- sub_request
- end
-
-
- def component_logging(options)
- unless logger then yield else
- logger.info("Start rendering component (#{options.inspect}): ")
- result = yield
- logger.info("\n\nEnd of component rendering")
- result
- end
- end
end
end
end
View
3 actionpack/lib/action_controller/filters.rb
@@ -1,7 +1,6 @@
module ActionController #:nodoc:
module Filters #:nodoc:
- def self.append_features(base)
- super
+ def self.included(base)
base.extend(ClassMethods)
base.send(:include, ActionController::Filters::InstanceMethods)
end

0 comments on commit e90bbbd

Please sign in to comment.