---
title: How to Customize Rails Form Error Handling
author: Victor Cobos
tags: Rails, Design
published_at: '2024-12-11T22:59:00+01:00'
updated_at: '2024-12-13T12:17:24+01:00'
canonical_url: https://www.dotruby.com/articles/how-to-customize-rails-form-error-handling
---

# How to Customize Rails Form Error Handling

If you've worked with Rails forms, you've likely encountered the infamous `.field_with_errors wrapper`. While it's designed to help highlight invalid fields, it can wreak havoc on your HTML structure and CSS styles. Fear not — there's an easy way to disable it!

By default, when Rails detects validation errors on a form field, it wraps the form element in a `<div class="field_with_errors">` (coming from [ActiveModelInstanceTag](https://api.rubyonrails.org/classes/ActionView/Helpers/ActiveModelInstanceTag.html#method-i-error_wrapping)).

```
<!-- erb -->
<%= form.label :name %>
<%= form.text_field :name %>

<!-- html -->
<label for="name">Name</label>
<input type="text" name="name" id="name">

<!-- html with error -->
<div class="field_with_errors">
  <label for="name">Name</label>
</div>
<div class="field_with_errors">
  <input type="text" name="name" id="name">
</div>
```

This behavior is intended to make it easier to style invalid fields. For example, you can add CSS like this to highlight error states:

```css
.field_with_errors input,
.field_with_errors textarea,
.field_with_errors select {
  border: 2px solid red;
  background-color: #ffe6e6;
}
```

While this works well in theory, the extra wrapper often introduces issues:

* It can disrupt CSS layouts, especially in grid or flexbox designs.
* It adds unwanted HTML, making your markup harder to debug.
* It can interfere with JavaScript selectors that expect specific input fields.

This additional wrapper can cause more harm than good. And more importantly maybe you prefer to write your own components to highlight form validation errors as it allows you to style the field- and label-inputs exactly how you want.
Thankfully, there are ways to handle it gracefully.

## Solution 1: Disable the Wrapper Entirely

The simplest solution is to disable the .field_with_errors wrapper entirely so that Rails outputs the form field as-is, without wrapping it in additional HTML.

Create an initializer file named `config/initializers/field_with_errors.rb`:

```ruby
ActionView::Base.field_error_proc = proc do |html_tag, instance|
  html_tag.html_safe
end
```

This approach ensures that Rails outputs the form field without any additional HTML. It’s clean, simple, and avoids layout issues.

However, this method doesn’t provide a way to visually highlight fields with errors. If you still want to style invalid fields, consider the next solution.

## Solution 2: Add an Error Class Dynamically

For more control over styling, you can append an error class (e.g., `is-invalid`) directly to the form field when an error occurs. This keeps your HTML clean and ensures invalid fields are visually distinguishable.

Use this initializer instead:

```ruby
ActionView::Base.field_error_proc = proc do |html_tag, instance|
  error_class = "is-invalid"

  element = Nokogiri::HTML::DocumentFragment.parse(html_tag)
  node = element.children.first

  if node
    node["class"] = class_names(
      node["class"],
      error_class
    )
  end

  element.to_s.html_safe
end
```

This approach uses `Nokogiri` to parse the HTML, dynamically appends the `is-invalid` class to the field, and ensures the output is clean without wrapping it in a `div`.
This method retains the ability to style fields with errors while avoiding the layout-breaking wrapper.

## CSS Workaround: Embrace the Wrapper

If you'd rather not change Rails's default behavior, you can adapt your CSS to work with `.field_with_errors`.
Using `display: contents;` makes the `.field_with_errors` wrapper effectively invisible in the layout. It removes the wrapper's box model while keeping its children intact, ensuring your layout stays consistent without altering the HTML structure.

```css
.field_with_errors {
  display: contents;
}

.field_with_errors input,
.field_with_errors textarea,
.field_with_errors select {
  border: 2px solid red;
  background-color: #ffe6e6;
}
```

This CSS ensures that the wrapper doesn't interfere with your layout while still highlighting invalid fields.

## Global Impact of field_error_proc

Customizing `ActionView::Base.field_error_proc` affects all Rails form builders globally. This means any gem or library that relies on Rails form helpers will also inherit your customizations. While this can be convenient for uniform styling, it could lead to unintended side effects.

To limit the impact, you can wrap your form field logic in a helper method or a custom builder that applies the same customization but only within the scope of your own forms.

## Security Note: Beware of XSS Vulnerabilities

When customizing form error handling, always consider the potential for `XSS` (Cross-Site Scripting) vulnerabilities. Rails escapes output by default when using form helpers like `text_fiel`, `text_area` ... so yo're usually safe. However, if your customization involves manually inserting error messages or modifying user-generated content in the HTML, ensure that all content is properly escaped.

You can use the `html_safe` method only for strings you know are safe, and prefe `h()` or `ERB::Util.html_escape` to escape potentially dangerous content.

## Conclusion

Depending on your needs, you now have three approaches to handle Rails's `.field_with_errors` behavior:

1. Disable the wrapper entirely for clean, minimal HTML.
2. Add an error class dynamically for fine-grained control over styling.
3. Style the wrapper with CSS to embrace the default behavior without layout issues.

Choose the solution that best fits your project,
and take back control of your forms ✊
