dry-monads
dry-monads copied to clipboard
`Try::Error` has an incorrect `deconstruct` implementation
Describe the bug
The following code should work:
case Try { n / d }
in Value(x)
puts "n / d = #{x}"
in Error(ZeroDivisionError => ex)
puts "divisor must not be zero"
else [x]
puts "Got exception: #{x}"
end
But it does not - because Try
implements deconstruct
from RightBiased
, which expects the value to be stored at the @value
instance variable.
Try::Error
does not have a @value
variable - it uses @exception
instead. Thus pattern matching on Error
values never has the expected results.
Current workarounds: call #to_result
.
To Reproduce
res = Try { 3 / 2 }
err = Try { 1 / 0 }
# Value works fine
res => Value(x)
puts x # => 1
# Error succeeds on pattern match
err => Try::Error(ex)
# But binds ex to nil, and ex != err.exception
puts ex.inspect => nil
puts err.exception => #<ZeroDivisionError: divided by 0>
# Workaround
err.to_result => Failure(ex)
puts ex.inspect => #<ZeroDivisionError: divided by 0>
Expected behavior
Pattern matching on Try::Error
values should bind the exception.
My environment
- Affects my production application: YES - workarounds are available
- Ruby version: ALL (strictly speaking
>= 3.0
) - OS: ALL