在调试ActionMailer的一个非常奇怪的问题时,我意识到我不知道如何访问创建异常的对象。不是例外,而是对象本身。
begin
AppMailer.send_invoice(hostel_resident).deliver_later
flash[:success] = "Your invoice was sent successfully!"
rescue => msg
# display the system generated error message
flash[:error] = "#{msg}"
end
NoMethodError: undefined method `disposition_type' for #<Mail::UnstructuredField:0x009g71c2a68258>
此代码非常适合捕获任何异常并打印消息。
但是,如何获得<Mail::UnstructuredField:0x009g71c2a68258>
对象?我希望能够和这个人玩游戏,阅读里面的消息,并且通常只能访问它。
这必须是可行的,但inspect
没有帮助,cause
没有用,backtrace
只是告诉你发生了什么。我需要那个对象,即不存在的方法的接收者。
谢谢!
动作制作者(4.2.4) 邮件(2.6.3)
答案 0 :(得分:0)
这似乎有效,使用NameError
上的receiver
(NoMethodError
是其子女)
obj = Object.new
puts obj.to_s
begin
obj.do_something
rescue NoMethodError => e
puts e.message
puts e.receiver
end
# #<Object:0x007fa5ac84da88>
# undefined method `do_something' for #<Object:0x007fa5ac84da88>
# #<Object:0x007fa5ac84da88>
这似乎需要ruby&gt; = 2.3,为&lt;执行此操作2.3,AFAIK你必须做这样的事情(没有在旧红宝石中测试,但应该工作):
class MyNoMethodError < NoMethodError
attr_accessor :my_receiver
end
obj = Object.new
puts obj.to_s
begin
begin
obj.do_something
rescue NoMethodError => e
# rescue the exception and wrap it in the method that caused it, using `self` instead of `obj`
error = MyNoMethodError.new(e)
error.my_receiver = obj
raise error
end
rescue MyNoMethodError => c
puts c.inspect # custom exception stuff
puts c.cause.inspect # original exception stuff
puts c.my_receiver
end
# #<Object:0x007f884e846d58>
# #<MyNoMethodError: undefined method `do_something' for #<Object:0x007f884e846d58>>
# #<NoMethodError: undefined method `do_something' for #<Object:0x007f884e846d58>>
# #<Object:0x007f884e846d58>
答案 1 :(得分:0)