鉴于Exception所有其他错误都继承自的ruby核心文档,陈述了以下内容:#message
  返回调用exception.to_s的结果。通常,这将返回异常的消息或名称。通过提供to_str方法,同意在需要字符串的地方使用异常。
http://ruby-doc.org/core-1.9.3/Exception.html#method-i-message
我会选择重新定义to_s/ to_str或初始化程序。这是一个示例,我们希望以一种易于理解的方式知道何时外部服务无法执行某些操作。  
注意:下面的第二种策略使用rails pretty string方法,例如demodualize,这可能有点复杂,因此在异常情况下可能不明智。如果需要,您还可以在方法签名中添加更多参数。
覆盖#to_s策略 而不是#to_str,它的工作方式有所不同
module ExternalService
  class FailedCRUDError < ::StandardError
    def to_s
      'failed to crud with external service'
    end
  end
  class FailedToCreateError < FailedCRUDError; end
  class FailedToReadError < FailedCRUDError; end
  class FailedToUpdateError < FailedCRUDError; end
  class FailedToDeleteError < FailedCRUDError; end
end
控制台输出 
begin; raise ExternalService::FailedToCreateError; rescue => e; e.message; end
# => "failed to crud with external service"
begin; raise ExternalService::FailedToCreateError, 'custom message'; rescue => e; e.message; end
# => "failed to crud with external service"
begin; raise ExternalService::FailedToCreateError.new('custom message'); rescue => e; e.message; end
# => "failed to crud with external service"
raise ExternalService::FailedToCreateError
# ExternalService::FailedToCreateError: failed to crud with external service
覆盖#初始化策略
这是最接近我在Rails中使用的实现的策略。如上所述,它使用demodualize,underscore以及humanize ActiveSupport方法。但是,就像以前的策略一样,可以轻松删除它。
module ExternalService
  class FailedCRUDError < ::StandardError
    def initialize(service_model=nil)
      super("#{self.class.name.demodulize.underscore.humanize} using #{service_model.class}")
    end
  end
  class FailedToCreateError < FailedCRUDError; end
  class FailedToReadError < FailedCRUDError; end
  class FailedToUpdateError < FailedCRUDError; end
  class FailedToDeleteError < FailedCRUDError; end
end
控制台输出 
begin; raise ExternalService::FailedToCreateError; rescue => e; e.message; end
# => "Failed to create error using NilClass"
begin; raise ExternalService::FailedToCreateError, Object.new; rescue => e; e.message; end
# => "Failed to create error using Object"
begin; raise ExternalService::FailedToCreateError.new(Object.new); rescue => e; e.message; end
# => "Failed to create error using Object"
raise ExternalService::FailedCRUDError
# ExternalService::FailedCRUDError: Failed crud error using NilClass
raise ExternalService::FailedCRUDError.new(Object.new)
# RuntimeError: ExternalService::FailedCRUDError using Object
演示工具
这是演示上述实施的救援和消息传递的演示。引发异常的类是Cloudinary的虚假API。只需将上述策略之一转储到Rails控制台中,然后执行此操作即可。
require 'rails' # only needed for second strategy 
module ExternalService
  class FailedCRUDError < ::StandardError
    def initialize(service_model=nil)
      @service_model = service_model
      super("#{self.class.name.demodulize.underscore.humanize} using #{@service_model.class}")
    end
  end
  class FailedToCreateError < FailedCRUDError; end
  class FailedToReadError < FailedCRUDError; end
  class FailedToUpdateError < FailedCRUDError; end
  class FailedToDeleteError < FailedCRUDError; end
end
# Stub service representing 3rd party cloud storage
class Cloudinary
  def initialize(*error_args)
    @error_args = error_args.flatten
  end
  def create_read_update_or_delete
    begin
      try_and_fail
    rescue ExternalService::FailedCRUDError => e
      e.message
    end
  end
  private def try_and_fail
    raise *@error_args
  end
end
errors_map = [
  # Without an arg
  ExternalService::FailedCRUDError,
  ExternalService::FailedToCreateError,
  ExternalService::FailedToReadError,
  ExternalService::FailedToUpdateError,
  ExternalService::FailedToDeleteError,
  # Instantiated without an arg
  ExternalService::FailedCRUDError.new,
  ExternalService::FailedToCreateError.new,
  ExternalService::FailedToReadError.new,
  ExternalService::FailedToUpdateError.new,
  ExternalService::FailedToDeleteError.new,
  # With an arg
  [ExternalService::FailedCRUDError, Object.new],
  [ExternalService::FailedToCreateError, Object.new],
  [ExternalService::FailedToReadError, Object.new],
  [ExternalService::FailedToUpdateError, Object.new],
  [ExternalService::FailedToDeleteError, Object.new],
  # Instantiated with an arg
  ExternalService::FailedCRUDError.new(Object.new),
  ExternalService::FailedToCreateError.new(Object.new),
  ExternalService::FailedToReadError.new(Object.new),
  ExternalService::FailedToUpdateError.new(Object.new),
  ExternalService::FailedToDeleteError.new(Object.new),
].inject({}) do |errors, args|
  begin 
    errors.merge!( args => Cloudinary.new(args).create_read_update_or_delete)
  rescue => e
    binding.pry
  end
end
if defined?(pp) || require('pp')
  pp errors_map
else
  errors_map.each{ |set| puts set.inspect }
end
               
              
rescue Exception => e。它比rescue => e从扩展的默认值更广泛StandardError,并且可以捕获包括Ctrl + C在内的所有内容。我会的rescue MyCustomError => e。