我在Heroku上有一个正在运行的RoR应用程序。我有一个代码片段,它将连接到外部API并将这些数据保存到我的数据库中。
然而,在Heroku的文档部分中,它说,如果请求超过30秒,则返回503错误。
我的数据库中有300个用户。每个用户平均有近30种车型。所以它应该发送带有for循环的9000(300 * 30)个请求并将数据保存到我的数据库中。
它只适用于localhost
。但我无法弄清楚在Heroku上处理这个问题的有效方法。
我想到的那些;
将现有数据库从Heroku保存到本地。然后将9.000辆汽车保存到我的数据库,然后再次将数据库导入Heroku。
运行cron job来处理Heroku上的代码片段。这当然需要超过30秒。
感谢任何帮助!
谢谢
答案 0 :(得分:0)
抱歉,我没有足够的声誉在这里发表评论。
如果你在这里发布一些代码会很好,因为你很难理解你想要做什么。
如果您只需运行一次脚本来填充数据,我建议您创建一个自定义rake任务,并使其生成一些可读输出,以便您知道其日志中发生了什么。而且你可以运行超过30秒。
在这里,您可以阅读有关佣金任务http://guides.rubyonrails.org/command_line.html#custom-rake-tasks
的信息考虑到您的描述,我可以想象您的代码如下所示:
namespace :car_types do
desc "Update car types from external api"
task update_from_api: :environment do
failed_to_update_ids = []
CarType.find_each do |car_type|
new_data = request_new_data_from_api_here(car_type)
car_type.update(new_data)
puts "Updated #{car_type.id}"
rescue => e
failed_to_update_ids << car_type.id
puts "Was not able to update #{car_type.id}: #{e.inspect}"
end
puts 'Failed to update ids:'
puts failed_to_update_ids
end
end
你这样运行:
heroku run rake car_types:update_from_api --app=your_heroku_instance
最好不要将代码存储在rake任务中,而是存储在某个类或库中,然后您就可以从任何地方运行此代码:从控制台或应用程序的任何部分,只需记住此代码是耗时的,必须在后台运行。
如果您需要定期运行,可以使用Heroku Scheduler安排它:https://devcenter.heroku.com/articles/scheduler
答案 1 :(得分:0)
顺序执行9000次api调用效率非常低。你应该并行化它们。这是一种快速天真的方式:
threads = users.map { |user| Thread.new { api_call(user) } } # Launch all api calls and returns an array of threads
thread.each(:join) # Wait for all api calls are ended
有关文档中线程的更多详细信息:http://ruby-doc.org/core-2.5.0/Thread.html
但是,如果最长的请求超过30秒,则无法帮助您。在这种情况下,您应该将其移至background / cron作业。
还有这个好的库可以发出并行HTTP请求:https://github.com/typhoeus/typhoeus
如果不了解应用程序的运行方式,很难帮助您。但我认为线程和背景/ cron工作是解决问题的好线索。