Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Custom Error Pages in Rails?

Tags:

I need to implement a custom error page in my rails application that allows me to use erb.

I've been following this tutorial (http://blog.tommilewski.net/2009/05/custom-error-pages-in-rails/) and I cannot get it to work locally (or remotely). I am running Rails 2.3.5

Here's the gist of the approach.

1) in the 'application_controller', I over ride the "render_optional_error_file(status_code)" method, and set the visibility to "protected", like this.

protected  def render_optional_error_file(status_code)   known_codes = ["404", "422", "500"]   status = interpret_status(status_code)    if known_codes.include?(status_code)     render :template => "/errors/#{status[0,3]}.html.erb", :status => status, :layout => 'errors.html.erb'   else     render :template => "/errors/unknown.html.erb", :status => status, :layout => 'errors.html.erb'   end end  def local_request?   true end 

I also created a folder within views called errors and created the following views: 404.html.erb, 422.html.erb, 500.html.erb,unknown.html.erb and I created a new layout "errors.html.erb"

I can't seem to get it to work. I've been trying to trigger the 404 page by navigating to http://localhost:3000/foobar -- but, instead of getting the new 404.html.erb, I seem to be getting the standard apache 500 error. This happens when I try both mongrel_rails start and mongrel_rails start -e production.

like image 289
rsturim Avatar asked Feb 10 '10 16:02

rsturim


2 Answers

I would suggest using exceptions to render such error pages, so you can use inheritance to group your error messages...

First, declare some (I usually do it in application_controller.rb)

class Error404 < StandardError; end class PostNotFound < Error404; end 

Then add code to ApplicationController to handle them

class ApplicationController < ActionController::Base    # ActionController::RoutingError works in Rails 2.x only.   # rescue_from ActionController::RoutingError, :with => :render_404   rescue_from Error404, :with => :render_404   rescue_from PostNotFound, :with => :render_post_not_found     def render_404     respond_to do |type|        type.html { render :template => "errors/error_404", :status => 404, :layout => 'error' }        type.all  { render :nothing => true, :status => 404 }      end     true   end    def render_post_not_found     respond_to do |type|        type.html { render :template => "errors/shop_not_found", :status => 404, :layout => 'error' }        type.all  { render :nothing => true, :status => 404 }      end     true   end end 

This renders errors/error_404 with the errors layout. Should get you started :)

And in your target_controller:

raise PostNotFound unless @post 

Edit

Note for Rails 3

for a longer explanation on why ActionController::RoutingError doesn't work for rails 3: Rails 3.0 Exception Handling.

Rails ticket 4444

"If your application relies on engines that extend your app with their own routes, things will break because those routes will never get fired!"

like image 98
galileoMonkey Avatar answered Sep 20 '22 14:09

galileoMonkey


Firstly - have you deleted the file: 'public/500.html' If that file exists, it will override anything else that you try to do.

Secondly, using an explicit "rescue_from" in the controller (as explained in the other comment) - is a good option if you need to fine-tune the response to different kinds of errors.

like image 33
Taryn East Avatar answered Sep 17 '22 14:09

Taryn East