https://bugs.ruby-lang.org/https://bugs.ruby-lang.org/favicon.ico?17113305112019-07-13T01:35:37ZRuby Issue Tracking SystemRuby master - Bug #8743: Inconsistent behaviour calling public_methods on class (Plus documentation slightly ambiguous)https://bugs.ruby-lang.org/issues/8743?journal_id=793712019-07-13T01:35:37Zjeremyevans0 (Jeremy Evans)merch-redmine@jeremyevans.net
<ul><li><strong>Status</strong> changed from <i>Open</i> to <i>Closed</i></li><li><strong>Backport</strong> deleted (<del><i>1.9.3: UNKNOWN, 2.0.0: UNKNOWN</i></del>)</li></ul><p>The reason for this interesting behavior is because the documentation for include flag (2nd argument) for <code>public_methods</code> is not precise. It states:</p>
<pre><code>If the all parameter is set to false, only those methods
in the receiver will be listed.
</code></pre>
<p>However, the behavior is actually:</p>
<pre><code>If the all parameter is set to false, the list will include methods
in ancestors, stopping after a non-singleton class is encountered
(including the methods from the non-singleton class).
</code></pre>
<p>The lookup process for <code>Empty.public_methods(false)</code> is something like this:</p>
<ul>
<li>Empty.singleton_class # adds no methods</li>
<li>Object.singleton_class # adds no methods</li>
<li>BasicObject.singleton_class # adds no methods</li>
<li>Class # adds 3 methods <code>[:allocate, :superclass, :new]</code>
</li>
<li>Module # does not get here, as Class is not a singleton class</li>
</ul>
<p>So that is the reason <code>Empty.public_methods(false)</code> gives you <code>[:allocate, :superclass, :new]</code>.</p>
<p><code>B.public_methods(false)</code> including singleton methods from <code>A</code> is similar:</p>
<ul>
<li>B.singleton_class # adds no methods</li>
<li>A.singleton_class # adds 1 method <code>[:bar]</code>
</li>
<li>Object.singleton_class # adds no methods</li>
<li>BasicObject.singleton_class # adds no methods</li>
<li>Class # adds 3 methods <code>[:allocate, :superclass, :new]</code>
</li>
<li>Module # does not get here, as Class is not a singleton class</li>
</ul>
<p>Which is the reason that <code>Bar.public_methods(false)</code> gives you <code>[:bar, :allocate, :superclass, :new]</code>.</p>
<p>I'm not sure it worth updating the documentation to be more precise in this area, but I'm open to suggestions.</p>