In Ruby module Forwardable, you can find the following line
#{accessor}.__send__(:#{method}, *args, &block)
This lets delegate some method to another class simplifying the code. For example,
Instead of writing
class Owner
def phone
'457364'
end
end
class Space
def phone
owner.phone
end
def owner
@owner ||= Owner.new
end
end
is shorter and easier to read
require 'forwardable'
class Owner
def phone
'457364'
end
end
class Space
extend Forwardable
delegate :phone => :owner
def owner
@owner ||= Owner.new
end
end
I want to explain why it uses __send__
instead of send
.
The send
method can be override. Example:
class Foo
def __send__(*args, &block)
false
end
def bar
true
end
end
Foo.new.bar
=> true
Foo.new.send(:bar)
=> false
Foo.new.__send__(:bar)
=> true
To avoid conflicts, specially in gems or libraries when the context where it will be used is unknown, always use __send__
.
Ruby warns when trying to redefine it:
warning: redefining `__send__' may cause serious problems