From 20d4a375e2df9bde23b027581099ca5c8515950d Mon Sep 17 00:00:00 2001 From: usa Date: Wed, 30 Apr 2014 06:32:24 +0000 Subject: merge revision(s) 43682,43727,43752,43759: [Backport #9560] * lib/delegate.rb (Delegator#send): override to get rid of global function interference. [Fixes GH-449] * lib/delegate.rb (Delegator#send): separate from method_missing so that super calls proper method. * lib/delegate.rb (Delegator#method_missing): try private methods defined in Kernel after the target. [Fixes GH-449] * lib/delegate.rb (SimpleDelegator#__getobj__): target object must be set. * lib/delegate.rb (DelegateClass#__getobj__): ditto. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_2_0_0@45747 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- lib/delegate.rb | 27 +++++++++++++++++++++------ 1 file changed, 21 insertions(+), 6 deletions(-) (limited to 'lib') diff --git a/lib/delegate.rb b/lib/delegate.rb index e46e4f8c23..b4d495edea 100644 --- a/lib/delegate.rb +++ b/lib/delegate.rb @@ -43,9 +43,16 @@ class Delegator < BasicObject kernel = ::Kernel.dup kernel.class_eval do + alias __raise__ raise [:to_s,:inspect,:=~,:!~,:===,:<=>,:eql?,:hash].each do |m| undef_method m end + private_instance_methods.each do |m| + if /\Ablock_given\?\z|iterator\?\z|\A__raise__\z/ =~ m + next + end + undef_method m + end end include kernel @@ -69,9 +76,15 @@ class Delegator < BasicObject def method_missing(m, *args, &block) target = self.__getobj__ begin - target.respond_to?(m) ? target.__send__(m, *args, &block) : super(m, *args, &block) + if target.respond_to?(m) + target.__send__(m, *args, &block) + elsif ::Kernel.respond_to?(m, true) + ::Kernel.instance_method(m).bind(self).(*args, &block) + else + super(m, *args, &block) + end ensure - $@.delete_if {|t| %r"\A#{Regexp.quote(__FILE__)}:#{__LINE__-2}:"o =~ t} if $@ + $@.delete_if {|t| %r"\A#{Regexp.quote(__FILE__)}:(?:#{[__LINE__-7, __LINE__-5, __LINE__-3].join('|')}):"o =~ t} if $@ end end @@ -142,7 +155,7 @@ class Delegator < BasicObject # method calls are being delegated to. # def __getobj__ - raise NotImplementedError, "need to define `__getobj__'" + __raise__ ::NotImplementedError, "need to define `__getobj__'" end # @@ -150,7 +163,7 @@ class Delegator < BasicObject # to _obj_. # def __setobj__(obj) - raise NotImplementedError, "need to define `__setobj__'" + __raise__ ::NotImplementedError, "need to define `__setobj__'" end # @@ -265,6 +278,7 @@ end class SimpleDelegator Sinclair # def __setobj__(obj) - raise ArgumentError, "cannot delegate to self" if self.equal?(obj) + __raise__ ::ArgumentError, "cannot delegate to self" if self.equal?(obj) @delegate_sd_obj = obj end end @@ -339,10 +353,11 @@ def DelegateClass(superclass) methods -= [:to_s,:inspect,:=~,:!~,:===] klass.module_eval do def __getobj__ # :nodoc: + __raise__ ::ArgumentError, "not delegated" unless defined?(@delegate_dc_obj) @delegate_dc_obj end def __setobj__(obj) # :nodoc: - raise ArgumentError, "cannot delegate to self" if self.equal?(obj) + __raise__ ::ArgumentError, "cannot delegate to self" if self.equal?(obj) @delegate_dc_obj = obj end methods.each do |method| -- cgit v1.2.3