🕌

[Bug #21159] Module#set_temporary_name で指定された値は不変であるというバグ報告

2025/02/27に公開

[Bug #21159] Module#set_temporary_name should freeze given name

  • Module#set_temporary_name では無名クラスに対して任意の名前を設定することができます
c = Class.new
# この時点ではまだ無名
pp c.name # => nil

c.set_temporary_name("hoge")

# #set_temporary_name に渡した文字列が名前として利用できる
pp c.name # => "hoge"
  • このときに #set_temporary_name に設定した値をあとから破壊的に変更した場合に #name にも影響があるというバグ報告です
str = +"hoge"

c = Class.new
c.set_temporary_name(str)
pp c.name # => "hoge"

# str の値を書き換えると #name の戻り値も影響が出る
str.upcase!
pp c.name # => "HOGE"
  • これは #set_temporary_name に渡した値と #name が返す値が同じオブジェクトを参照しているからみたいですね
str = "hoge"

c = Class.new
c.set_temporary_name(str)
pp str.__id__    # => 16
pp c.name.__id__ # => 16
  • Ractor のことを考えると共有可能オブジェクトな Module は不変であるべきとのこと
  • これは開発版の Ruby 3.5-dev で元のオブジェクトを破壊的な変更にしても影響がないように修正されています
# Ruby 3.5
str = "hoge"

c = Class.new
c.set_temporary_name(str)
pp str.__id__    # => 16
pp c.name.__id__
# Ruby 3.4 => 16
# Ruby 3.5 => 24

str.upcase!
pp c.name # => "hoge"
# Ruby 3.4 => "HOGE"
# Ruby 3.5 => "hoge"
GitHubで編集を提案

Discussion