用Bootstrap/Rails样式化表单错误信息

22
我的Rails表单使用Bootstrap后,错误信息看起来很糟糕。有人知道如何解决这个问题,让错误信息更好看吗?我使用的是Rails和Bootstrap。
我的表单(它是一个helper)就像这样:
<%= form_for(@user) do |f| %>
  <% if @user.errors.any? %>
    <div id="error_explanation">
      <h2><%= pluralize(@user.errors.count, "error") %> prohibited this user from being saved:</h2>

      <ul>
      <% @user.errors.full_messages.each do |msg| %>
        <li><%= msg %></li>
      <% end %>
      </ul>
    </div>
  <% end %>

  <div class="form-inline">
    <%= f.text_field :email, class:'input-large', placeholder:'Test' %>
<!--   </div>
  <div class="actions"> -->
    <%= f.submit class:'btn btn-large btn-success' %>
  </div>
<% end %>

The error message

8个回答

24
请看Michael Hartl在railstutorial中是如何做的。 screenshot 这就是所使用的CSS:
#error_explanation {
  color: #f00;
  ul {
    list-style: none;
    margin: 0 0 18px 0;
  }
}

.field_with_errors {
  @extend .control-group;
  @extend .error;
 }

He描述了这里的一切。
如果您也想在每行开头有一个小星星,您必须将其包含在表单中:
     <div id="error_explanation">
        <h2><%= pluralize(@user.errors.count, "error") %> prohibited this user from being saved:</h2>
        <ul>
          <% @user.errors.full_messages.each do |msg| %>
            <li> * <%= msg %></li>    <--- insert here
          <% end %>
        </ul>
     </div>
      ...

3
在开始时搭建一个表单并在之后重构代码绝对是个好主意,这样你就可以拥有一个干净的首次设置。KentTucky提到观察Michael Hartl的过程是一个非常好的建议。谢谢@KentTucky。 - Fawyd
这需要包括Bootstrap源SASS代码。这会使你的JS和CSS编译资产变得更大。当使用.error.control-group时,无法使用CDN版本。 - Chloe
在Bootstrap 4中,我们应该在输入框上扩展.is-invalid类。我使用.field_with_errors input { @extend .is_invalid }使其正常工作。 - Igbanam

15

我有点晚意识到,但今天我在Rails 4和Bootstrap 3中遇到了这个问题,最终我创建了一个视图助手来使用面板显示错误:

Rails 4 / Bootstrap 3

def errors_for(object)
    if object.errors.any?
        content_tag(:div, class: "panel panel-danger") do
            concat(content_tag(:div, class: "panel-heading") do
                concat(content_tag(:h4, class: "panel-title") do
                    concat "#{pluralize(object.errors.count, "error")} prohibited this #{object.class.name.downcase} from being saved:"
                end)
            end)
            concat(content_tag(:div, class: "panel-body") do
                concat(content_tag(:ul) do
                    object.errors.full_messages.each do |msg|
                        concat content_tag(:li, msg)
                    end
                end)
            end)
        end
    end
end

enter image description here

Rails 4 / Bootstrap 4 Beta

def errors_for(object)
    if object.errors.any?
        content_tag(:div, class: "card border-danger") do
            concat(content_tag(:div, class: "card-header bg-danger text-white") do
                concat "#{pluralize(object.errors.count, "error")} prohibited this #{object.class.name.downcase} from being saved:"
            end)
            concat(content_tag(:div, class: "card-body") do
                concat(content_tag(:ul, class: 'mb-0') do
                    object.errors.full_messages.each do |msg|
                        concat content_tag(:li, msg)
                    end
                end)
            end)
        end
    end
end

enter image description here

Rails 4 / Bootstrap 4 Beta 列表组变化

def errors_for(object)
    if object.errors.any?
        content_tag(:div, class: "card border-danger") do
            concat(content_tag(:div, class: "card-header bg-danger text-white") do
                concat "#{pluralize(object.errors.count, "error")} prohibited this #{object.class.name.downcase} from being saved:"
            end)
            concat(content_tag(:ul, class: 'mb-0 list-group list-group-flush') do
                object.errors.full_messages.each do |msg|
                    concat content_tag(:li, msg, class: 'list-group-item')
                end
            end)
        end
    end
end

输入图像描述

我把它放在application_helper里,然后在我的表单视图中调用它。

<%= errors_for(@user) %>

也许有人会偶然发现这篇内容,发现它很有用。


2
也许您可以添加一张屏幕截图,展示您的消息是什么样子的? - Cas

5

假设有人在使用Bootstrap 4 alpharails 5以及bootstrap_form_for gem时遇到问题,这里提供一些帮助。

我使用的是:

<div class="form-group">
  <%= f.alert_message "Please fix the errors below." %>
</div>

这看起来非常漂亮。

enter image description here


4

我已经在Rails 5和Bootstrap 4中实现了Rabbott的视图帮助程序

