许多rails具有相同标志的型号。什么是最佳做法?

时间:2011-03-02 17:09:19

标签: ruby-on-rails ruby-on-rails-3 activerecord data-modeling models

我的一个铁轨项目有许多具有相同标志的型号:已批准。 我不喜欢为这么多车型管理“已批准”的旗帜,我正在寻求一个干燥的解决方案。 我找到了一些像flag_shih_tzu或can_flag这样的插件,但我认为它们只适用于模型。

你知道一些插件可以同时标记许多模型吗? 我认为我是一个很好的解决方案(没有插件)应该使用多态关联,你同意吗?

非常感谢, 的Alessandro

3 个答案:

答案 0 :(得分:4)

如果您正在寻找的是一种将所有功能存储在一个地方的方法,但是可以从所有可标记的模型中访问它们,我建议为它们编写一个mixin。例如,在lib / approved.rb中,您可以拥有模块:

module Approved

    # Any approval functions/constants that don't belong in a model go here...

    module Mixin
        def self.included(klass)
            klass.class_eval do
                # Class-levell model macros can be run here
                named_scope :approved,   {:conditions => {:approved => true}}
                named_scope :unapproved, {:conditions => {:approved => false}}
            end
        end

        def approved?
            return (self.approved == true)
        end

        # Other shared model functions go here...
    end
end

然后,只需将mixin包含在需要这些功能的所有模型中:

class Approvable < ActiveRecord::Base
    include Approved::Mixin

    # etc.
end

希望有所帮助!

答案 1 :(得分:1)

我的应用程序中存在类似问题,我们有10个左右的模型都需要批准,并且不想在任何地方复制代码。在我们的示例中,我们使用transitions作为我们的工作流gem,因此我们没有标记approved,而是有一个字符串列state

需要批准的模型如下所示:

class Comment < A:RB
  include ApprovalWorkflow
end

然后我们有一个如下所示的工作流程:

# /app/workflows/approval_workflow.rb
module ApprovalWorkflow
  def self.included(klass)
    klass.class_eval do
      state_machine do
        .. workflow junk goes here .. 
      end
    end
  end
end

所以这里发生的是我们已经创建了一个模块,您可以将其视为一个不属于任何地方的匿名代码片段(阅读更多有关模块以了解为什么这是一个糟糕的描述),然后我们在我们的类中包含混合功能。现在我们的评论课有批准工作流程了!

在您的情况下,假设您要保留批准标记,您可以添加默认验证,某些方法(如approve!(user)或范围)进行查询。

我希望这会有所帮助。

答案 2 :(得分:0)

使用多态关联不是解决方案,除非它们都是相同的基础对象。请记住,对于继承,父级应该与子级具有is-a关系。

您可以做的是创建一个Approval模型,并与可批准的模型建立一对一的关系。