lib/inherited_resources/legacy/responder.rb in inherited_resources-0.9.5 vs lib/inherited_resources/legacy/responder.rb in inherited_resources-1.0.pre
- old
+ new
@@ -12,16 +12,15 @@
# end
# end
#
# When a request comes, for example with format :xml, three steps happen:
#
- # 1) respond_with searches for a template at people/index.xml;
+ # 1) responder searches for a template at people/index.xml;
#
- # 2) if the template is not available, it will create a responder, passing
- # the controller and the resource and invoke :to_xml on it;
+ # 2) if the template is not available, it will invoke :to_xml in the given resource;
#
- # 3) if the responder does not respond_to :to_xml, call to_format on it.
+ # 3) if the responder does not respond_to :to_xml, call :to_format on it.
#
# === Builtin HTTP verb semantics
#
# Rails default responder holds semantics for each HTTP verb. Depending on the
# content type, verb and the resource status, it will behave differently.
@@ -79,72 +78,93 @@
# Check polymorphic_url documentation for more examples.
#
class Responder
attr_reader :controller, :request, :format, :resource, :resources, :options
+ ACTIONS_FOR_VERBS = {
+ :post => :new,
+ :put => :edit
+ }
+
def initialize(controller, resources, options={})
@controller = controller
@request = controller.request
@format = controller.formats.first
@resource = resources.is_a?(Array) ? resources.last : resources
@resources = resources
@options = options
+ @action = options.delete(:action)
@default_response = options.delete(:default_response)
end
delegate :head, :render, :redirect_to, :to => :controller
delegate :get?, :post?, :put?, :delete?, :to => :request
- # Undefine :to_json since it's defined on Object
- undef_method :to_json
+ # Undefine :to_json and :to_yaml since it's defined on Object
+ undef_method(:to_json) if method_defined?(:to_json)
+ undef_method(:to_yaml) if method_defined?(:to_yaml)
# Initializes a new responder an invoke the proper format. If the format is
# not defined, call to_format.
#
def self.call(*args)
- responder = new(*args)
- method = :"to_#{responder.format}"
- responder.respond_to?(method) ? responder.send(method) : responder.to_format
+ new(*args).respond
end
+ # Main entry point for responder responsible to dispatch to the proper format.
+ #
+ def respond
+ method = :"to_#{format}"
+ respond_to?(method) ? send(method) : to_format
+ end
+
# HTML format does not render the resource, it always attempt to render a
# template.
#
def to_html
default_render
- rescue ActionView::MissingTemplate
- if get?
- raise
- elsif has_errors?
- render :action => default_action
- else
- redirect_to resource_location
- end
+ rescue ActionView::MissingTemplate => e
+ navigation_behavior(e)
end
# All others formats follow the procedure below. First we try to render a
# template, if the template is not available, we verify if the resource
# responds to :to_format and display it.
#
def to_format
default_render
- rescue ActionView::MissingTemplate
+ rescue ActionView::MissingTemplate => e
raise unless resourceful?
+ api_behavior(e)
+ end
+ protected
+
+ # This is the common behavior for "navigation" requests, like :html, :iphone and so forth.
+ def navigation_behavior(error)
if get?
+ raise error
+ elsif has_errors? && default_action
+ render :action => default_action
+ else
+ redirect_to resource_location
+ end
+ end
+
+ # This is the common behavior for "API" requests, like :xml and :json.
+ def api_behavior(error)
+ if get?
display resource
elsif has_errors?
display resource.errors, :status => :unprocessable_entity
elsif post?
display resource, :status => :created, :location => resource_location
else
head :ok
end
end
- protected
-
# Checks whether the resource responds to the current format or not.
#
def resourceful?
resource.respond_to?(:"to_#{format}")
end
@@ -179,11 +199,11 @@
# Results in:
#
# render :xml => @user, :status => :created
#
def display(resource, given_options={})
- render given_options.merge!(options).merge!(format => resource)
+ controller.send :render, given_options.merge!(options).merge!(format => resource)
end
# Check if the resource has errors or not.
#
def has_errors?
@@ -192,9 +212,9 @@
# By default, render the :edit action for html requests with failure, unless
# the verb is post.
#
def default_action
- request.post? ? :new : :edit
+ @action ||= ACTIONS_FOR_VERBS[request.method]
end
end
-end
+end
\ No newline at end of file