def errors_for(object)
    if object.errors.any?
      content_tag(:div, class: 'card text-white bg-danger mb-3') do
        concat(content_tag(:div, class: 'card-header') do
          concat(content_tag(:h4) do
            concat "#{pluralize(object.errors.count, 'error')} prohibited this #{object.class.name.downcase} from being saved:"
          end)
        end)
        concat(content_tag(:div, class: 'card-body') do
          concat(content_tag(:ul) do
            object.errors.full_messages.each do |msg|
              concat content_tag(:li, msg)
            end
          end)
        end)
      end
    end
  end

它看起来像这样: 输入图像描述


3

Bootstrap 4 Alpha 6

我从https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-alpha.6/css/bootstrap.css复制了编译后的Bootstrap CSS。

然后搜索了.has-danger,复制了所有类,对.has-danger进行了搜索和替换为.field_with_errors,同时添加了.field_with_errors label

.field_with_errors label,
.field_with_errors .form-control-feedback,
.field_with_errors .form-control-label,
.field_with_errors .col-form-label,
.field_with_errors .form-check-label,
.field_with_errors .custom-control {
  color: #d9534f;
}

.field_with_errors .form-control {
  border-color: #d9534f;
}

.field_with_errors .input-group-addon {
  color: #d9534f;
  border-color: #d9534f;
  background-color: #fdf7f7;
}

.field_with_errors .form-control-danger {
  background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='%23d9534f' viewBox='-2 -2 7 7'%3E%3Cpath stroke='%23d9534f' d='M0 0l3 3m0-3L0 3'/%3E%3Ccircle r='.5'/%3E%3Ccircle cx='3' r='.5'/%3E%3Ccircle cy='3' r='.5'/%3E%3Ccircle cx='3' cy='3' r='.5'/%3E%3C/svg%3E");
}

我无法正确显示输入组附加项,因为它会用 <div> 包装输入。

bootstrap 4 with rails errors

文档:https://v4-alpha.getbootstrap.com/components/forms/#validation

老实说,有些类别没有被使用,因为Rails没有明显的方法来设置错误字段的类别。

对于错误列表,我只是使用了这个简单的类:

#error_explanation {
  color: red;
}

0

也许更简单的方法是在表单本身上搜索ID和类。适用于任何组合。

默认情况下,这些行是包含在脚手架中以排列错误消息的。您可以根据需要在css.scss文件中扩展它们:

.field_with_errors {
  padding: 2px;
  background-color: red;
  display: table;
}

#error_explanation {
  width: 450px;
  border: 2px solid red;
  padding: 7px 7px 0;
  margin-bottom: 20px;
  background-color: #f0f0f0;
}

#error_explanation h2 {
  text-align: left;
  font-weight: bold;
  padding: 5px 5px 5px 15px;
  font-size: 12px;
  margin: -7px -7px 0;
  background-color: #c00;
  color: #fff;
}

#error_explanation ul li {
  font-size: 12px;
  list-style: square;
}

如果出现问题,请在开发者模式下检查导航器。在那里,您应该能够找到Rails创建的所有HTML和CSS...


0
我创建了一个自定义初始化器,使每个字段下面都有自己的错误。
# app/config/initializers/bootstrap_form_errors_customizer.rb

ActionView::Base.field_error_proc = proc do |html_tag, instance|
  is_label_tag = html_tag =~ /^<label/
  class_attr_index = html_tag.index 'class="' 

  def format_error_message_to_html_list(error_msg)
    html_list_errors = "<ul></ul>"
    if error_msg.is_a?(Array)
      error_msg.each do |msg|
        html_list_errors.insert(-6,"<li>#{msg}</li>")
      end
    else 
      html_list_errors.insert(-6,"<li>#{msg}</li>")
    end
    html_list_errors
  end

  invalid_div =
    "<div class='invalid-feedback'>#{format_error_message_to_html_list(instance.error_message)}</div>"

  
  if class_attr_index && !is_label_tag
    html_tag.insert(class_attr_index + 7, 'is-invalid ')
    html_tag + invalid_div.html_safe
  elsif !class_attr_index && !is_label_tag
    html_tag.insert(html_tag.index('>'), ' class="is-invalid"')
    html_tag + invalid_div.html_safe
  else
    html_tag.html_safe
  end
end

0

只使用SCSS的另一种变体

#error_explanation{
  background: #f23551;
  color: #fff;
  border-radius: 4px;
  margin-bottom: 20px;
  h2{
    padding: 20px;
    margin: 0;
    font-size: 20px;
  }
  ul{
    background: #fff;
    color: #e5324a;
    border: 1px solid #F23551;
    margin: 0;
    list-style: none;
    padding: 14px 0;
    li{
      padding: 4px 20px;
      &:before {
        content: '×';
        font-weight: bold;
        font-size: 20px;
        margin-right: 10px;
      }
    }
  }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接