Module: Fear::Try

Included in:
Failure, Success
Defined in:
lib/fear/try.rb

Overview

Note:

only non-fatal exceptions are caught by the combinators on Try. Serious system errors, on the other hand, will be thrown.

Note:

all Try combinators will catch exceptions and return failure unless otherwise specified in the documentation.

The Try represents a computation that may either result in an exception, or return a successfully computed value. Instances of Try, are either an instance of Success or Failure.

For example, Try can be used to perform division on a user-defined input, without the need to do explicit exception-handling in all of the places that an exception might occur.

An important property of Try shown in the above example is its ability to pipeline, or chain, operations, catching exceptions along the way. The flat_map and map combinators in the above example each essentially pass off either their successfully completed value, wrapped in the Success type for it to be further operated upon by the next combinator in the chain, or the exception wrapped in the Failure type usually to be simply passed on down the chain. Combinators such as recover_with and recover are designed to provide some type of default behavior in the case of failure.


Examples:

include Fear::Try::Mixin

dividend = Fear.try { Integer(params[:dividend]) }
divisor = Fear.try { Integer(params[:divisor]) }
problem = dividend.flat_map { |x| divisor.map { |y| x / y } }

problem.match |m|
  m.success do |result|
    puts "Result of #{dividend.get} / #{divisor.get} is: #{result}"
  end

  m.failure(ZeroDivisionError) do
    puts "Division by zero is not allowed"
  end

  m.failure do |exception|
    puts "You entered something wrong. Try again"
    puts "Info from the exception: #{exception.message}"
  end
end

See Also:

Defined Under Namespace

Modules: Mixin

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.matcher {|| ... } ⇒ Fear::PartialFunction

Build pattern matcher to be used later, despite off Try#match method, id doesn't apply matcher immanently, but build it instead. Unusually in sake of efficiency it's better to statically build matcher and reuse it later.

Examples:

matcher =
  Try.matcher do |m|
    m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    m.success(String) { |x| x.to_i * 2 }
    m.failure(ActiveRecord::RecordNotFound) { :err }
    m.else { 'error '}
  end
matcher.call(try)

Yield Parameters:


281
282
283
# File 'lib/fear/try.rb', line 281

def matcher(&matcher)
  TryPatternMatch.new(&matcher)
end

Instance Method Details

#any? {|value| ... } ⇒ Boolean

Returns false if Failure or returns the result of the application of the given predicate to the Success value.

Examples:

Fear.success(12).any?( |v| v > 10)                #=> true
Fear.success(7).any?( |v| v > 10)                 #=> false
Fear.failure(ArgumentError.new).any?( |v| v > 10) #=> false

Yield Parameters:

  • value (any)

Yield Returns:

  • (Boolean)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#each {|value| ... } ⇒ Try

Note:

if block raise an error, then this method may raise an exception.

Performs the given block if this is a Success.

Examples:

Fear.success(17).each do |value|
  puts value
end #=> prints 17

Fear.failure(ArgumentError.new).each do |value|
  puts value
end #=> does nothing

Yield Parameters:

  • value (any)

Yield Returns:

  • (void)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#failure?Boolean

Returns true if it is a Failure, false otherwise.


252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#flat_map {|value| ... } ⇒ Try

Returns the given block applied to the value from this Success or returns this if this is a Failure.

Examples:

Fear.success(42).flat_map { |v| Fear.success(v/2) }
  #=> Fear.success(21)
Fear.failure(ArgumentError.new).flat_map { |v| Fear.success(v/2) }
  #=> Fear.failure(ArgumentError.new)

Yield Parameters:

  • value (any)

Yield Returns:


252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#flattenTry

Transforms a nested Try, ie, a Success of Success, into an un-nested Try, ie, a Success.

Examples:

Fear.success(42).flatten                         #=> Fear.success(42)
Fear.success(Fear.success(42)).flatten                #=> Fear.success(42)
Fear.success(Fear.failure(ArgumentError.new)).flatten #=> Fear.failure(ArgumentError.new)
Fear.failure(ArgumentError.new).flatten { -1 }   #=> Fear.failure(ArgumentError.new)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#getany

Returns the value from this Success or raise the exception if this is a Failure.

Examples:

Fear.success(42).get                 #=> 42
Fear.failure(ArgumentError.new).get  #=> ArgumentError: ArgumentError

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#get_or_else(&default) ⇒ any #get_or_else(default) ⇒ any

Returns the value from this Success or evaluates the given default argument if this is a Failure.

Overloads:

  • #get_or_else(&default) ⇒ any

    Examples:

    Fear.success(42).get_or_else { 24/2 }                #=> 42
    Fear.failure(ArgumentError.new).get_or_else { 24/2 } #=> 12
    

    Yield Returns:

    • (any)
  • #get_or_else(default) ⇒ any

    Examples:

    Fear.success(42).get_or_else(12)                #=> 42
    Fear.failure(ArgumentError.new).get_or_else(12) #=> 12
    

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#include?(other_value) ⇒ Boolean

Returns true if it has an element that is equal (as determined by ==) to other_value, false otherwise.

Examples:

Fear.success(17).include?(17)                #=> true
Fear.success(17).include?(7)                 #=> false
Fear.failure(ArgumentError.new).include?(17) #=> false

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#left_classObject


254
255
256
# File 'lib/fear/try.rb', line 254

def left_class
  Failure
end

#map {|value| ... } ⇒ Object

Maps the given block to the value from this Success or returns this if this is a Failure.

Examples:

