2013-02-19 2 views
0

У меня есть приложение Rails, которое содержит счетчик пользователей, комментарии для многих Movie_Categories. Модели выглядят следующим образом:Большинство DRY-подходов для Rails-приложений с множеством субтитров

class User < ActiveRecord::Base 
    has_many :comments 
end 

class Movie < ActiveRecord::Base 
    belongs_to :movie_category 

    has_many :comments 
end 

class MovieCategory < ActiveRecord::Base 
    has_many :movies 
end 

class Comment < ActiveRecord::Base 
    belongs_to :movie 
    belongs_to :user 
end 

Я могу, конечно, найти Комментарии пользователя подсчитывают MovieCategory делать что-то вроде этого для каждого MovieCategory:

@user.comment.where("movie_category_id =?", movie_category_id) 

Однако это ставит много нагрузки на сервер, если мне нужно сделать этот вызов слишком часто, поэтому я думал о том, чтобы делать вычисления один раз в час (в фоновом задании) для всех пользователей для всех Movie_Categories, а затем для хранения счетчиков в таблице «Пользователь», каждая категория фильмов со своим собственным столбцом , Таким образом, мне не нужно выполнять вычисления для каждого пользователя так часто, и вы можете просто получить доступ к подсчетам из таблицы User.

Что мне интересно, если есть более сухой способ сделать это, так как я не уверен, когда мой Movie_Categories перестанет расти (и каждый раз появляется новое поле таблицы). Я также думал о кэшировании представлений представления пользователей (где эти значения отображаются), но даже в этом случае, если у меня нет этих столбцов в таблице User, то кажется, что каждый раз, когда загружается новая страница пользователя (или кэшируется истек), это вам придется выполнить вычисление всего этого для подсчета комментариев пользователя снова.

Есть ли лучший подход к проблеме, с которой я столкнулся, не ставя слишком много бремени на сервер?

+1

Накладывает ли он много нагрузки на сервер, потому что в этих таблицах много записей? У вас есть индексы, настроенные для этого запроса? Это похоже на разумный запрос. –

+0

Прямо сейчас, это не слишком большая загрузка, потому что приложение не в сети. Я просто думаю о том, как это выглядит, если у вас есть 100 или более категорий и несколько сотен тысяч пользователей. – yellowreign

ответ

0

Учитывая ваши комментарии о том, что вы находитесь в разработке на данный момент, я бы сказал, не беспокойтесь об этом, пока вам не придется беспокоиться об этом! Тем не менее, если вы планируете планировать свои планы, мы должны пойти с fragment caching и индексировать внешние ключи.

Если ваш сайт растет до размера, о котором вы говорите, выполнение миграции для добавления дополнительных полей в таблицу ваших пользователей может занять значительное время.

Замечу, вы упоминается кэширование в вашем вопросе так предполагаю, что вы в целом знакомы с ним, но учитывая вид, такие как:

<ul> 
    <li>Action Movies: 23 Comments</li> 
    <li>Comedy Movies: 14 Comments</li> 
</ul> 

Вы бы обернуть это в cache блоке:

<% cache "user-#{user.id}-comments", @user.comments.last.created_at.to_i do %> 
    ... 
<% end %> 

Это будет кэшировать фрагмент, отображающий счетчики, и автоматически истекает его каждый раз, когда новый комментарий отправляется этим пользователем. Вы могли бы получить подробные детали, кэшируя каждый <li> и заканчивая только в том случае, если комментарий опубликован в этой категории, но на ранней стадии он может быть излишним.

Для индекса на внешних ключей, вы можете добавить это в миграции, используя синтаксис:

add_index :comments, :movie_category_id 

Я не думаю, что запрос запуска является , что плохой но вы никогда не знаете, пока вы ударил производство и масштаб, какой эффект он будет иметь.

Смежные вопросы