Я не могу найти много информации о пользовательских классах исключений.
Что я знаю
Вы можете объявить свой собственный класс ошибок и позволить ему наследовать от него StandardError
, поэтому он может быть rescue
d:
class MyCustomError < StandardError
end
Это позволяет поднять его, используя:
raise MyCustomError, "A message"
а позже получите это сообщение при спасении
rescue MyCustomError => e
puts e.message # => "A message"
Что я не знаю
Я хочу предоставить своему исключению несколько настраиваемых полей, но я хочу унаследовать message
атрибут от родительского класса. Я прочитал по этой теме, что @message
не является переменной экземпляра класса исключения, поэтому я беспокоюсь, что мое наследование не сработает.
Кто-нибудь может дать мне более подробную информацию об этом? Как мне реализовать собственный класс ошибок с object
атрибутом? Правильно ли следующее:
class MyCustomError < StandardError
attr_reader :object
def initialize(message, object)
super(message)
@object = object
end
end
А потом:
raise MyCustomError.new(anObject), "A message"
получить:
rescue MyCustomError => e
puts e.message # => "A message"
puts e.object # => anObject
будет ли это работать, и если да, то правильно ли это?
rescue Exception => e
. Он шире, чем значение по умолчанию,rescue => e
которое продолжается отStandardError
и улавливает все, включая Ctrl + C. Я бы сделалrescue MyCustomError => e
.Ответы:
raise
уже устанавливает сообщение, поэтому вам не нужно передавать его конструктору:Я заменил его
rescue Exception
наrescue MyCustomError
, см. Почему это плохой стиль для `rescue Exception => e` в Ruby? .источник
rescue Exception
, а почему бы и нетrescue MyCustomError
?raise MyCustomError, "a message"
без негоnew
, «сообщение» не будет установлено.Учитывая, что в основной документации Ruby
Exception
, от которой наследуются все остальные ошибки, говорится о#message
http://ruby-doc.org/core-1.9.3/Exception.html#method-i-message
Я бы выбрал новое определение
to_s
/to_str
или инициализатор. Вот пример, в котором мы хотим знать, в основном доступным для понимания человеком способом, когда внешняя служба что-то не смогла сделать.ПРИМЕЧАНИЕ. Вторая стратегия ниже использует довольно строковые методы rails, такие как
demodualize
, которые могут быть немного сложными и, следовательно, потенциально неразумными в исключении. Вы также можете добавить дополнительные аргументы в подпись метода, если вам это нужно.Переопределение стратегии #to_s, а не #to_str, работает иначе
Консольный вывод
Переопределение стратегии #initialize
Это стратегия, наиболее близкая к реализациям, которые я использовал в рельсах. Как было отмечено выше, он использует
demodualize
,underscore
иhumanize
ActiveSupport
методу. Но это можно было легко удалить, как и в предыдущей стратегии.Консольный вывод
Демо-инструмент
Это демонстрация, демонстрирующая спасение и обмен сообщениями вышеупомянутой реализации. Класс, вызывающий исключения, - это поддельный API Cloudinary. Просто загрузите одну из вышеперечисленных стратегий в свою консоль rails, а затем выполните эту.
источник
Ваша идея верна, но то, как вы ее называете, неверно. Так должно быть
источник
raise
ключевого слова или чего-то в этом роде.initialize
два аргумента.new
передает аргументы вinitialize
.raise(BillRowError.new(:roamingcalls, @index), "Roaming Calls field missing")
. Поэтому он вызываетraise
с двумя параметрами: новыйBillRowError
объект и его сообщение. Меня просто сбивает с толку синтаксис ... В других уроках я всегда вижу это так:raise Error, message
raise
; это довольно гибко. Проблема в том, что вы решилиinitialize
принимать два аргумента и дали только один. Посмотрите на свой пример.BillRowError.new(:roamingcalls, @index)
приводится два аргумента.Я хотел сделать нечто подобное. Я хотел передать объект #new и установить сообщение на основе некоторой обработки переданного объекта. Следующие работы.
Обратите внимание: если вы не объявите,
attr_accessor :message
это не сработает. Обращаясь к проблеме OP, вы также можете передать сообщение в качестве дополнительного аргумента и сохранить все, что захотите. Важнейшей частью, похоже, является #message.источник