Fear.success(42).map { |v| v/2 }                 #=> Fear.success(21)
Fear.failure(ArgumentError.new).map { |v| v/2 }  #=> Fear.failure(ArgumentError.new)

Yield Parameters:

  • value (any)

Yield Returns:

  • (any)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#match(&matcher) ⇒ Object

Pattern match against this Try

Examples:

Fear.try { ... }.match do |m|
  m.success(Integer) do |x|
   x * 2
  end

  m.success(String) do |x|
    x.to_i * 2
  end

  m.failure(ZeroDivisionError) { 'not allowed to divide by 0' }
  m.else { 'something unexpected' }
end

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#or_else(&alternative) ⇒ Try

Returns this Try if it's a Success or the given alternative if this is a Failure.

Examples:

Fear.success(42).or_else { Fear.success(-1) }                 #=> Fear.success(42)
Fear.failure(ArgumentError.new).or_else { Fear.success(-1) }  #=> Fear.success(-1)
Fear.failure(ArgumentError.new).or_else { Fear.try { 1/0 } }
  #=> Fear.failure(ZeroDivisionError.new('divided by 0'))

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#recover {|matcher| ... } ⇒ Fear::Try

Applies the given block to exception. This is like map for the exception.

Examples:

#recover

Fear.success(42).recover do |m|
  m.case(&:message)
end #=> Fear.success(42)

Fear.failure(ArgumentError.new).recover do |m|
  m.case(ZeroDivisionError) { 0 }
  m.case(&:message)
end #=> Fear.success('ArgumentError')

# If the block raises error, this new error returned as an result

Fear.failure(ArgumentError.new).recover do |m|
  raise
end #=> Fear.failure(RuntimeError)

Yield Parameters:

Yield Returns:

  • (any)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#recover_with {|matcher| ... } ⇒ Fear::Try

Applies the given block to exception. This is like flat_map for the exception.

Examples:

Fear.success(42).recover_with do |m|
  m.case(ZeroDivisionError) { Fear.success(0) }
end #=> Fear.success(42)

Fear.failure(ArgumentError.new).recover_with do |m|
  m.case(ZeroDivisionError) { Fear.success(0) }
  m.case(ArgumentError) { |error| Fear.success(error.class.name) }
end #=> Fear.success('ArgumentError')

# If the block raises error, this new error returned as an result

Fear.failure(ArgumentError.new).recover_with do |m|
  raise
end #=> Fear.failure(RuntimeError)

Yield Parameters:

Yield Returns:


252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#right_classObject


259
260
261
# File 'lib/fear/try.rb', line 259

def right_class
  Success
end

#select {|value| ... } ⇒ Try

Converts this to a Failure if the predicate is not satisfied.

Examples:

Fear.success(42).select { |v| v > 40 }
  #=> Fear.success(21)
Fear.success(42).select { |v| v < 40 }
  #=> Fear.failure(Fear::NoSuchElementError.new("Predicate does not hold for 42"))
Fear.failure(ArgumentError.new).select { |v| v < 40 }
  #=> Fear.failure(ArgumentError.new)

Yield Parameters:

  • value (any)

Yield Returns:

  • (Boolean)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#success?Boolean

Returns true if it is a Success, false otherwise.


252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#to_eitherRight<any>, Left<StandardError>

Returns Left with exception if this is a Failure, otherwise returns Right with Success value.

Examples:

Fear.success(42).to_either                #=> Fear.right(42)
Fear.failure(ArgumentError.new).to_either #=> Fear.left(ArgumentError.new)

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end

#to_optionOption

Returns an Some containing the Success value or a None if this is a Failure.

Examples:

Fear.success(42).to_option                 #=> Fear.some(21)
Fear.failure(ArgumentError.new).to_option  #=> Fear.none()

252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
# File 'lib/fear/try.rb', line 252

module Try
  # @private
  def left_class
    Failure
  end

  # @private
  def right_class
    Success
  end

  class << self
    # Build pattern matcher to be used later, despite off
    # +Try#match+ method, id doesn't apply matcher immanently,
    # but build it instead. Unusually in sake of efficiency it's better
    # to statically build matcher and reuse it later.
    #
    # @example
    #   matcher =
    #     Try.matcher do |m|
    #       m.success(Integer, ->(x) { x > 2 }) { |x| x * 2 }
    #       m.success(String) { |x| x.to_i * 2 }
    #       m.failure(ActiveRecord::RecordNotFound) { :err }
    #       m.else { 'error '}
    #     end
    #   matcher.call(try)
    #
    # @yieldparam [Fear::TryPatternMatch]
    # @return [Fear::PartialFunction]
    def matcher(&matcher)
      TryPatternMatch.new(&matcher)
    end
  end

  # Include this mixin to access convenient factory methods.
  # @example
  #   include Fear::Try::Mixin
  #
  #   Fear.try { 4/2 } #=> #<Fear::Success value=2>
  #   Fear.try { 4/0 } #=> #<Fear::Failure exception=#<ZeroDivisionError: divided by 0>>
  #   Fear.success(2)  #=> #<Fear::Success value=2>
  #
  module Mixin
    # Constructs a +Try+ using the block. This
    # method ensures any non-fatal exception is caught and a
    # +Failure+ object is returned.
    # @return [Try]
    #
    def Try(&block)
      Fear.try(&block)
    end

    # @param exception [StandardError]
    # @return [Failure]
    #
    def Failure(exception)
      Fear.failure(exception)
    end

    # @param value [any]
    # @return [Success]
    #
    def Success(value)
      Fear.success(value)
    end
  end
end