Posted almost 9 years ago. Visible to the public. Repeats.

Custom error pages in Rails

Starting with Rails 3.2, there is a nicer way to display custom error pages (i.e. "page not found") that does not interfere with ExceptionNotifier. (I'm not sure about Airbrake et al.)

José Valim has posted this on his blog Archive , here is a slightly more verbose rundown:

  1. Register your own app as the application responsible for showing error pages by adding

    config.exceptions_app = self.routes

    to your config/application.rb.

  2. Add routes for the error pages, by appending this to your config/routes.rb:

    match '/404' => 'errors#not_found', via: :all match '/422' => 'errors#server_error', via: :all match '/500' => 'errors#server_error', via: :all
  3. Add an ErrorsController like this one:

    class ErrorsController < ApplicationController skip_before_action :verify_authenticity_token def not_found render :status => 404, :formats => [:html] end def server_error render :status => 500, :formats => [:html] end end
  4. Add the corresponding views.

  5. Add some tests, for example a cucumber feature:

    @allow-rescue Scenario: 404 page When I go to the path "/foobar" Then the page should be titled "Page not found" And I should see "We're sorry, but couldn't find the page you requested" And the response status should be "404"
  6. (Optional) In a request spec, you'll need to stub a few config variables (in the cached Rails environment config):

    # spec/requests/error_pages_spec.rb describe "Error pages" do def handle_errors env_config = Rails.application.env_config show_exceptions = env_config['action_dispatch.show_exceptions'] local_requests = env_config['action_dispatch.show_detailed_exceptions'] # Disables Rails built-in error reports, so our custom error application # can handle them and render it's own templates. This overrides the cached # setting in Rails.application.config.consider_all_requests_local env_config['action_dispatch.show_detailed_exceptions'] = false # Render exception templates instead of raising exceptions. # This is the cached setting for # Rails.application.config.action_dispatch.show_exceptions env_config['action_dispatch.show_exceptions'] = true yield env_config['action_dispatch.show_exceptions'] = show_exceptions env_config['action_dispatch.show_detailed_exceptions'] = local_requests end around(:each) do |example| handle_errors(&example) end # ... end

Additional notes

  • You cannot modify headers, so you can't modify the session, cookies etc.
  • You won't see this in development, except if you set config.consider_all_requests_local = false in your config/development.rb.
  • Rails will automatically choose a particular error page for some types of unhandled exceptions
  • It is also possible to edit the error pages directly in public/ of you application. Since these files are static, they e.g. do not allow you to access you assets to reuse layout settings. On the other hand, every error request is processed by the application worker and can not be served directly from the webserver.

Once an application no longer requires constant development, it needs periodic maintenance for stable and secure operation. makandra offers monthly maintenance contracts that let you focus on your business while we make sure the lights stay on.

Owner of this card:

Tobias Kraze
Last edit:
3 months ago
by Emanuel De
About this deck:
We are makandra and do test-driven, agile Ruby on Rails software development.
License for source code
Posted by Tobias Kraze to makandra dev
This website uses short-lived cookies to improve usability.
Accept or learn more