Rails将验证放在模块mixin中?

31

我的模型中有一些重复的验证:

validates :name, :length => { :minimum => 2 }, :presence => true, :uniqueness => true
validates :name_seo, :length => { :minimum => 2 }, :presence => true, :uniqueness => true

我该如何将这个放入一个mixin中?如果我只是把它们放在mixin中,我会遇到这个错误。

app/models/validations.rb:5: undefined method `validates' for Validations:Module (NoMethodError)
2个回答

55
module Validations
  extend ActiveSupport::Concern

  included do
    validates :name, :length => { :minimum => 2 }, :presence => true, :uniqueness => true
    validates :name_seo, :length => { :minimum => 2 }, :presence => true, :uniqueness => true
  end
end

validates宏必须在包含者的上下文中评估,而不是模块的上下文(就像您可能正在执行的那样)。


在 Rails 2 中有没有任何方法可以做到这一点? - CantGetANick
只是顺便提一下,我可能会将其命名为“SeoValidatable”,并将其保留在该域中。 - unflores

29

你的模块应该长成这样:

module CommonValidations
  extend ActiveSupport::Concern

  included do
    validates :name, :length => { :minimum => 2 }, :presence => true, :uniqueness => true
    validates :name_seo, :length => { :minimum => 2 }, :presence => true, :uniqueness => true
  end
end

然后在你的模型中:

class Post < ActiveRecord::Base
  include CommonValidations

  ...
end

我在这里使用ActiveSupport::Concern来使代码更加清晰。


1
在Rails 2中是否有可能进行测试?例如,在Rails 3中,您可以使用ActiveModel来创建一个类Test; end并包含我们需要的内容。然后为此模块编写规范。但是在Rails 2版本中呢? - oivoodoo

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