Issue #7097 has been updated by Eregon (Benoit Daloze).


Aaron wrote:
> On Fri, Oct 26, 2012 at 11:38:19PM +0900, Eregon (Benoit Daloze) wrote:
>  > * Remove the "thread_" prefix (as usually the thread instance is Thread.current which is very explicit, or the variable name should be clear enough).
>
>  If it becomes cumbersome, we can add aliases later.  get/set aren't very
>  ruby-like, but we have other examples (instance_variable_(get|set)).

Yeah, I think these examples are not particularly the best, but I see no other good name (well, #[] and #[]= but they are already taken). I'd rather remove the 'thread_' prefix from now, but it makes sense to follow instance_variable_{get,set}.
 
>  I'd rather not expose another object.  We can't just expose the hash
>  object because it would have inconsistent behavior with fiber locals:
>  
>      irb(main):001:0> t = Thread.new { }.join
>      => #<Thread:0x007fe5f11278c8 dead>
>      irb(main):002:0> t[:foo] = "bar"
>      => "bar"
>      irb(main):003:0> t["foo"]
>      => "bar"
>      irb(main):004:0>
>
>  Also, we'd have to figure out what calling `freeze` on that hash means.
>  Because of these things, we would have to expose a new object that isn't
>  a Hash.  Exposing a new object means propagating things like
>  Thread#freeze down to the new object.

I understand your concern, indeed it's giving too much freedom to the user (and too less to implementers).

>  If we implement these 4 new method in my patch, our API footprint is
>  only increased by 4 new methods (vs 5 methods + a new object type).  If
>  we find later on that exposing an object is a good thing, we can easily
>  implement these 4 methods in terms of the new object and deprecate the
>  4 methods.  Going in the other direction, deprecating an object, is not
>  so easy.
>  
>  I don't particularly care what the method names are (since we can just
>  alias them later), but I'm firmly against exposing a new object.

I see, this was a bold suggestion (which I made because I would greatly prefer that API), but it has too much drawbacks and complexity.
Thank you for answering it in details.
----------------------------------------
Bug #7097: Thread locals don't work inside Enumerator
https://bugs.ruby-lang.org/issues/7097#change-31635

Author: tenderlovemaking (Aaron Patterson)
Status: Assigned
Priority: Normal
Assignee: ko1 (Koichi Sasada)
Category: 
Target version: 
ruby -v: ruby 2.0.0dev (2012-09-25 trunk 37032) [x86_64-darwin12.2.0]


I set a thread local outside an Enumerator.  The Enumerator runs inside the same thread where I set the local.  I would expect the thread local to be available since I am in the same thread, but it is not.

Here is a test that shows the problem:

require 'minitest/autorun'

class ThreadLocalBreaks < MiniTest::Unit::TestCase
  def test_thread_local_in_enumerator
    Thread.current[:foo] = "bar"

    thread, value = Enumerator.new { |y|
      y << [Thread.current, Thread.current[:foo]]
    }.next

    assert_equal Thread.current, thread       # passes
    assert_equal Thread.current[:foo], value  # fails
  end
end



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