From: "ioquatix (Samuel Williams)" Date: 2022-10-22T21:56:42+00:00 Subject: [ruby-core:110481] [Ruby master Bug#19078] Introduce `Fiber#storage` for inheritable fiber-scoped variables. Issue #19078 has been reported by ioquatix (Samuel Williams). ---------------------------------------- Bug #19078: Introduce `Fiber#storage` for inheritable fiber-scoped variables. https://bugs.ruby-lang.org/issues/19078 * Author: ioquatix (Samuel Williams) * Status: Open * Priority: Normal * Assignee: ioquatix (Samuel Williams) * Backport: 2.7: UNKNOWN, 3.0: UNKNOWN, 3.1: UNKNOWN ---------------------------------------- Pull Request: https://github.com/ruby/ruby/pull/6612 This is an evolution of the previous ideas: - https://bugs.ruby-lang.org/issues/19058 - https://bugs.ruby-lang.org/issues/19062 This PR introduces fiber scoped variables, and is a solution for problems like . The main interface is: ```ruby Fiber[key] = value Fiber[key] # => value ``` The variables are scoped by fiber and inherited into child fibers and threads. ```ruby Fiber[:request_id] = SecureRandom.hex(16) Fiber.new do p Fiber[:request_id] # prints the above request id end ``` The fiber scoped variables are stored and can be accessed: ```ruby Fiber.current.storage # => returns a Hash of the internal storage. Fiber.current.storage= # => assigns a Hash to the internal storage. ``` I'm still on the fence as to whether these methods should return an actual mutable Hash, or function as a copy (so we don't force the internal representation to be a hash table). Fiber itself has one new keyword argument: ``` Fiber.new(..., storage: hash, false, undef, nil) ``` This can control how the fiber variables are setup in a child context. To minimise the performance overhead of some of the implementation choices, we are also simultaneously implementing . ## Examples ### Request loop ```ruby Thread.new do while request = queue.pop Fiber.new(storage: {id: SecureRandom.hex(16)}) do handle_request.call(request) end end end ``` OR ```ruby Thread.new do while request = queue.pop Fiber.current.storage = {id: SecureRandom.hex(16)} handle_request.call(request) end end ``` -- https://bugs.ruby-lang.org/ Unsubscribe: