https://bugs.ruby-lang.org/https://bugs.ruby-lang.org/favicon.ico?17113305112013-12-02T04:13:56ZRuby Issue Tracking SystemRuby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=433192013-12-02T04:13:56Zelight (Evan Light)evan@tripledogdare.net
<ul></ul><p>Ran against trunk:</p>
<pre><code>-e:1:in `<main>': private method `foo' called for :foo:Symbol (NoMethodError)
</code></pre> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=436532013-12-14T07:50:17Znobu (Nobuyoshi Nakada)nobu@ruby-lang.org
<ul><li><strong>Status</strong> changed from <i>Open</i> to <i>Assigned</i></li><li><strong>Assignee</strong> set to <i>nobu (Nobuyoshi Nakada)</i></li></ul> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=438422013-12-23T15:54:51Zjeremyevans0 (Jeremy Evans)merch-redmine@jeremyevans.net
<ul></ul><p>There's only two days until the release of 2.1.0, and this still hasn't been fixed. This is a serious regression that breaks existing code (among other things, it causes Sequel's tests to freeze). If this can't be fixed before 2.1.0, I think r40022 should be reverted on the 2.1 branch, and the feature should be moved to 2.2.0. Assuming this is fixed on trunk before 2.1.0, it should be immediately backported to the 2.1 branch.</p> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=438532013-12-23T20:52:42Znobu (Nobuyoshi Nakada)nobu@ruby-lang.org
<ul></ul><p><code>send</code> is irrelevant here.<br>
If you make <code>define_method</code> public, it isn't needed.</p>
<pre><code class="ruby syntaxhl" data-language="ruby"><span class="n">c</span> <span class="o">=</span> <span class="no">Class</span><span class="p">.</span><span class="nf">new</span> <span class="p">{</span>
<span class="k">class</span> <span class="o"><<</span> <span class="nb">self</span>
<span class="kp">public</span> <span class="ss">:define_method</span>
<span class="k">end</span>
<span class="p">}</span>
<span class="n">c</span><span class="p">.</span><span class="nf">define_method</span><span class="p">(</span><span class="ss">:foo</span><span class="p">)</span> <span class="p">{}</span>
<span class="n">c</span><span class="p">.</span><span class="nf">new</span><span class="p">.</span><span class="nf">foo</span> <span class="c1">#=> NoMethodError</span>
</code></pre>
<p>Your code just reflects the default visibility at the top level.</p> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=438662013-12-24T16:28:22Znobu (Nobuyoshi Nakada)nobu@ruby-lang.org
<ul><li><strong>Status</strong> changed from <i>Assigned</i> to <i>Closed</i></li><li><strong>% Done</strong> changed from <i>0</i> to <i>100</i></li></ul><p>This issue was solved with changeset r44380.<br>
Jeremy, thank you for reporting this issue.<br>
Your contribution to Ruby is greatly appreciated.<br>
May Ruby be with you.</p>
<hr>
<p>proc.c: make method by define_method public</p>
<ul>
<li>proc.c (rb_mod_define_method): consider visibility only if self<br>
in the caller is same as the receiver, otherwise make public as<br>
well as old behavior. <a href="/issues/9005">[ruby-core:57747]</a> [Bug <a class="issue tracker-1 status-5 priority-4 priority-default closed" title="Bug: object.send(:define_method, ...){...} creates private method (Closed)" href="https://bugs.ruby-lang.org/issues/9005">#9005</a>]<br>
<a href="/issues/9141">[ruby-core:58497]</a> [Bug <a class="issue tracker-1 status-5 priority-4 priority-default closed" title="Bug: define_singleton_method creates private method (Closed)" href="https://bugs.ruby-lang.org/issues/9141">#9141</a>]</li>
<li>vm.c (rb_vm_cref_in_context): return ruby level cref if self is<br>
same.</li>
</ul> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=438682013-12-24T16:34:51Znobu (Nobuyoshi Nakada)nobu@ruby-lang.org
<ul><li><strong>Backport</strong> set to <i>1.9.3: DONTNEED, 2.0.0: DONTNEED, 2.1.0: REQUIRED</i></li></ul> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=495872014-10-22T17:25:55Zscotttam (Scott Tamosunas)tamosunas@gmail.com
<ul></ul><p>This isn't fixed on 2.1.3. Has that changeset not made it into a release?</p>
<pre><code>2.1.3 :001 > RUBY_VERSION
=> "2.1.3"
2.1.3 :002 > class Foo
2.1.3 :003?>
2.1.3 :004 > private
2.1.3 :005?>
2.1.3 :006 > define_method("bar") { puts "BAR" }
2.1.3 :007?> end
=> :bar
2.1.3 :008 >
2.1.3 :009 > Foo.new.bar
NoMethodError: private method `bar' called for #<Foo:0x007ff90b8e3198>
from (irb):9
from /Users/me/.rvm/rubies/ruby-2.1.3/bin/irb:11:in `<main>'`
</code></pre>
<p>Where this works on 2.0</p>
<pre><code>2.0.0-p451 :001 > RUBY_VERSION
=> "2.0.0"
2.0.0-p451 :002 > class Foo
2.0.0-p451 :003?>
2.0.0-p451 :004 > private
2.0.0-p451 :005?>
2.0.0-p451 :006 > define_method("bar") { puts "BAR" }
2.0.0-p451 :007?> end
=> #<Proc:0x0000010103cd00@(irb):6 (lambda)>
2.0.0-p451 :008 >
2.0.0-p451 :009 > Foo.new.bar
BAR
</code></pre> Ruby master - Bug #9005: object.send(:define_method, ...){...} creates private methodhttps://bugs.ruby-lang.org/issues/9005?journal_id=496482014-10-26T15:58:08Zjeremyevans0 (Jeremy Evans)merch-redmine@jeremyevans.net
<ul></ul><p>Scott Tamosunas wrote:</p>
<blockquote>
<p>This isn't fixed on 2.1.3. Has that changeset not made it into a release?</p>
<pre><code>2.1.3 :001 > RUBY_VERSION
=> "2.1.3"
2.1.3 :002 > class Foo
2.1.3 :003?>
2.1.3 :004 > private
2.1.3 :005?>
2.1.3 :006 > define_method("bar") { puts "BAR" }
2.1.3 :007?> end
=> :bar
2.1.3 :008 >
2.1.3 :009 > Foo.new.bar
NoMethodError: private method `bar' called for #<Foo:0x007ff90b8e3198>
from (irb):9
from /Users/me/.rvm/rubies/ruby-2.1.3/bin/irb:11:in `<main>'`
</code></pre>
<p>Where this works on 2.0</p>
<pre><code>2.0.0-p451 :001 > RUBY_VERSION
=> "2.0.0"
2.0.0-p451 :002 > class Foo
2.0.0-p451 :003?>
2.0.0-p451 :004 > private
2.0.0-p451 :005?>
2.0.0-p451 :006 > define_method("bar") { puts "BAR" }
2.0.0-p451 :007?> end
=> #<Proc:0x0000010103cd00@(irb):6 (lambda)>
2.0.0-p451 :008 >
2.0.0-p451 :009 > Foo.new.bar
BAR
</code></pre>
</blockquote>
<p>The behavior change here is deliberate, since you are calling <code>define_method</code> inside the class definition after calling private. This bug was that <code>define_method</code> when called outside the class definition was generating private methods, which was fixed before the release of 2.1.0.</p>