【问题标题】:Ruby on Rails - Breaking down a hash of hashes to include caching of queriesRuby on Rails - 分解散列以包含查询缓存
【发布时间】:2018-05-28 12:21:41
【问题描述】:

我有一个哈希值,用于创建堆积柱形图。沿着 x 轴,我有一周中的天数,y 轴是每个目标当天的总分,叠加到当天的总分。

这是我控制器中的方法:

def goal_xp_by_day

  # Create an array of goals to iterate through only if they have activities
  # recorded in the last 7 days.
  days_goals = current_user.goals.select { |g| g.empty_days}

  # Iterate through goals and for each goal, create a hash of days and points
  goals = days_goals.map do |goal|
    days = {}
    (Date.today-6..Date.today).each do |day|

      # Pass the day to a method which uses the paramater 
      # to calculate the points for that period
      days[day.strftime("%a")] = goal.daily_goal_xp(day)
    end
    {
      name: goal.name,
      data: days
    }
  end
  render json: goals
end

随着时间的流逝,我知道每天的结果(不包括当前)不会改变,但当天的结果可能随时改变,因此缓存整个图表毫无意义。我想找到一个缓存前 6 天的数据以防止过度查询,但我不确定如何分解此方法以查询最近 6 天,缓存它并运行查询到计算今天的结果,然后最后将它们合并在一起以创建更新的图表。

我正在考虑将诸如日期之类的参数传递到 cache_key 中,并可能对每个哈希使用某种形式的俄罗斯娃娃缓存。这是可以在控制器中完成的事情吗?我知道它们通常在视图文件中使用,但在这种情况下,结果会在控制器中返回。

如果有办法提高这些查询的效率,我非常感谢一些建议/指针,即使缓存不是一种选择。

【问题讨论】:

  • 一种简单的方法是例如首先实现一个模型函数goal_xp_by_day(_selected_goals),它计算前几天的json结果。然后控制器只需使用参数调用模型函数。然后将结果缓存在文件中,并在每次调用函数时检查文件年龄。如果文件年龄超过 x 天/小时,则创建一个新文件。由于您需要 json 格式的结果,因此将它们保存到临时 .json 文件是有意义的。

标签: ruby-on-rails ruby caching hash


【解决方案1】:

是的,这样的事情可以在控制器级别完成。您可以使用通用缓存调用包装整个方法内容,然后使用另一个键包装每个不经常更改的代码部分。

这样的事情可能会让你找到正确的方向:

(Date.today-6..Date.today).each do |day|
  days[day.strftime("%a")] = Rails.cache.fetch("day-goal", day) do 
    goal.daily_goal_xp(day)
  end
end

这将导致给定日期的缓存键不会更改。不要忘记使用任何可能导致缓存过期的模型实例更新缓存键。

【讨论】:

    猜你喜欢
    • 2012-10-05
    • 1970-01-01
    • 1970-01-01
    • 2012-09-24
    • 2019-05-13
    • 2012-12-16
    • 2019-01-08
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多