首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >利用typhoeus加速rake任务

利用typhoeus加速rake任务
EN

Stack Overflow用户
提问于 2016-09-27 20:12:03
回答 1查看 153关注 0票数 0

所以我偶然发现了这个:https://github.com/typhoeus/typhoeus

我想知道这是不是加速我的rake任务所需要的

代码语言:javascript
复制
Event.all.each do |row|

  begin
  url = urlhere + row.first + row.second
  doc = Nokogiri::HTML(open(url))
  doc.css('.table__row--event').each do |tablerow|
    table = tablerow.css('.table__cell__body--location').css('h4').text
    next unless table == row.eventvenuename
      tablerow.css('.table__cell__body--availability').each do |button|
        buttonurl = button.css('a')[0]['href']
        if buttonurl.include? '/checkout/external'
          else
        row.update(row: buttonurl)
      end
      end
  end
  rescue Faraday::ConnectionFailed
    puts "connection failed"
  next
  end
end

我想知道这是否会加快速度,或者因为我正在做一个.each它不会?

如果可以的话,你能举个例子吗?

相同的

EN

回答 1

Stack Overflow用户

发布于 2016-09-28 22:22:38

如果你设置Typhoeus::Hydra运行并行请求,你也许能够加速你的代码,假设Kernel#open调用是减慢你的速度的原因。在优化之前,您可能希望运行基准测试来验证这一假设。

如果这是真的,并且并行请求将加速它,那么您将需要重新组织代码以批量加载事件,为每个批处理构建并行请求队列,然后在它们执行后处理它们。这是一些草图代码。

代码语言:javascript
复制
class YourBatchProcessingClass

  def initialize(batch_size: 200)
    @batch_size = batch_size
    @hydra = Typhoeus::Hydra.new(max_concurrency: @batch_size)
  end

  def perform
    # Get an array of records
    Event.find_in_batches(batch_size: @batch_size) do |batch|
      # Store all the requests so we can access their responses later.
      requests = batch.map do |record|
        request = Typhoeus::Request.new(your_url_build_logic(record))
        @hydra.queue request
        request
      end

      @hydra.run # Run requests in parallel

      # Process responses from each request
      requests.each do |request|
        your_response_processing(request.response.body)
      end
    end
  rescue WhateverError => e
    puts e.message
  end

  private

  def your_url_build_logic(event)
    # TODO
  end

  def your_response_processing(response_body)
    # TODO
  end

end

# Run the service by calling this in your Rake task definition
YourBatchProcessingClass.new.perform

Ruby可以用于纯脚本,但它最适合作为面向对象的语言。将您的处理工作分解为清晰的方法可以帮助您澄清代码,并帮助您捕获Tom洛德在对您的问题的评论中提到的事情。此外,您可以像上面的#perform那样使用方法级的rescue,或者只包装@hydra.run,而不是将整个脚本包装在一个@hydra.run块中。

注意,.all.each占用大量内存,因此被认为是迭代记录的糟糕解决方案:.all在使用.each迭代记录之前将所有记录加载到内存中。为了节省内存,最好使用.find_each.find_in_batches,具体取决于您的使用情况。请参阅:http://api.rubyonrails.org/classes/ActiveRecord/Batches.html

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/39724333

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档