4

When going to on object's show page with an id that doesn't exist, the RecordNotFonud exception is thown. Is there a way I can redirect to some error page, or maybe a different action when this error is thrown?

2
  • 2
    Just a note: redirecting instead of returning 404 code is not a good idea. It might be better if you just render some view and return it with HTTP code 404. (rescue .. render :action => 'not_found', :status => 404) Commented Aug 30, 2011 at 13:49
  • 2
    People have answered your question, but I feel everyone is missing an important detail. Your production server will automatically handle a RecordNotFound exception by rendering the file public/404.html. A routing error will also render the 404 page in production. Most other errors will cause the server to render the 500 error (internal server error). Commented Aug 30, 2011 at 14:30

6 Answers 6

11

You may use rescue_from if you are using Rails 3:

class ApplicationController < ActionController::Base rescue_from ActiveRecord::RecordNotFound, :with => :render_404 def render_404 respond_to do |format| format.html { render :action => "errors/404.html.erb", :status => 404 } # and so on.. end end end 

Yes, you can also do a redirect instead of render, but this is not a good idea. Any semi-automatic interaction with your site will think that the transfer was successfull (because the returned code was not 404), but the received resource was not the one your client wanted.

Sign up to request clarification or add additional context in comments.

Comments

1

In development mode you'll see the exception details but it should automatically render the 404.html file from your public directory when your app is running in production mode.

Comments

1

See http://api.rubyonrails.org/classes/ActiveSupport/Rescuable/ClassMethods.html. Rails has nice features for exception handling.

Comments

1

I generally do something like this in my ApplicationController

class ApplicationController < ActionController::Base rescue_from ActiveRecord::RecordNotFound, :with => :routing_error private def routing_error redirect_to(root_url, :alert => "Sorry, the page you requested could not be found.") end end 

Comments

0

If you need to handle more than one specific exception, use rescue_action or rescue_action_in_public, the difference in to hook local requests or not (development/production in common). I prefer to use in_public , because need to review exception's backtrace in development mode.

take a look at my source code:

class ApplicationController < ActionController::Base include CustomExceptionsHandler .... end module CustomExceptionsHandler # Redirect to login/dashboard path when Exception is caught def rescue_action_in_public(exception) logger.error("\n !!! Exception !!! \n #{exception.message} \n") case exception.class.to_s when "Task::AccessDenied" logger.error(" !!! 403 !!!") notify_hoptoad(exception) //catch this kind of notification to Hoptoad render_403 when "AuthenticatedSystem::PermissionDenied" logger.error(" !!! 403 !!!") render_403 when "Task::MissingDenied" logger.error(" !!! 404 !!!") notify_hoptoad(exception) render_404 when "ActionController::RoutingError" logger.error(" !!! 404 !!!") render_404 else notify_hoptoad(exception) redirect_to(current_user.nil? ? login_path : dashboard_path) and return false end end private #403 Forbidden def render_403 respond_to do |format| format.html { render :template => "common/403", :layout => false, :status => 403 } format.xml { head 403 } format.js { head 403 } format.json { head 403 } end return false end #404 Not Found def render_404 respond_to do |format| format.html { render :template => "common/404", :layout => false, :status => 404 } format.xml { head 404 } format.js { head 404 } format.json { head 404 } end return false end end 

Comments

-1

Use a begin - rescue - end construct to catch the exception and do something useful with it.

userid=2 begin u=User.find userid rescue RecordNotFound redirect_to "/errorpage" #Go to erropage if you didn't find the record exit end redirect_to u # Go to the user page 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.