0

我有一组连接到各种 API 的 Adapter 类,等等。以下是每个适配器如何设置的简单通用示例:

class AmazonAdapter
    include Sidekiq::Worker
    def perform(id)
        get_results_from_api(id)
    end
end

class WalmartAdapter
    include Sidekiq::Worker
    def perform(id)
        get_results_from_api(id)
    end
end

所以一般来说,通过调用AmazonAdapter.new(500),它将连接到 API 并根据您作为 ID 传入的内容返回结果。这都是 Sidekiq 收集过程的一部分,并作为后台作业运行,因此当出现问题时,它不一定会抛出明显的异常或错误来提醒我。

当 API 未正确连接或抛出任何其他错误时,我想使用 AirBrake 的通知系统通知我,但不会停止收集过程或 sidekiq。我希望将错误处理和通知系统纳入主流。

我的一些想法是创建一个子类可以从中继承的 ParentClass,看起来类似于:

class Adapter
    include Sidekiq::Worker
    def perform(id)
        begin
            #execute subclass perform method
        rescue Exception => e
            Airbrake.notify(e)
        end
    end
end

但我不太确定解决这个问题的最佳方法。我真的可以在这方面使用一些建议或帮助,谢谢!

4

2 回答 2

0

有一个瓶颈Sidekiq,基本上执行一切:Sidekiq::Processor#execute_job,接收两个参数(worker, cloned_args)并随后调用worker.perform(*cloned_args). 因此,出于您的目的,我将在模块前添加:

Sidekiq::Processor.prepend(Module.new do
  def execute_job(worker, cloned_args)
    super # CALL ORIGINAL
  rescue => e # NEVER RESCUE FROM EXCEPTION!!!
    Airbrake.notify(e) # NOTIFY
    raise e # RE-RAISE SO SIDEKIQ DOES HIS JOB
  end
end)

在你的第一份工作之前调用它,你就完成了:在 Sidekiq 调用工作人员期间发生的所有错误现在都被空气制动了。

希望能帮助到你。

于 2016-09-21T17:36:58.517 回答
0

我使用类似的构造来提醒我某些 chron 作业中的失败并 ping 一个松弛通道,但好的部分是它不需要继承!一个天真的版本看起来像这样:

class AirbrakeNotifier
  def safe_run
    yield
  rescue StandardError => e
    log_error(e)
    raise e
  end

  private

  def log_error(e)
    # do your logging here
  end
end

然后你的工人看起来像这样:

class AmazonAdapter
  include Sidekiq::Worker

  def perform(id)
    AirbrakeNotifier.new.safe_run { get_results_from_api(id) }
  end
end

这为您提供了更大的灵活性,可以按照您想要的每个类、每个进程或您能想到的不同方式配置日志记录!

于 2016-09-21T21:06:19.507 回答