https://bugs.ruby-lang.org/https://bugs.ruby-lang.org/favicon.ico?17113305112015-06-18T15:39:46ZRuby Issue Tracking SystemRuby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530162015-06-18T15:39:46Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul><li><strong>Description</strong> updated (<a title="View differences" href="/journals/53016/diff?detail_id=38197">diff</a>)</li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530172015-06-18T15:46:50Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul><li><strong>Description</strong> updated (<a title="View differences" href="/journals/53017/diff?detail_id=38198">diff</a>)</li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530182015-06-18T15:48:04Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul><li><strong>Description</strong> updated (<a title="View differences" href="/journals/53018/diff?detail_id=38199">diff</a>)</li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530192015-06-18T15:49:32Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul><li><strong>Description</strong> updated (<a title="View differences" href="/journals/53019/diff?detail_id=38200">diff</a>)</li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530202015-06-18T15:51:31Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul><li><strong>Description</strong> updated (<a title="View differences" href="/journals/53020/diff?detail_id=38201">diff</a>)</li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530212015-06-18T15:52:31Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul><li><strong>Description</strong> updated (<a title="View differences" href="/journals/53021/diff?detail_id=38202">diff</a>)</li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530252015-06-18T19:11:55Zfunny_falcon (Yura Sokolov)funny.falcon@gmail.com
<ul></ul><p>This is "hidden feature", not the bug: <code>Proc.new</code> can consume unnamed block passed to method.<br>
It makes possible following code:</p>
<pre><code class="ruby syntaxhl" data-language="ruby"> <span class="k">def</span> <span class="nf">do_now_or_later</span>
<span class="k">if</span> <span class="n">can_do_now?</span>
<span class="k">yield</span>
<span class="k">else</span>
<span class="n">do_it_later</span> <span class="no">Proc</span><span class="p">.</span><span class="nf">new</span>
<span class="k">end</span>
<span class="k">end</span>
<span class="n">do_now_or_later</span> <span class="p">{</span> <span class="nb">puts</span> <span class="s1">'hi'</span> <span class="p">}</span>
</code></pre>
<p>In your case block is passed to implicit <code>Proc.new</code> in the implementation of <code>define_method</code>.</p>
<p>I agree, that it is a bit weird feature.</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530262015-06-18T19:31:47Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul></ul><p>This feature buzzes and wiggles aerials like a bug.</p>
<p>I cannot see why is it needed for your example. It is pretty explicit and has no hidden calls. Both the <code>yield</code> and <code>Proc.new</code> are used intentionally, while in my examples they weren't.</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530272015-06-18T21:56:18Z0x0dea (D.E. Akers)0x0dea+redmine@gmail.com
<ul></ul><p>Andrew, what would you like Ruby to do when you attempt to define a method with no body?</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530302015-06-18T22:45:58Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul></ul><p>I'd expect Ruby to do any of two options:</p>
<ul>
<li>Either provide a method with empty proc (<code>Proc.new</code>)</li>
<li>Or call <code>SyntaxError</code> as a strict way to ask for the programmer's intention</li>
</ul>
<p>I think any of these options could follow POLA better than the current one</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530332015-06-19T02:25:37Z0x0dea (D.E. Akers)0x0dea+redmine@gmail.com
<ul></ul><blockquote>
<ul>
<li>Either provide a method with empty proc (<code>Proc.new</code>)</li>
</ul>
</blockquote>
<p>That is, in fact, exactly what Ruby is doing:</p>
<pre><code class="ruby syntaxhl" data-language="ruby"><span class="k">def</span> <span class="nf">build</span>
<span class="no">Class</span><span class="p">.</span><span class="nf">new</span> <span class="p">{</span> <span class="n">define_method</span> <span class="ss">:foo</span><span class="p">,</span> <span class="no">Proc</span><span class="p">.</span><span class="nf">new</span> <span class="p">}</span>
<span class="k">end</span>
<span class="n">build</span><span class="p">{</span> <span class="ss">:bar</span> <span class="p">}.</span><span class="nf">new</span><span class="p">.</span><span class="nf">foo</span> <span class="c1"># => :bar</span>
</code></pre>
<p><code>Proc.new</code>, called without an explicit block, will instead attempt to use the one that was passed to the surrounding method:</p>
<pre><code class="ruby syntaxhl" data-language="ruby"><span class="k">def</span> <span class="nf">foo</span>
<span class="no">Proc</span><span class="p">.</span><span class="nf">new</span><span class="p">.</span><span class="nf">call</span> <span class="mi">1</span>
<span class="k">end</span>
<span class="n">foo</span> <span class="p">{</span> <span class="o">|</span><span class="n">x</span><span class="o">|</span> <span class="n">x</span> <span class="o">+</span> <span class="mi">1</span> <span class="p">}</span> <span class="c1"># => 2</span>
</code></pre>
<p>Note well that methods need not explicitly declare that they take a block. This double whammy of implicit behavior is certainly "astonishing" the first time you encounter it, but it all hangs together in the final analysis.</p>
<blockquote>
<ul>
<li>Or call <code>SyntaxError</code> as a strict way to ask for the programmer's intention</li>
</ul>
</blockquote>
<p>This is a semantic rather than syntactic concern, and Ruby does warn against it. That it doesn't raise an <code>ArgumentError</code> as it does for standalone <code>Proc.new</code> is indeed unexpected, and may well be a bug.</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530342015-06-19T05:49:51Znepalez (Andrew Kozin)andrew.kozin@gmail.com
<ul></ul><p>Not, in my examples (from the initial post) it does not do that, but something different. Namely, it doesn't assigning a <strong>new</strong> proc (that would be OK)</p>
<p>Instead, the interpreter looks around in search <strong>what else</strong> it could use when I doesn't send a proc, then takes what it found somewhere and pushes it to the method.</p>
<p>MRI doesn't let me decide whether the method should be called without a proc (that should be interpreted as asking for <code>Proc.new</code>, as in your example).<br>
<strong>This</strong> is the bug, not the way it works out the <code>:define_method</code> call.</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=530352015-06-19T05:54:28Znobu (Nobuyoshi Nakada)nobu@ruby-lang.org
<ul><li><strong>Status</strong> changed from <i>Open</i> to <i>Closed</i></li></ul><p>Applied in changeset r50971.</p>
<hr>
<p>proc.c: ArgumentError if no block</p>
<ul>
<li>proc.c (rb_mod_define_method): now requires a block direct to<br>
this method call. <a href="/issues/11283">[ruby-core:69655]</a> [Bug <a class="issue tracker-1 status-5 priority-4 priority-default closed" title="Bug: Block assigned implicitly (Closed)" href="https://bugs.ruby-lang.org/issues/11283">#11283</a>]</li>
</ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=531702015-06-30T03:25:49Zusa (Usaku NAKAMURA)usa@garbagecollect.jp
<ul><li><strong>Backport</strong> changed from <i>2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN</i> to <i>2.0.0: WONTFIX, 2.1: REQUIRED, 2.2: REQUIRED</i></li></ul> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=537882015-08-14T07:50:00Znagachika (Tomoyuki Chikanaga)nagachika00@gmail.com
<ul><li><strong>Backport</strong> changed from <i>2.0.0: WONTFIX, 2.1: REQUIRED, 2.2: REQUIRED</i> to <i>2.0.0: WONTFIX, 2.1: REQUIRED, 2.2: WONTFIX</i></li></ul><p>The change of define_method's behavior is added into NEWS file at r50971. I think this is a spec change even thought original behavior is confusing.</p> Ruby master - Bug #11283: Block assigned implicitlyhttps://bugs.ruby-lang.org/issues/11283?journal_id=538302015-08-17T08:55:56Zusa (Usaku NAKAMURA)usa@garbagecollect.jp
<ul><li><strong>Backport</strong> changed from <i>2.0.0: WONTFIX, 2.1: REQUIRED, 2.2: WONTFIX</i> to <i>2.0.0: WONTFIX, 2.1: WONTFIX, 2.2: WONTFIX</i></li></ul><p>I agree with you, chikanaga-san.</p>