Почему Ruby on Rails выполняет запросы SELECT 1 AS one? - PullRequest
0 голосов
/ 23 мая 2018

В настоящее время я работаю над проектом в Ruby on Rails, с которым у меня на самом деле нет никакого опыта. Теперь мы сталкиваемся с некоторыми проблемами производительности, которые, я думаю, связаны с выполнением слишком большого количества запросов.

У нас есть модель Service, которую мы установили в нашем контроллере следующим образом:

@services = Service.includes(:points).with_points

Область действия with_points определяется в сервисе следующим образом:

scope :with_points, -> { joins(:points).where.not(points: []).distinct }

(Я думаю, что предложение where здесь не нужно, но, вероятно, это не имеет отношения к вопросу.)

Затем в представлении мы используем извлеченные services со связанными баллов , как показано ниже:

<% @services.each do |s| %>
    <div class="col-xs-12 col-sm-6 col-lg-4 serviceDiv" data-rating="<%= s.service_ratings %>" >
        <% if s.service_ratings == "A" %>
            <% grade = "rating-a" %>
                <!-- etc. -->

Теперь, насколько я видел при исследовании, это относительно нормальный паттерн при попытке вывести все строки из таблицы.Однако, когда я просматриваю логи, кажется, что для каждого сервиса ?

# This query is what I'd expect:
SQL (1.6ms)  SELECT DISTINCT "services"."id" # etc, etc
# But then we also get one of these for every service
Service Exists (1.5ms)  SELECT  1 AS one FROM "services" WHERE "services"."name" = $1 AND ("services"."id" != $2) LIMIT $3
# And quite a few of these for every service:
CACHE Service Exists (0.0ms)  SELECT  1 AS one FROM "services" WHERE "services"."name" = $1 AND ("services"."id" != $2) LIMIT $3

выполняется отдельный запрос. Теперь я догадываюсь, что эти строки "Service Exists" плохиеНовости.Кто они и откуда они?Есть ли что-то еще, что мне здесь не хватает?

1 Ответ

0 голосов
/ 23 мая 2018

После указателей @ MarekLipka в комментариях к этому вопросу мне удалось найти источник проблемы.Не уверен, сколько людей столкнется с этой настройкой в ​​будущем, но я поделюсь ею на всякий случай.

Подсказка была в нашем доступе к s.service_ratings, который на самом деле не был столбцом вбаза данных. ActiveRecord Query Trace указывал на источник всех этих запросов, являющийся ссылкой на s.service_ratings в представлении, который был красным флагом.

service_ratings был фактически методом (предполагая, что яя использую правильную терминологию здесь) в модели Service, которая, кроме возврата значения, основанного на вычислении нескольких свойств модели, также , называемая self.update_attributes, для фактического сохранения этого значения вбаза данных.Это означало, что каждый раз, когда мы извлекали данные этой модели для их отображения, мы также запускали другой запрос для сохранения этого значения в базе данных - часто избыточно.

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

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