Rails + Sunspot: фасет «Неназначенный» для фильтрации записей, которым не назначена ассоциация? - PullRequest
0 голосов
/ 09 ноября 2011

Все еще изучаю аспекты, но я хотел бы отфильтровать записи, которым не назначена соответствующая запись. Сначала код:

Модель:

class Project < ActiveRecord::Base
  belongs_to :category

  searchable do
    text :name
    integer :category_id, :references => Category
  end
end

Контроллер:

class ProjectsController < ApplicationController
  def index
    @search = Project.search do
      fulltext params[:q]
      facet :category_id
      with(:category_id, params[:category_id]) if params[:category_id].present?
    end
    @projects = @search.results
    respond_with(@projects)
  end

Вид:

<ul>
  <% for row in @search.facet(:category_id).rows %>
    <li>
      <% if params[:category_id].blank? %>
        <%= link_to row.instance.name, :category_id => row.value %> (<%= row.count %>)
      <% else %>
        <strong><%= row.value %></strong> (<%= link_to "remove", :category_id => nil %>)
      <% end %>
    </li>
  <% end %>
</ul>

Представление отображает список фильтров категорий с их соответствующим количеством, однако я хочу включить фасет «Неназначенный» (и его количество) , который будет запрашивать проекты, которым не была назначена категория. Это возможно с гранями? Кроме того, как насчет фасета «Назначен любой» (и его количества), который фильтрует проекты, которым назначена категория любая ? Спасибо.

1 Ответ

2 голосов
/ 04 июля 2012

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

Фасеты - это способ классификации текущих результатов поиска.Один из способов реализовать фасет «Неназначенный» - это фактически проиндексировать объекты с ним.

В вашей модели проекта я бы изменил его на:

class Project < ActiveRecord::Base
  belongs_to :category

  searchable do
    text :name
    string :category_name do
      category_id.present? ? (category.name + "|" + category_id.to_s) : "Unassigned"
    end
  end
end

Я вижу вас 'повторно используйте row.instance.name в представлении, чтобы получить название категории.Поскольку я переключил атрибут searchable на строку (и по понятным причинам вы не можете использовать :references и row.instance со строковым значением!), Я решил индексировать поле с помощью комбинации category_name|category_id поле типа.Если Project не имеет category_id, используется строка "Unassigned".

Теперь мы изменим код в вашем блоке поиска для отражения или изменения модели.

class ProjectsController < ApplicationController
  def index
    @search = Project.search do
      fulltext params[:q]
      facet :category_name
      with(:category_name, params[:category_name]) if params[:category_name].present?
    end
    @projects = @search.results
    respond_with(@projects)
  end

и код представления также изменяется:

<ul>
  <% for row in @search.facet(:category_name).rows %>
    <li>
      <% if params[:category_name].blank? %>
        <%= link_to (row.value.include? '|') ? row.value.split('|')[0] : row.value, :category_name => row.value %> (<%= row.count %>)
      <% else %>
        <strong><%= row.value %></strong> (<%= link_to "remove", :category_name => nil %>)
      <% end %>
    </li>
  <% end %>
</ul>
...