Defining methods from a runtime template in ruby

Let's say I have the following classes:

class Foo
  attr_accessor :name, :age
end

class Bar
    def initialize(name)
        @foo = Foo.new
        @foo.name = name
    end
end

I would like to define an accessor on Bar, which is just an alias of foo.name. Easy enough:

def name
  @foo.name
end

def name=(value)
  @foo.name = value
end

With just one property, this is simple enough. However, let's say Foo provides several properties that I want to open through Bar. Instead of defining each method manually, I want to do something like this, although I know that the syntax is incorrect:

[:name, :age].each do |method|
  def method
    @foo.method
  end

  def method=(value)
    @foo.method = value
  end
end

So ... What is the correct way to define such methods?

+3
source share
3 answers
[:name, :age].each do |method|
  define_method(method) do
    foo.send(method)
  end

  define_method("#{method}=") do |value|
    foo.send("#{method}=", value)
  end
end
+1
source

To dynamically define a method, you can use define_methodone that takes the method name as a character or string argument.

send, .

[:name, :age].each do |method|
  define_method(method) do
    @foo.send(method)
  end

  define_method("#{method}=") do |value|
    @foo.send("#{method}=", value)
  end
end
+2

. Delegator Ruby , .

+1
source

Source: https://habr.com/ru/post/1788049/