I just noticed something I think is interesting and wanted to see what
everyone felt about it.  Using a quick and dirty scaffold to create a
resource, I found that if I hit a show url, with an invalid id, it
will throw an exception  in html instead of xml.
Here is how you repeat this.
$ rails testing_rest
$ cd testing_rest
$ ./script/generate scaffold person name:string
$ rake db:migrate
$ ./script/server
From another window
$ curl -i -H "Accept: application/xml" -H "Content-Type:
application/
xml" http://127.0.0.1:3000/people
So far, so good.  I was returned an empty array in xml
HTTP/1.1 200 OK
...
Content-Type: application/xml; charset=utf-8
...
<?xml version="1.0" encoding="UTF-8"?>
<nil-classes type="array"/>
-----
Now, I send over a request for a person that doesn''t exist.
$ curl -i -H "Accept: application/xml" -H "Content-Type:
application/
xml" http://127.0.0.1:3000/people/1
I get back a full html debug output in html.  Yuck!
HTTP/1.1 404 Not Found
...
Content-Type: text/html; charset=utf-8
...
I chopped the content for readability, its not what matters.
----
Ok, so I''m in development mode and it will automatically assume I am
local and spit out the debug.  I can handle that, although I still
don''t think it should be in html.
But, if I run db:migrate again under production and start it up (or
modify enviroment.rb), and now hit the external IP of my machine
instead of localhost, I get back the 404 page.  Better, but, its still
coming back in html.
$ curl -i -H "Accept: application/xml" -H "Content-Type:
application/
xml" http://192.168.1.101:3000/people/1
lication/xml" http://192.168.247.20:3000/people/1
HTTP/1.1 404 Not Found
Connection: close
Date: Fri, 29 Feb 2008 02:24:02 GMT
Set-Cookie:
_testing_rest_session=BAh7BiIKZmxhc2hJQzonQWN0aW9uQ29udHJvbGxlcjo6Rmxhc2g6OkZsYXNo
%250ASGFzaHsABjoKQHVzZWR7AA%253D%253D--
d1e3f66166f02f6c78f45395f7c0186d7ab9dcd9; path=/
Status: 404 Not Found
Cache-Control: no-cache
Server: Mongrel 1.1.3
Content-Type: text/html; charset=utf-8
Content-Length: 947
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
       "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en"
lang="en">
...
-------
My question is, shouldn''t this be returning me xml?  I do have a
respond_to block saying that it should spit back xml.  Well, the
problem is in the way rails handles uncaught exceptions.  It doesn''t
do anything with content-type from what I can see.  If there is a
404.html file in public, it will render it as html.  If you don''t have
a 404.html file, it will simply send back a head with 404 as the
response.  However, it still shows content-type as xml.
So, I guess I have three choices.  The first one is to catch that
exception in my action.  The second one is to create a plugin.  The
third is to just not care that I am sending back html to my xml
clients.  I chose the plugin.
What are you all doing?  Does it matter that I am sending content-type
html to an xml client?  What about rss, javascript, etc....
BTW - here is my plugin.  Nothing special I just add the alternate
formats I want to the ALT_FORMATS array.  I also have access to a
template to render instead of a static html file in public.  Not sure
if that gives me anything great, just how I chose to do it at the
time.
Thoughts??
-Dusty Doris
--------
    module MyExceptionHandler
      DEFAULT_CODES = {
        ''ActionController::RoutingError'' => :not_found,
        ''ActionController::UnknownAction'' => :not_found,
        ''ActiveRecord::RecordNotFound'' => :not_found,
        ''ActiveRecord::StaleObjectError'' => :conflict,
        ''ActiveRecord::RecordInvalid'' =>
:unprocessable_entity,
        ''ActiveRecord::RecordNotSaved'' =>
:unprocessable_entity,
        ''ActionController::MethodNotAllowed'' =>
:method_not_allowed,
        ''ActionController::NotImplemented'' =>
:not_implemented,
        ''ActionController::InvalidAuthenticityToken''
=> :unprocessable_entity
      }
      ALT_FORMATS = [:xml, :json, :js, :rss, :atom, :text]
      def rescue_action_in_public(exception)
        @exception = exception
        respond_to do |format|
          format.html do
            render :template => "exceptions/#{return_code.to_s}",
                   :layout   => "exceptions",
                   :status   => return_code
          end
          ALT_FORMATS.each do |f|
            format.send(f) { head :status => return_code }
          end
        end
      end
      def rescue_action_locally(exception)
        respond_to do |format|
          format.html do
            add_variables_to_assigns
            @template.instance_variable_set("@exception", exception)
            @template.instance_variable_set("@rescues_path",
              File.dirname(rescues_path("stub")))
            @template.send!(:assign_variables_from_controller)
            @template.instance_variable_set("@contents",
 
@template.render_file(template_path_for_local_rescue(exception),
              false))
            response.content_type = Mime::HTML
            render_for_file(rescues_path("layout"),
              response_code_for_rescue(exception))
          end
          ALT_FORMATS.each do |f|
            format.send(f) { head :status => return_code }
          end
        end
      end
      private
      def return_code
        DEFAULT_CODES[@exception.class.to_s] || :internal_server_error
      end
    end
With a little
require ''my_exception_handler''
ActionController::Base.send :include, MyExceptionHandler
ActionController::Base.consider_all_requests_local = false
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups
"Ruby on Rails: Talk" group.
To post to this group, send email to
rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org
To unsubscribe from this group, send email to
rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org
For more options, visit this group at
http://groups.google.com/group/rubyonrails-talk?hl=en
-~----------~----~----~----~------~----~------~--~---
Ilan Berci
2008-Feb-29  02:52 UTC
Re: default exception doesn''t render with correct content ty
dusty wrote:> > require ''my_exception_handler'' > ActionController::Base.send :include, MyExceptionHandler > ActionController::Base.consider_all_requests_local = falsesomething like the following will also work.. class Application < ActionController::Base around_filter :catch_exceptions def catch_exceptions begin yield rescue Exception => e render :xml => e.message, :status => 500 end end end -- Posted via http://www.ruby-forum.com/. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en -~----------~----~----~----~------~----~------~--~---
Thanks for the reply. That would be much easier. The filters are nice, unfortunately, it doesn''t catch things like ActionController::RoutingErrors. At least its not for me. It does catch things like notfound errors within an action though. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en -~----------~----~----~----~------~----~------~--~---
Ilan Berci
2008-Feb-29  03:35 UTC
Re: default exception doesn''t render with correct content ty
dusty wrote:> Thanks for the reply. That would be much easier. The filters are > nice, unfortunately, it doesn''t catch things like > ActionController::RoutingErrors. At least its not for me. It does > catch things like notfound errors within an action though.You are right, it won''t catch routing errors as they are thrown before the surround_filters get a chance to party :( ilan -- Posted via http://www.ruby-forum.com/. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en -~----------~----~----~----~------~----~------~--~---