【问题标题】:How do I use Rails clockwork gem to run rake tasks?如何使用 Rails 发条 gem 运行 rake 任务?
【发布时间】:2012-07-15 19:36:44
【问题描述】:

从clockwork调用rake任务的语法是什么?我尝试了各种语法,但似乎没有任何效果。 (我对发条特别感兴趣,因为 Heroku 支持它。)

这是我的clock.rb,使用了与everyge gem 相同的语法:

module Clockwork
  puts "testing clockwork!"
  every(30.seconds, 'Send Messages') {
    rake 'scheduler:send_messages'
    }
end

这是我在 scheduler.rake 中的 rake 任务:

task :send_messages => :environment do
  puts "rake task run successfully!"
end

当我开始发条过程时会发生以下情况:

$ clockwork lib/clock.rb
testing clockwork!
I, [2012-07-16T14:42:58.107245 #46427]  INFO -- : Starting clock for 1 events: [ Send Messages ]
I, [2012-07-16T14:42:58.107364 #46427]  INFO -- : Triggering 'Send Messages'
attempting to run rake task!
E, [2012-07-16T14:42:58.107437 #46427] ERROR -- : undefined method `rake' for Clockwork:Module (NoMethodError)

每 30 秒运行一次。可以看到,clock.rb 执行成功。但我一生都无法弄清楚运行 rake 任务的语法。不幸的是,发条自述文件没有帮助:

https://github.com/tomykaira/clockwork

【问题讨论】:

  • 浏览clockworks自述文件后,它没有使用您正在使用的语法(rake 'some:task
  • 是的,事实上它根本没有提供语法示例。我已经尝试了 cron 语法(rake some:task),以及when 语法(rake 'some:task')并且没有骰子。看描述如何读作“Clockwork 是 cron 替代品”。你会认为其中一个会起作用。
  • 为什么不使用 Heroku 调度器?
  • 如果必须的话我会这样做,但是 Heroku 调度程序不会扩展超过某个点,我想放置一些可以扩展的东西。
  • 另外,我无法在我的开发机器上测试 Heroku 调度程序。我尝试过使用whengem,但也没有关于如何在开发机器上使用的说明。

标签: ruby-on-rails heroku rake


【解决方案1】:

rake 不是方法,所以不能在这里调用它。

你可以shell out并调用它,比如

every(30.seconds, 'Send Messages') {
  `rake scheduler:send_messages`
}

或者更确切地说,使用 heroku API 调用一个新的分离进程。这是我目前首选的方法:

Heroku::API.new.post_ps('your-app', 'rake scheduler:send_messages')

Heroku::API 可从 heroku.rb 获得:https://github.com/heroku/heroku.rb

【讨论】:

  • 好的,使用该语法不再有错误消息,但它实际上并没有运行 rake 任务。我在部署时肯定会使用 Heroku API,但现在我需要在本地机器上进行一些测试,以确保 rake 任务可以正确访问数据库。谢谢
  • 您可以在 shell 中使用 heroku run rake scheduler:send_messages 调用 rake 任务,并查看您的任务打印到标准输出的任何输出。你可能也需要一个 bundle exec
  • 现在只是想让它在我的本地机器 (OSX) 上运行。当我从项目目录运行 $ bundle exec rake send_messages 时,它会正确运行 rake 任务。为什么它不运行 Clockwork 的 rake 任务是一个谜。
  • 运行heroku run rake scheduler:send_messages 时会发生什么?这将在 heroku dyno 上运行它,与我提出的 Heroku::API 方法相同
  • 这个问题解决了吗?我在语法上遇到了类似的问题:(stackoverflow.com/questions/13465869/…)
【解决方案2】:

您可以将一个块传递给执行您的 rake 任务的every

every(1.day, "namespace:task") do
  ApplicationName::Application.load_tasks
  Rake::Task['namespace:task'].invoke
end

【讨论】:

  • 当使用这种方法时记得要求你的application.rb文件:require_relative './application'(如果clock.rb在config:config/clock.rb),这一行应该在模块外声明
【解决方案3】:

您可以将以下方法添加到您的clock.rb 文件中:

def execute_rake(file,task)
require 'rake'
rake = Rake::Application.new
Rake.application = rake
Rake::Task.define_task(:environment)
load "#{Rails.root}/lib/tasks/#{file}"
rake[task].invoke
end

然后调用

execute_rake("your_rake_file.rake","your:rake:task")

在你的处理程序中

【讨论】:

  • 如果没有要引用的文件,您将如何执行 delay_job rake 任务?例如。 rake jobs:work
  • @Kelseydh 我正在尝试做同样的事情。你有没有想过如何做到这一点?
  • @webdevguy 可能不是你要找的东西,但这是让我用发条处理 rake 任务的答案:stackoverflow.com/a/29340040/3448554
【解决方案4】:

使用Rake::Task['...'].invoke 调用任务第一次运行良好,但需要重新启用该任务才能稍后再次调用。

    ApplicationName::Application.load_tasks

    module Clockwork do
        every(10.minutes, "namespace:task") do
          Rake::Task['namespace:task'].invoke
          Rake::Task['namespace:task'].reenable
        end
    end

否则任务将在第一次被调用,但之后不会再被调用,直到时钟进程重新启动。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-08-04
    • 1970-01-01
    • 2015-04-15
    • 2020-06-02
    • 1970-01-01
    • 2010-10-09
    • 2018-02-20
    • 1970-01-01
    相关资源
    最近更新 更多