class LunaPark::Errors::Base

This class extends standard exception with a few things:

@example Fatalism class

module Errors
  class Fatalism < LunaPark::Errors::Base
    message  'You cannot change your destiny', i18n_key: 'errors.fatalism'
    notify: :info
  end
end

error = Error::Fatalism.new(choose: 'The first one')
error.message # => 'You cannot change your destiny'
error.message(lang: :ru) # => 'Вы не можете выбрать свою судьбу'
error.details # => { :choose => "The first one" }

Constants

DEFAULT_NOTIFY_LEVEL
NOTIFY_LEVELS
NOTIFY_VALUES

Attributes

default_message_block[R]

Proc, that receives details hash: { detail_key => detail_value }

@private

default_notify[R]

Explains how this error class will be notified

@return [Boolean, Symbol] the behavior of the notification

i18n_key[R]

What the key of the translation was selected for this error

@return [NilClass, String] internationalization key

details[R]

It is additional information which extends the notification message

@example

error = Fatalism.new('Message text', custom: 'Some important', foo: Foo.new )
error.details # => {:custom=>"Some important", :foo=>#<Foo:0x000055b70ef6c370>}

Public Class Methods

inherited(inheritor) click to toggle source
Calls superclass method
# File lib/luna_park/errors/base.rb, line 78
def inherited(inheritor)
  if default_message_block
    inheritor.message(i18n_key: i18n_key, &default_message_block)
  elsif i18n_key
    inheritor.message(i18n_key: i18n_key)
  end

  inheritor.default_notify = default_notify

  super
end
message(txt = nil, i18n_key: nil, &default_message_block) click to toggle source

Specify default error message

@param txt [String] - text of message @param i18n_key [String] - internationalization key @return [NilClass]

# File lib/luna_park/errors/base.rb, line 72
def message(txt = nil, i18n_key: nil, &default_message_block)
  @default_message_block = block_given? ? default_message_block : txt && ->(_) { txt }
  @i18n_key = i18n_key
  nil
end
new(msg = nil, notify: nil, **details) click to toggle source

Create new error

@param msg - Message text @param notify - defines notifier behaviour (see self.notify) @param details - additional information to notifier

@example without parameters

error = Fatalism.new
error.message     # => 'You cannot change your destiny'
error.notify_lvl  # => :error
error.notify?     # => true

@example with custom parameters

@error = Fatalism.new 'Forgive me Kuzma, my feet are frozen', notify: false
error.message     # => 'Forgive Kuzma, my feet froze'
error.notify_lvl  # => :error
error.notify?     # => false

TODO: make guards safe: remove these raises from exception constructor (from runtime)

Calls superclass method
# File lib/luna_park/errors/base.rb, line 127
def initialize(msg = nil, notify: nil, **details)
  raise ArgumentError, "Unexpected notify value: #{notify}" unless notify.nil? || NOTIFY_VALUES.include?(notify)

  @message = msg
  @notify  = notify
  @details = details
  super(message)
end
notify(lvl) click to toggle source

Specifies the expected behavior of the error handler if an error instance of this class is raised

@param [Symbol] - set behavior of the notification (see default_notify)

@return [NilClass]

# File lib/luna_park/errors/base.rb, line 61
def notify(lvl)
  self.default_notify = lvl unless lvl.nil?

  nil
end

Protected Class Methods

default_notify=(notify) click to toggle source
# File lib/luna_park/errors/base.rb, line 92
def default_notify=(notify)
  raise ArgumentError, "Unexpected notify value #{notify}" unless NOTIFY_VALUES.include? notify

  @default_notify = notify
end

Public Instance Methods

message(locale: nil) click to toggle source

Error message

The message text is defined in the following order:

  1. In the `initialize` method

  2. Translated message, if i18n key was settled in class (see `.message`)

  3. In the class method (see `.message`)

@param locale [Symbol,String] @return [String] message text

@example message is not settled

LunaPark::Errors::Base.new.message # => 'LunaPark::Errors::Base'

@example message is defined in class

class WrongAnswerError < LunaPark::Errors::Base
  message 'Answer is 42'
end

WrongAnswerError.new.message # => 'Answer is 42'

@example message is in internatialization config

# I18n YML
# ru:
#   errors:
#     frost: Прости Кузьма, замерзли ноги!

class FrostError < LunaPark::Errors::Base
  message 'Forgive Kuzma, my feet froze', i18n_key: 'errors.frost'
end

error = FrostError.new
error.message(locale: :ru) # => 'Прости Кузьма, замерзли ноги!'

@example message is defined in class with block

class WrongAnswerError < LunaPark::Errors::Base
  message { |details| "Answer is '#{details[:correct]}' - not '#{details[:wrong]}'" }
end

error = WrongAnswerError.new(correct: 42, wrong: 420)
error.message # => "Answer is '42' - not '420'"

@example message is in internalization config with i18n interpolation

# I18n YML
# de:
#   errors:
#     wrong_answer: Die richtige Antwort ist '%{correct}', nicht '%{wrong}'

class WrongAnswerError < LunaPark::Errors::Base
  message i18n_key: 'errors.wrong_answer'
end

error = WrongAnswerError.new(correct: 42, wrong: 420)
error.message(locale: :de) # => "Die richtige Antwort ist '42', nicht '420'"
# File lib/luna_park/errors/base.rb, line 216
def message(locale: nil)
  return @message if @message

  default_message = build_default_message
  localized_message(locale, show_error: default_message.nil?) || default_message || self.class.name
end
notify?() click to toggle source

Should the handler send this notification ?

@return [Boolean] it should be notified?

@example notify is undefined

error = LunaPark::Errors::Base
error.notify # => false
# File lib/luna_park/errors/base.rb, line 143
def notify?
  @notify || self.class.default_notify ? true : false
end
notify_lvl() click to toggle source

Severity level for notificator

@return [Symbol] expected notification level

@example notify is undefined

error = LunaPark::Errors::Base
error.notify_lvl # => :error
# File lib/luna_park/errors/base.rb, line 155
def notify_lvl
  return @notify                   if NOTIFY_LEVELS.include? @notify
  return self.class.default_notify if NOTIFY_LEVELS.include? self.class.default_notify

  DEFAULT_NOTIFY_LEVEL
end

Private Instance Methods

build_default_message() click to toggle source

@return [String] - Default message

# File lib/luna_park/errors/base.rb, line 239
def build_default_message
  self.class.default_message_block&.call(details)
end
localized_message(locale = nil, show_error:) click to toggle source

Return translation of an error message if 18n_key is defined if `show_error: true` and translation is missing, will return string 'translation missing: path' if `show_error: false` and translation is missing, will return nil

@param locale [Symbol] - specified locale @return [String] - Translated text

# File lib/luna_park/errors/base.rb, line 231
def localized_message(locale = nil, show_error:)
  return unless self.class.i18n_key
  return unless show_error || I18n.exists?(self.class.i18n_key)

  I18n.t(self.class.i18n_key, locale: locale, **details)
end