Я не думаю, что есть какой-либо особый способ сделать это. Вам просто нужно это сделать.
Предположим, вы могли бы эффективно захватить все действия и связанные с ними пользователи. Вероятно, вы не можете сделать это эффективно, для чего-то столь же частого, как активность на веб-сайте, но предположительно предположим, что вы могли бы, для простоты.
Вы хотите, чтобы повторять действия и собирать строки, которые вы хотите отобразить. Легкая дорога, по моему скромному мнению, просто была бы подобным методом на вашей модели Activity
, которая возвращает массивы последовательных действий пользователя.
Оставьте свои пороговые значения для представления. (Не более двух последовательных действий, не более 10 строк.)
Если у Ruby есть некоторый причудливый способ сбора последовательных элементов из массива, то я, вероятно, буду выглядеть глупо, но вот некоторые (untested) код:
class Activity < ActiveRecord::Base
belongs_to :user
def self.each_consecutive_group(options={})
default_options = { :order => 'created_at DESC' }
current_group = nil
last_user_id = false
self.all(default_options.merge(options)).each do |activity|
# Look for consecutive activities from the same user.
# (This is never true on the first iteration.)
if last_user_id == activity.user_id
current_group << activity
else
# The nil case happens during first iteration.
yield current_group unless current_group.nil?
# Initialize state for the next group of activities.
current_group = [activity]
last_user_id = activity.user_id
end
end
# Do we still have something to yield?
yield current_group if current_group
end
# Just return the above as an array, rather than iterating.
def self.consecutive_groups(options={})
groups = []
self.each_consecutive_group(options) { |group| groups << group }
groups
end
end
# Usage:
Activity.each_grouped(:include => :user, :limit => 30) do |group|
# [...]
end
# Or if you want to pass something from the controller to the view:
@activity_groups = Activity.grouped(:include => :user, :limit => 30)
Чтобы затем смягчить проблему производительности, я бы просто взять безопасный запас. Если 10 строк - это то, что вы хотите, вы можете выбрать диапазон из 20 видов деятельности для поиска, и будет 10 мест для скрытия. Больше, и вы можете увидеть менее 10 строк. Выбирать 20 записей вряд ли много, и вы можете расширить этот номер.
Если вы умираете на всегда, показывая 10 строк, вам, вероятно, придется переместить пороговый код в вышеуказанные способы. Затем вы можете использовать find_in_batches
, а не :limit
, и продолжайте цикл до превышения порогового значения.
Не могли бы вы прояснить это для меня пожалуйста? Если он группирует то, что пользователь делал> 2 раза подряд, счет меньше 10. Затем вы хотите включить больше действий, пока не перечислите 10 действий для пользователя, или вы бы просто group_by только для последних 10 видов деятельности? –
Правильно, Shripad, мы хотели бы получить больше активных действий, чтобы мы показывали предметы. – Newy