From: Ehsanul Hoque Date: 2009-09-22T17:56:19+09:00 Subject: Re: Monkeypatching multiple classes with similar methods --_1f93cb12-2b01-4045-b125-bf1c00468b6f_ Content-Type: text/plain; charset="Windows-1252" Content-Transfer-Encoding: quoted-printable Hey. You just have a tiny couple of bugs. Try this instead (untested=2C but= you get the idea): [Klass1=2C Klass2=2C Klass3].each do |klass| klass.module_eval do alias_method :original_meth=2C :meth def meth(*stuff=2C &block) puts "#{self.class}.meth has been patched" original_meth(*stuff=2C &block) end end end > Date: Tue=2C 22 Sep 2009 17:45:06 +0900 > From: lasso@lassoweb.se > Subject: Monkeypatching multiple classes with similar methods > To: ruby-talk@ruby-lang.org >=20 > Hello! >=20 > I'm trying to monkeypatch a number of related classes that all > implements the same method (meth). The methods all take one required > argument (stuff) but some of the individual methods may require more > arguments (or a block). All I want to do in each call to meth is to > print some debug data and then pass the incoming arguments to the > original method. This works great as long as I know the exact number > of arguments required=2C but when the number of arguments starts to > change my code breaks badly. Is there any way (in ruby 1.8.7) to > "copy" the original method signature when defining my own replacement > method? >=20 > /lasso >=20 > --- CODE START --- > class Klass1 > def meth(stuff) > puts "You've sent #{stuff} to #{self.class}.meth" > end > end >=20 > class Klass2 > def meth(stuff=2C &block) > block_text =3D block_given? ? 'with' : 'without' > puts "You've sent #{stuff} to #{self.class}.meth #{block_text} a > block" > end > end >=20 > class Klass3 > def meth(stuff=2C morestuff) > puts "You've sent #{stuff} to #{self.class}.meth" > end > end >=20 > # Broken monkeypatching. Only works on Klass1 > [Klass1=2C Klass2=2C Klass3].each do |klass| > klass.module_eval do > alias_method :original_meth=2C :meth > def meth(stuff) > puts "#{self.class}.meth has been patched" > original_meth(stuff) > end > end > end >=20 > Klass1.new.meth('one') > Klass2.new.meth('two') { 'three' } # Block is not passed after > monkeypatching > Klass2.new.meth('four') > Klass3.new.meth('five'=2C 'six') # Raises ArgumentError after > monkeypatching > --- CODE END --- >=20 =0A= _________________________________________________________________=0A= Microsoft brings you a new way to search the web. Try Bing=99 now=0A= http://www.bing.com?form=3DMFEHPG&publ=3DWLHMTAG&crea=3DTEXT_MFEHPG_Core_ta= gline_try bing_1x1= --_1f93cb12-2b01-4045-b125-bf1c00468b6f_--