如何动态选择Rails模型进行实例化?

时间:2017-04-16 19:27:11

标签: ruby-on-rails ruby oop

我有两个处理特定工作的“引擎”,每个工具都使用不同的工具/ apis。我有一个Engine模型,它包含它们之间的公共数据/行为,但每个Engine都有其他特定的字段/方法。

class Engine
  field :name
  field :status
end

class DefaultEngine
  field :job_id

  def process
     # default engine process
     # ...
  end
end

class SpecialEngine

  def process
    # special engine process
    # ...
  end
end

class Site
  field :engine, type: String, default: '::DefaultEngine'
end

我想要做的是让Engine负责子类化正确的引擎,具体取决于site.engine值。例如,在控制器中我想要执行以下操作:

def start
  job = Engine.create()
  job.process
end

我不想直接引用这两个引擎。相反,我希望Engine负责确定哪个是正确的引擎。处理此问题的方法是什么,以便Engine.create可以返回SpecialEngineDefaultEngine的实例。

2 个答案:

答案 0 :(得分:3)

由于此标记为ruby-on-rails,因此您可以使用constantize

site.engine # => 'SpecialEngine', your string field
site.engine.constantize # => SpecialEngine, class
site.engine.constantize.new # => #<SpecialEngine:0x007fc52c9893a8>, engine instance

答案 1 :(得分:1)

class Site
  field :engine, type: String, default: '::DefaultEngine'

  def engine_class
     @engine_class ||= engine.constantize
  end 
end
def start
  job = site.engine_class.create
  job.process
end