新手问题 errors.add 不能拦截对象保存吗?

ad583255925 · March 23, 2017 · Last by easonlovewan replied at March 24, 2017 · 1630 hits

我好像记得以前 errors 不为空的时候,不能保存的啊

最好能贴代码出来

class Aaa
  before_save :check_num

  def check_num
    errors.add(:id, '不能保存就对了')
  end
end

Aaa.new.save
=> true

error 对 validation 有效,而 save 动作已经在 validation 之后。如果要在 save 拦截,可以抛出异常。

这就是 validate 的用处啊

加上 return false

class Aaa
  before_save :check_num

  def check_num
    errors.add(:id, '不能保存就对了')
    return false # 看这里
  end
end

update:

  1. 抱歉,rails 5 更新了规则,return false 不能中断后续的 callback,使用 throw :abort
  2. validate 更合适
Reply to leekelby

这样虽然也能达到相同的目的,但是不推荐,eg:

class Foo < ApplicationRecord
  before_save :foobar

  def foobar
    errors.add(:base, "I'm a foo")
    false
  end
end

begin
  foo = Foo.new
  foo.save!
rescue => ex
  puts ex # Output as "Failed to save the record"
end

正确的方法是用 validate

class Foo < ApplicationRecord
  validate :foobar

  def foobar
    errors.add(:base, "I'm a foo")
  end
end
Reply to mengqing

楼上用 validate 是正解

Reply to leekelby

这种写法不行哦,这个方法返回 false 了,然而不影响 save

Reply to leekelby

" 狗拿耗子"

You need to Sign in before reply, if you don't have an account, please Sign up first.