Rails,自定义验证和错误未显示

时间:2013-09-11 12:51:56

标签: ruby-on-rails error-handling formtastic

我目前有五个布尔属性。我对它们进行了自定义验证:

def limit_impacts
    i = 0
    choices = [self.first_attr, self.sec_attr, self.third_attr, self.fourth_attr, self.fifth_attr]
    choices.each do |choice|
      if choice == true
        i+=1
      end
    end
    if i > 2
      errors[:base] << ("There must be one or two impacts.")
    end
  end

想法是测试是否将其中两个以上设置为true,如果是这种情况,则设置错误。 我正在设置:base error因为它与一个属性没有直接关系。

我只是为了验证而执行此操作:validate :limit_impacts

以及处理此问题的视图部分:

  = f.input :first_attr, :as => :boolean

  = f.input :sec_attr, :as => :boolean

  = f.input :third_attr, :as => :boolean

  = f.input :fouth_attr, :as => :boolean

  = f.input :fifth_attr, :as => :boolean

问题是,当我检查超过2个复选框时,entrie未保存且这是正常的,但视图中没有显示错误消息。

我做错了什么?

顺便说一句,我在rails console中测试了它:

MyModel.errors[:base]
 => ["There must be one or two impacts."]

这种语法也不起作用:

errors.add :base, "message"
编辑:这是我的控制器。这是关于编辑方法。

  def edit
    @page_title = t('projects.edit.title')
    @project = Project.find(params[:id])
    @steps = @project.steps
    @rewards = @project.rewards
    @project_bearer = @project.user
  end

与这些属性无关。

当我尝试通过rails控制台创建项目时,它返回false:

2.0.0p247 :001 > t = Project.create(:social_influence => true, :environmental_influence => true, :economical_influence => true)
=> <Project all my attributes ..>
2.0.0p247 :002 > t.save
(1.2ms)  BEGIN
(2.0ms)  ROLLBACK
=> false 

解决方案:

问题是我的更新方法,渲染和重定向。感谢@delba我解决了它。 如果你想看到解决方案,他的答案的评论中会有讨论。

2 个答案:

答案 0 :(得分:3)

在包含表单的视图中,请确保显示错误:

<%= form_for @my_model do |f|
  <% if @my_model.errors.any? %>
    <ul class="errors">
      <% @my_model.errors.full_messages.each do |msg| %>
        <li><%= msg %></li>
      <% end %>
    </ul>
  <% end %>

  <%# the rest of the form %>
<% end %>

在您的控制器中:

def create
  @my_model = MyModel.new(my_model_params)
  if @my_model.save
    redirect_to 'blabla'
  else
    render :new
  end
end

在你的模特中:

validate :limit_impacts

private

def limit_impacts
  if [first_attr, sec_attr, third_attr, fourth_attr, fifth_attr].count(true) > 2
    errors[:base] << "There must be one or two impacts."
  end
end

答案 1 :(得分:0)

让我们从您的验证方法开始:

def limit_impacts
  choices = [first_attr, sec_attr, third_attr, fourth_attr, fifth_attr]
  errors[:base] << "There must be one or two impacts." if choices.count(true) > 2
end

更干净,不是吗? :)

你能告诉我们你的布局/你的视图位显示错误吗?我会更新答案。