In Rails, error handling mainly works through a combination of Ruby exception handling (begin-rescue-end blocks) and Rails’ built-in mechanisms for managing errors in web requests, models, and controllers.
Difference between Error and Exception
In programming, you come across the terms exception and error, which have different meanings.
An exception represents an error condition in a program. Exceptions provide a mechanism for stopping the execution of a program. They work somewhat like break statements in that they cause the program flow to jump to another location. However, unlike break, the location may be another layer of the program stack. Unhandled exception causes the program to stop.
An error, on the other hand, is an unwanted or unexpected event, which occurs during the execution of a program, i.e., at runtime, that disrupts the normal flow of the programâs instructions.
Ruby has a hierarchy of exception classes, highest level of exception handling StandardError class.
Exception Handling Keywords
The following keywords are important for exception handling −
- begin – end − A set of instructions where probable exception appears is put inside the begin â end block.
- raise − The raise statement allows the program to explicitly raise an exception.
- ensure − The ensure statement allows the program to ensure that a block of code is executed, whether an exception is raised or not
- rescue − A block where an exception is captured.
The standard Ruby exception handling syntax is represented as −
begin# risky operationrescueSomeError=> e # handle errorend
The rescue_from Method
In a Rails application, you usually don’t write explicit begin-rescue blocks for each action of a controller. Instead, Rails provides structured ways to catch errors.
Starting from the release 2.0, Rails provides a clean way to rescue exceptions in a controller, mapping specific error classes to corresponding handlers. Instead of rescue, Rails has the rescue_from method.
rescue_from is a class-level method specific to Ruby on Rails, typically used in controllers or ActiveSupport-based classes. This enables you to handle exceptions for the entire class, without repeating the same error handling code in every action or method.
You can also specify the type of exception you want to handle and provides a block or method reference that will be called when that exception is raised.
rescue_from is useful for handling application-level exceptions and keeping your code DRY (Don’t Repeat Yourself).
classBooksController<ApplicationController rescue_from ActiveRecord::RecordNotFound, with::record_not_founddefshow@book=Book.find(params[:id])endprivatedefrecord_not_foundrender plain:"Book not found", status::not_foundendend</pre>
In this code snippet, if Book.find(params[:id]) raises ActiveRecord::RecordNotFound, the record_not_found method is called.
rescue_from can be used at the controller level or in ApplicationController to handle errors app-wide.
Model-Level Error Handling
When saving models (save, update, etc.), Rails provides a validation errors system.
@user=User.new(email:"")[email protected] # successelse# @user.error full_messages will have validation error messagesendSince failed saves don't raise exceptions by default, you inspect @model.errors to know what went wrong. If you want to force exceptions on validation failures, use save! or update! −
[email protected]!rescueActiveRecord::RecordInvalid=> e puts e.message endRails Error Reporter
The Rails framework also has the Active Support Error Reporter feature that is a common interface for error reporting services. It provides a standard way to collect errors in your application and report them to your preferred service (monitoring service such as Sentry).
- Error Handling refers to how your code reacts to exceptions (rescue, fallback actions, custom error pages, etc.).
- Error Reporting, on the other hand, is how your application logs, notifies, or tracks errors (e.g., showing logs, sending error notifications, etc.).
To rescue and report any unhandled error, you can use the handle method −
Rails.error.handle do do_something!end
If an error is raised, it will be reported and swallowed.
Alternatively, if you want to report the error but not swallow it, you can use record −
Rails.error.record do do_something!end
Ways to Report Methods
Rails error reporter has four methods that allow you to report methods in different ways −
Rails.error.handle
This method will report any error raised within the block. It will then swallow the error, and the rest of your code outside the block will continue as normal.
Rails.error.record
This method will report errors to all registered subscribers and then reraise the error, meaning that the rest of your code won't execute.
Rails.error.report
You can also manually report errors by calling this method −
begin# coderescueStandardError=> e Rails.error.report(e)end
Rails.error.unexpected
You can report any unexpected error by calling this method.
Leave a Reply