Ruby 2.7 adds FrozenError#receiver

1 minute read

Ruby 2.7 has added FrozenError#receiver to return the frozen object on which modification was attempted. It is similar to NameError#receiver . This can help in pinpointing the frozen object.

Before

In Ruby, we use freeze on objects, to make sure objects are not allowed to be mutated by others. If we try to modify such a frozen object, it will throw a FrozenError .

a = []. freeze #=> [] a << 1 rescue ( e = $! ) #=> #<FrozenError: can't modify frozen Array>

But with this error, its not easy to simply identify or perform some cleanup operations on the frozen object

We can also manually initialize and throw a FrozenError :

raise FrozenError . new ( "Error Message" )

FrozenError#receiver

When we try to modify frozen object, it gives FrozenError . With this error, we can pinpoint the frozen object by calling FrozenError#receiver method.

a = []. freeze #=> [] a << 1 rescue ( e = $! ) #=> #<FrozenError: can't modify frozen Array> e . receiver #=> []

While initializing the FrozenError , we can pass the frozen object as the second argument.

# Trying to initialize FrozenError with receiver as second argument error = FrozenError . new ( "Error Message" , []. freeze ) #=> #<FrozenError: Error Message> error . receiver #=> []

Usage

FrozenError#receiver gives us the flexibility to handle the FrozenError exception specific to receiver, in a graceful manner.