繁体   English   中英

Rails 4 - Resque背景作业里面的印象派

[英]Rails 4 - Impressionist Inside of a Resque Background Job

我正在使用Rails 4 w /印象派和resque gem。

我正在使用印象派来记录我的文章显示页面上的唯一会话点击。 由于性能问题而且无需向用户显示匹配(仅限管理员),我希望将日志记录显示移至后台。

通常我会使用impressionist(@article, unique: [:session_hash])记录一个印象impressionist(@article, unique: [:session_hash])但是通过resque将它移到bg中我现在正在做这样的事情......

articles_controller:

def show
  .
  .
  .
  Resque.enqueue(ImpressionLogger, @article.id)
end

应用程序/工人/ impression_logger.rb:

class ImpressionLogger 

  @queue = :impression_queue

  def self.perform(article_id)
    article = Article.find(article_id)
    impressionist(article, unique: [:session_hash])
  end

end

当我这样设置时,当resque尝试处理作业时,它会返回undefined method "impressionist" for ImpressionLogger:Class 你认为最好的方法是什么? 我不确定如何在我的resque工作者中包含印象派方法。

印象派是否与捆绑器正确安装? 如果是这样,Rails应该将它加载到您的环境中。 我会检查你是否可以在你的Rails代码中的其他地方访问impressionist功能(即不通过Resque)作为调试它的第一步。

问题

您的问题源于这样一个事实:由于在ActionController的任何实例上的引擎初始化程序中包含一个带有impressionist方法的模块,因此Impressionist在控制器级别上工作:

https://github.com/charlotte-ruby/impressionist/blob/master/lib/impressionist/engine.rb#L11

您试图从Resque作业中调用的常规类调用impressionist方法,因此它不会定义该方法。

这有点粗,但是如果你真的想使用印象派,我们可以深入研究这个......看看这里找到的印象派方法的实际实现,我们看到以下内容:

def impressionist(obj,message=nil,opts={})
  if should_count_impression?(opts)
    if obj.respond_to?("impressionable?")
      if unique_instance?(obj, opts[:unique])
        obj.impressions.create(associative_create_statement({:message => message}))
      end
    else
      # we could create an impression anyway. for classes, too. why not?
      raise "#{obj.class.to_s} is not impressionable!"
    end
  end
end

假设你手动调用这样的东西(你想从resque工作中调用),关键是这三行:

if unique_instance?(obj, opts[:unique])
  obj.impressions.create(associative_create_statement({:message => message}))
end

如果要实现功能,if包装器似乎很重要。 它看起来像你做的。 associative_create_statement的调用似乎是根据控制器名称以及从Rack传递的参数(例如useragent字符串和ip地址( 此处 ))来提取参数。 因此,您必须在调用Resque作业之前解析这些值。

我在这一点上建议实现一个Resque类,它接受两个参数,一个article_id和你想要的印象参数。 然后,resque类将直接在可展示对象上创建印象。 您的Resque课程将成为:

class ImpressionLogger 
  @queue = :impression_queue

  def self.perform(article_id, impression_params = {})
    article = Article.find(article_id)
    article.impressions.create(impression_params)
  end
end

你的控制器方法看起来像这样:

def show
  .
  .
  .
  Resque.enqueue(ImpressionLogger, @article.id, associative_create_statement({message: nil})) if unique_instance?(@article, [:session_hash])
end

放弃

尽管这样做有一个相当大的免责声明......方法associative_create_statement被标记为protected和unique_instance? 被标记为私有...所以这些都不是印象派宝石的公共API的一部分,所以这个代码可能会在gem的版本之间中断。

你是如何开始你的resque工人的? 如果您需要加载Rails环境,请尝试rake environment resque:work

https://github.com/resque/resque/wiki/FAQ#how-do-i-ensure-my-rails-classesenvironment-is-loaded

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM