我想通过 ActiveSupport::Concern 将一个 module 里的实例方法引入到 module 中,但发现在 include 后,不能马上使用这个方法。
代码如下:
# writable.rb
module Writable
  extend ActiveSupport::Concern
  included do
    attr_reader :write_worker
  end
  def set_options(worker)
    @worker = worker
  end
end
# user.rb
class User < ApplicationRecord
  include Writable
  set_options("UserWorker") # 这里因为每个model需要传入不同的参数,所在需要单独在每个被include的model中调用
end
这时候我去 new 这个类的时候会出错,找不到 set_options 方法
# console
user = User.new
# => undefined method `set_options' for #<Class:0x007f909bec0508>
如果我把这个方法放在 after_initialize 里,就可以正常,但感觉很啰嗦
# user.rb
class User < ApplicationRecord
  include Writable
  after_initialize do
    set_options(xxxx)
  end
end
请问有没有办法在不使用 after_initialize 的情况下让代码晚优雅简练地达到目的?
之前搞错了概念,用如下方式就可以在实例方法里取类成员属性,不用加 after_initialize 了。
module Workable
  def self.included(base)
    base.extend ClassMethods
    #include InstanceMethods
    base.send(:include, InstanceMethods)
  end
  module ClassMethods
    attr_reader :worker
    def set_options(worker: nil)
      @worker = worker
    end
  end
  module InstanceMethods
    def get_options
      puts "worker: #{self.class.worker}"
    end
  end
end
class Test
  include Workable
  set_options(worker: 'worker1')
end
class Test2
  include Workable
  set_options(worker: 'worker2')
end
Test.new.get_options # => worker1
Test2.new.get_options # => worker2