0

我有三个 activerecord 模型:客户、访问和活动。

Customer    has_many   :visits
Visit       belongs_to :customer
Campaign    has_many   :visits    

访问模型跟踪特定客户每次访问网站、访问的页面、显示的广告以及最重要的是他们是否进行了购买。广告系列是客户在访问网站期间看到的一系列广告。每个活动持续 1 小时(每天 24 个活动)并且有很多访问。

我正在尝试做的是开发一些 activerecord 范围或类方法,使我能够识别“下次访问购买”。

例如,7 月 4 日当天的第四个活动有 100 次客户访问。我希望能够查看每个客户的下一次访问,并确定那些访问/客户在下一次访问时已经/进行了购买。我发现很难解决的是客户随后的访问并非都是在同一天,但我想确定“下一次访问”以及导致购买的那些。

我的设想是这样的:

Campaign.find(2232).next_visit.purchase     #where next_visit and purchase are scopes

或者

Visit.find(5445).next_visit.purchase 

我在访问模型中有一个购买标志,因此购买范围相当简单。

scope, :purchase, where(:purchase_flag => true)

同样基于Railscast #215,如果我在访问模型上创建此范围,则可以使用连接和合并将它们应用于客户和活动模型。

Campaign.joins(:visits).merge(Visit.purchase)

这是正确的方法吗?如果是这样,我如何定义我的 Next 范围,如果不是,你会建议什么作为替代方法。

更新:我得到了一些很好的回应。只是想知道普遍的共识是迪帕克的方法是正确的还是其他反应更可取。

4

3 回答 3

2

我认为范围在这里不是正确的,因为您需要在对象上调用它。您可以将其实现为 visit.rb 中的方法。

可能像:

def next_visit
  Visit.where(['date > ?', self.date]).order(:date).limit(1).first
end

编辑: 让您能够链接方法

def next_visits
  Visit.where(['date > ?', self.date])
end
于 2013-07-18T12:15:23.823 回答
1

在当前的数据库结构中,实现您需要的东西非常笨拙,而且效率也可能非常低。

我对这个问题有不同的方法:

  • 购买时 - 最好的机会是了解导致此次购买的活动/访问(检查用户的上次访问并找到活动)。
  • 要捕获这些信息,请在活动和访问之间使用自定义名称创建适当的关系。
  • 在适当模型的 after_save/after_create 回调中填充这些(很可能是购买或访问)。

以上述方式捕获数据后,查询相对容易。

于 2013-07-21T16:41:08.340 回答
1

因此,您需要衡量活动的效率,并获得活动后回来并进行购买的客户的数据。

我提议:

class Campaign

  def next_visits
    # Wrapping the whole code of this method in @next_visits will perform local caching
    # There is a good railscast that explain it in details (5 minutes long video)
    # You can see it there: http://railscasts.com/episodes/1-caching-with-instance-variables
    @next_visits ||= begin
      # This will be the starting date of "next visits"
      since = self.end_of_campaign # I assume you can get the TimeDate of the end of campain

      # List of ids of customers that participated to the campaign
      customers_ids = self.visits.uniq(:customer_id).pluck(:customer_id)

      # Return the visit records
      next_visits = Visit.where(purchase_flag: true, customer_id: customers_ids)
      next_visits.where('created_at > ?', since).first
    end
  end

end

然后你打电话Campaign.find(123).next_visits

编辑

您应该对变量使用正确的 TZsince

关于@next_visits ||= begin ... end:这是一种缓存技术。第一次调用该方法时,块内的所有代码begin都将被执行,结果(记录)将存储在实例变量@next_visits 中并返回给调用者。

下次调用该方法时,@next_visits 中的缓存结果将直接返回,而不会访问您的数据库。这对性能有好处。

有关该http://railscasts.com/episodes/1-caching-with-instance-variables的更多信息

于 2013-07-25T01:03:15.107 回答