【问题标题】:Rails STI override model_name in parent class for all subclassesRails STI 覆盖所有子类的父类中的 model_name
【发布时间】:2015-04-08 23:34:16
【问题描述】:

我在 Rails 应用程序中使用 STI,为了不必为所有子类定义路由,我在每个子类中添加了以下内容:

def self.model_name
  Mapping.model_name
end

在上面的示例中,Mapping 是父模型名称。示例:

class UserMapping < Mapping; end

必须把它放在每个子类中并不是很干燥,所以我正在寻找一种方法以某种方式在父类中设置它,以便从父类继承的每个类都会自动将模型名称设置为父模型名字。

也许还有更好的方法来克服与设置 model_name 无关的 STI 引起的路由问题 - 我愿意接受建议!

提前致谢!

【问题讨论】:

    标签: ruby-on-rails model routing sti


    【解决方案1】:

    把它放在你的Mapping 类中:

    class Mapping < ActiveRecord::Base
      def self.inherited(subclass)
        super
        def subclass.model_name
          superclass.model_name
        end
      end
    end
    

    之后,Mapping 的所有子类也将继承父类的model_name

    【讨论】:

      【解决方案2】:

      另一种选择是覆盖超类中的model_name 方法以返回自定义ActiveModel::Name

      class Mapping < ActiveRecord::Base
        def self.model_name
          ActiveModel::Name.new(base_class)
        end
      end
      

      默认情况下model_name 将当前类作为第一个参数传递给ActiveModel::Name.new,因此每个子类将根据其类接收不同的名称。 ActiveRecord 模型有一个 base_class 方法,我们可以使用它来获取单表继承层次结构的基础。

      如果您愿意,您也可以将其命名为完全不同的名称。当您尝试将模型转换为新名称时,这可能很有用:

      class Mapping < ActiveRecord::Base
        def self.model_name
          ActiveModel::Name.new(self, nil, "AnotherMapping")
        end
      end
      

      More in the docs

      【讨论】:

        猜你喜欢
        • 2021-05-02
        • 2018-03-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-06-03
        • 2017-11-18
        相关资源
        最近更新 更多