【问题标题】:Typhoeus retry if failTyphoeus 失败时重试
【发布时间】:2013-09-05 14:29:18
【问题描述】:

目前,Typhoeus 没有在失败时自动重新下载。如果下载不成功,确保重试的最佳方法是什么?

def request
  request ||= Typhoeus::Request.new("www.example.com")
  request.on_complete do |response|
    if response.success?
      xml = Nokogiri::XML(response.body)
    else
      # retry to download it
    end
  end
end

【问题讨论】:

  • 理想情况下,重试逻辑应包括最大重试次数(如@the-tin-man 提到的)、退避策略(例如指数退避)以及指定要执行哪些状态代码的方法重试(无需重试 4xx 错误)。

标签: ruby typhoeus


【解决方案1】:

我认为你需要重构你的代码。您至少应该有两个正在使用的队列和线程。

第一个是您通过Typhoeus::Request 拉取并读取的URL 队列。

如果队列为空,则让该线程休眠一分钟,然后查找要检索的 URL。如果您成功阅读了该页面,请对其进行解析并将生成的 XML 文档推送到第二个 DOM 队列中以进行处理。从第二个线程处理它。并且,如果第二个队列为空,则休眠第二个线程,直到有东西可以处理。

如果读取 URL 失败,自动将其重新推送到第一个队列。

如果两个队列都是空的,您可以退出代码,或者让两个线程休眠,直到有消息再次开始处理 URL 并重新填充第一个队列。

您还需要一个与 URL 关联的重试计数器,否则如果网站出现故障,您可能会永远重试。您可以将小子数组推送到队列中:

["url", 0]

其中0 是重试,或者使用对象或定义类变得更复杂。不管你做什么,增加那个计数器直到它达到一个死值,然后停止将它添加到队列中并报告它或者以某种方式从你的 URL 数据库源中删除它。

这有点类似于我为处理大型爬虫任务而编写的代码。

有关这方面的示例,请参阅 Ruby 的 Thread 和 Queue 类。

还有:

request ||= Typhoeus::Request.new("www.example.com")

没有意义。 request 将在该代码运行时为零,因此 ||= 将始终触发。而是使用:

request = Typhoeus::Request.new("www.example.com")

使用适当的代码进行修改以从上述第一个队列中提取下一个值。

【讨论】:

    猜你喜欢
    • 2013-11-14
    • 2016-05-27
    • 2019-01-24
    • 2019-11-16
    • 1970-01-01
    • 1970-01-01
    • 2012-03-15
    • 2018-02-20
    • 1970-01-01
    相关资源
    最近更新 更多