On Mon, 13 Mar 2006 nobu / ruby-lang.org wrote:

> Hi,
>
> At Mon, 13 Mar 2006 13:10:45 +0900,
> ara.t.howard / noaa.gov wrote in [ruby-talk:183841]:
>>      harp:~ > cat a.rb
>>      class Module
>>        def abstract_method m
>>          define_method(m) do |*a|
>>            begin; super; rescue NoMethodError; raise NotImplementedError, m; end
>
> This hides NoMethodError within the super method too.
>
> Instead:
>
>      defined?(super) or raise NotImplementedError, m
>      super

hmmm - but that (both actually) fails here:

     harp:~ > cat a.rb
     class Module
       def abstract_method m
         define_method(m) do |*a|
           defined?(super) ? super : raise(NotImplementedError, m)
         end
       end
     end

     class A
       def foo; 42; end
     end
     class B < A
       abstract_method "foo"
     end

     p B::new.foo


     harp:~ > ruby a.rb
     42


what about this fix?


     harp:~ > cat a.rb
     class Module
       def abstract_method m
         already_respond_to_m = instance_method(m) rescue nil

         define_method(m) do |*a|
           if already_respond_to_m
             raise(NotImplementedError, m)
           else
             defined?(super) ? super : raise(NotImplementedError, m)
           end
         end

       end
     end

     class A
       def foo; 42; end
     end
     class B < A
       abstract_method "foo"
     end

     p B::new.foo


     harp:~ > ruby a.rb
     b.rb:7:in `foo': foo (NotImplementedError)
             from b.rb:23


thoughts?

-a
-- 
share your knowledge.  it's a way to achieve immortality.
- h.h. the 14th dali lama