ruby - 覆盖方法然后还原

ste*_*ard 7 ruby extension-methods

我试图找到一种方法,我可以覆盖一个方法,做一些事情,然后恢复,而不会留下任何文物.

我已经使用mocha实现了这一点,但显然这不会在生产应用程序中飞行.请注意,新方法有参数而旧方法没有.

示例如下

require 'rubygems'
require 'mocha'

class Example

  def to_something
    self.stubs(:attribs => other(1))
    r = attribs_caller
    self.unstub(:attribs)
    r
  end

  def other(int)
    {"other" => int }
  end

  def attribs_caller
    attribs
  end

  def attribs
    {"this" => 1 }
  end

end

a1 = Example.new

puts a1.attribs_caller  #=> this1
puts a1.to_something    #=> other1
puts a1.attribs_caller  #=> this1
Run Code Online (Sandbox Code Playgroud)

ste*_*lag 8

class String
  alias orig_reverse reverse
  def reverse(n)
    'fooled you. '*n
  end
end

puts "ab".reverse(2)
#=> fooled you fooled you

# clean up:
class String
  alias reverse orig_reverse
  remove_method(:orig_reverse)
end

puts "ab".reverse #=> ba
Run Code Online (Sandbox Code Playgroud)


Gui*_*nal 3

另一种无需创建额外方法即可实现此目的的方法是:

class Foo
  def bar
    :old_method
  end
end

Foo.new.bar # => :old_method

$old_method = Foo.new.method(:bar)

class Foo
  def bar
    :new_method
  end
end

Foo.new.bar # => :new_method

class Foo
  define_method($old_method.name, &$old_method)
end

Foo.new.bar # => :old_method
Run Code Online (Sandbox Code Playgroud)

我认为这比使用别名方法更好。在 Ruby 中,方法也是对象。我只是在破坏对象(方法)与类的关联之前获取对象的引用。我添加相同的方法后。如果您使用undef关键字从类中删除该方法,它也有效。不好的一点是你必须有一个类的对象来获取方法的引用。