Rails фильтрует записи через has_many

Я пытаюсь найти модель элемента с фильтром по имени жанры, которые связаны через has_many.

Моя проблема в том, что когда я выбираю два или более жанра, он также выбирает записи, которые содержат только один жанр.

Пример: есть два жанра: "Экшн" и "Приключение". Запись A имеет жанр Action, а запись B имеет оба жанра. Выбрав оба флажка жанра на мой взгляд, записи, возвращаемые Rails, включают в себя как записи A и B, в то время как это должна была быть только запись B.

Это мой оператор фильтра под контроллером

  //This is under controller
  @item = Item.includes(:genres).where('genres.id' => params['genre_ids'])
  // This is under my view
  <%= simple_form_for Item.new, :method => :get, url: search_path do |f| %>

        <% Genre.all.each do |sc| %>
            <div>
                <label>
              <%= check_box_tag 'genre_ids[]',sc.id %>
                <span style="font-weight:normal;"><%= sc.name %> </span>
             </label>
            </div>
          <% end %>

    <% end %>

1 ответ

Причина, по которой это не работает, в том, что SQL создается из вашего выражения. where('genres.id' => [1, 2, 3]) дает тебе SELECT ... WHERE genres.id IN (1,2,3) который по сути является OR-выражением.

Чтобы это исправить, вам нужно отфильтровать количество выбранных жанров в Ruby или SQL. Я бы сделал это с SQL следующим образом:

genre_ids = params['genre_ids']
items = Item.joins(:genres).where('genres.id' => genre_ids).group('items.id').having("count(*) = #{genre_ids.size}")

При этом вы будете выбирать предметы с точным заданным набором жанров. Не забудьте обработать случай с пустым genre_ids в параметрах.

Другие вопросы по тегам