【问题标题】:delayed_job: NoMethodError延迟作业:NoMethodError
【发布时间】:2011-12-14 17:39:55
【问题描述】:

这是我的小型 Rails3 控制器:

class HomeController < ApplicationController
  def index
    HomeController.delay.do_stuff
  end
  def self.do_stuff
    puts "Hello"
  end
end

访问index 时,作业会正确插入数据库:

--- !ruby/struct:Delayed::PerformableMethod 
object: !ruby/object:Class HomeController
method_name: :do_stuff

问题:执行bundle exec rake jobs:work时,我得到:

Class#do_stuff failed with NoMethodError:
    undefined method `do_stuff' for #<Class:0x0000000465f910>

尽管HomeController.do_stuff 完美运行。有什么想法吗?

【问题讨论】:

    标签: ruby-on-rails delayed-job


    【解决方案1】:

    请参阅文档中的 https://github.com/collectiveidea/delayed_job/wiki/Common-problems#wiki-undefined_method_xxx_for_class

    看来你应该有

    ..object: !ruby/class HomeController method_name ...

    在数据库中,但你有

    ..object: !ruby/object:Class HomeController method_name ...

    相反。哪个不好。

    即使是delayed_job 作者也不知道原因。它以某种方式取决于您运行的网络服务器。试试 wiki 的建议。

    【讨论】:

    • 确实,运行rails server而不是我的IDE服务器解决了这个问题,非常感谢!
    • 你的回答也解决了我的赏金问题:stackoverflow.com/questions/7845874 在那里发布答案(例如,只是链接到这里),我会奖励你赏金:-)
    • 我使用 RubyMine IDE 来运行我的控制台。停止它并在我的 Mac 上的终端窗口中运行“rails s”解决了这个问题。
    【解决方案2】:

    我遇到了同样的问题。

    我发现有几个讨论表明,当 Web 应用程序将作业放入队列时以及稍后执行时,使用了不同的 yaml 解析器。

    有些人建议应该使用心理解析器。有人建议 syck。首先,我尝试了 psych,但最终遇到了与其他 gem 不兼容的问题。所以我选择了syck。

    我无法弄清楚 Web 服务器和队列使用了哪些配置文件。经过大量实验,我最终得到了以下配置(所有配置都在文件顶部):

    #application.rb
    require File.expand_path('../boot', __FILE__)
    
    require 'rails/all'
    require 'yaml'
    YAML::ENGINE.yamler= 'syck'
    # ...
    

    #environment.rb
    require 'yaml'
    YAML::ENGINE.yamler= 'syck'
    # ...
    

    #boot.rb
    require 'yaml' 
    YAML::ENGINE.yamler= 'syck' 
    require 'rubygems'
    # ...
    

    我正在使用 Ruby 1.9.3、Rails 3.2.8、Webrick、delayed_job 3.0.3

    【讨论】:

      【解决方案3】:

      我的问题主要是因为我将哈希作为参数传递给传递给延迟作业队列的对象。 但是经过 25 次跟踪后,我得出的结论是,delayed_job 只接受带有整数作为参数的对象。因此,我将所有参数存储在数据库中,然后将该记录 id 作为参数传递给延迟作业,在 perform 函数中,我们可以使用该记录 id 访问所有参数,并在获取该数据后删除该记录。

      Delayed::Job.enqueue LeadsJob.new(params[:customer]) # this job will be queued but will never run, this is because of the way Delayed_job serializes and De-serializes the objects.
      

      改为这样做

      @customer = Customer.create(params[:customer])
      Delayed::Job.enqueue LeadsJob.new(@customer.id)
      

      如果客户详细信息只是为了传递参数,则在函数中删除该记录。

      如果您需要更多详细信息,请联系我。

      问题也可能是因为 Delayed_Job 使用的 YAML 解析器,但我还没有尝试过 @Stefan Pettersson 提到的那个选项

      【讨论】:

        猜你喜欢
        • 2012-01-25
        • 2016-03-29
        • 2022-11-10
        • 2013-06-10
        • 2012-03-29
        • 2018-08-05
        • 2013-11-26
        • 2015-10-02
        • 1970-01-01
        相关资源
        最近更新 更多