Issue #15886 has been updated by jeremyevans0 (Jeremy Evans).


moio (Silvio Moioli) wrote:
> jeremyevans0 (Jeremy Evans) wrote:
> > moio (Silvio Moioli) wrote:
> > > Well, as a Timeout.timeout user I would like to be able to wrap any code in a block and have a guarantee it will actually terminate after the specified number of seconds - no matter how the wrapped code looks like and especially if it is from a third party.
> > 
> > I don't think this is something Ruby can guarantee.  If you really want that level of control, you need to run the code in a separate process, [...]
> 
> I understand your reasoning - but in this case I would suggest to clarify the method documentation to be more explicit about the limits of what Ruby guarantees here, or equivalently stating the assumptions on the block for the method to behave as documented. If appropriate, a note about implementation details might also guide the programmer to decide the applicability to his/her own use case - at least to me this was not clear at all.
> 
> At the moment all https://docs.ruby-lang.org/en/2.6.0/Timeout.html#method-c-timeout states is "Perform an operation in a block, raising an error if it takes longer than sec seconds to complete", which at least to me naively meant what I stated above.
> 
> Would it make possible to at least treat this as a "documentation bug"?

The documentation is technically accurate, so I would not classify this as a documentation bug. The exception is raised, but the code swallows it.

However, I think it makes sense to expand the Timeout.timeout documentation to mention that you should not use it with blocks that you do not trust, with examples of things that can go wrong (such as your case).

----------------------------------------
Bug #15886: return in rescue block breaks Timeout.timeout
https://bugs.ruby-lang.org/issues/15886#change-78313

* Author: moio (Silvio Moioli)
* Status: Rejected
* Priority: Normal
* Assignee: 
* Target version: 
* ruby -v: ruby 2.5.1p57 (2018-03-29 revision 63029) [x86_64-linux-gnu]
* Backport: 2.4: UNKNOWN, 2.5: UNKNOWN, 2.6: UNKNOWN
----------------------------------------
Passing `Timeout.timeout` a block with a rescue clause that contains a return statement prevents `Timeout::Error` to be raised as expected.

Reproducer:

``` ruby
require 'timeout'

begin
  Timeout.timeout(1) do
    begin
      sleep 10
    ensure
      puts "ensure block executed"

      ## commenting line below restores expected behaviour
      return true

    end
  end
rescue Timeout::Error => e
  puts "EXPECTED BEHAVIOUR: timeout error rescued"
end
```


Expected output:
```
ensure block executed
EXPECTED BEHAVIOR: timeout error rescued
```

Actual output:
```
ensure block executed
```



Looking in Redmine the following two issues appear related (but I lack the insight to tell for sure):
 - https://bugs.ruby-lang.org/issues/14859
 - https://bugs.ruby-lang.org/issues/7503


I apologize in advance if this issue is a duplicate.



-- 
https://bugs.ruby-lang.org/

Unsubscribe: <mailto:ruby-core-request / ruby-lang.org?subject=unsubscribe>
<http://lists.ruby-lang.org/cgi-bin/mailman/options/ruby-core>