Кэшировать (большие и статические) данные с помощью переменных класса - PullRequest
3 голосов
/ 08 октября 2011

Во-первых, позвольте мне объяснить ситуацию, у меня есть следующее:

Класс "Узел" со следующими атрибутами:

  • node_id (уникальный)
  • имя_узла (уникальное)

И класс "NodeConnection" со следующими атрибутами:

  • node_from
  • node_to

У нас будет около 1–3 миллионов узлов и около 3–10 миллионов узлов NodeConnections.

После однократного импорта узлов и соединений они не изменятся .

При каждом запросе к Rails-приложению мы должны искать от 10 до 100 узлов по возможным именам узлов.И нам нужно найти от нескольких сотен до нескольких тысяч узлов_связей.

В настоящее время мы прототипировали это без какого-либо кэширования (так, МНОГО запросов к базе данных), и время отклика было ужасным (например, 2 минуты).Поэтому мы переключились на кеширование узлов и соединений через memcached .

Получил прирост производительности, но все еще не хватает производительности.(Поскольку мы вызываем Cache.read для каждого NodeConnection, это несколько тысяч вызовов на запрос)

Теперь мы попробовали кэшировать с помощью Classvariable и получили огромный прирост производительности.(Время ответа в течение нескольких сотен мс)

# Pseudocode below
class Node
  def nodes
    @@nodes ||= get_nodes
  end
  def node_connections
    @@node_connections ||= get_node_connections
  end
end

Итак, я хотел бы спросить о Плюсах и Минусах этого решения.

Минусы, которые я получил:

  • Каждый экземпляр Rails должен создавать свой собственный кеш (свои собственные ClassVariables) -> более высокое общее использование памяти
  • Инициализация кеша - это времяпотребляет (1-3 минуты), поэтому мы не можем сделать это в запросе

Любые другие решения для кэширования больших (> 100 МБ) и статических (данные не изменятся в течение срока службы приложений)) данные, поэтому все экземпляры rails на одной машине могут очень быстро получить доступ к этому кешу (!)?

1 Ответ

3 голосов
/ 08 октября 2011

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

РЕДАКТИРОВАТЬ | Обратите внимание, что если вы использовали что-то вроде Unicorn, который поддерживает предварительную загрузку кода приложения перед разветвлением рабочих процессов, вы можете минимизировать влияние такой инициализации.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...