In my app I am using Sunspot for a fulltext search. The problem is that I want to have sorting by association model field. In my case:
class Movie < ActiveRecord::Base
attr_accessible :description, :genre, :name
has_many :premieres
end
and my Premier model has:
belongs_to :movie
Searching by movie name is done by defining the method:
def movie_name
movie.name
end
but when I try to do:
order_by :movie_name, :asc
It says:
No field configured for Premiere with name 'movie_name'
How do I make this sorting available?
you can do it like this
searchable auto_index: true do
text :movie_name do
if self.movie.present?
self.movie.name
end
end
end
then you can use
order_by :movie_name, :asc
Related
I am trying to set search on a model that has a lot of different associations. I am starting with the belongs_to associations. I am able to search on the name field of the Product model successfully but the when I perform a search on what would be in the associated models I just get the default results.
What am I doing wrong?
Any help would be much appreciated.
#Product Model
Class Product < ActiveRecord::Base
searchable do
text :name
integer :store_id, :references => Store.name
text :store do
Store.all.map { |store| store.name }
end
end
end
#product controler
def search
#search = Sunspot.search(Product) do
fulltext params[:search] do
fields(:name, :store)
end
end
#products = #search.results
end
#Store Model
searchable do
text :name
end
Class Product < ActiveRecord::Base
belongs_to :store
searchable do
text :name
index :store do
index :name
end
integer :store_id # do you really need this? I think not.
end
end
Don't forget to reindex after each change in your models.
EDIT: You don't need to index the Store class by itself, unless you plan to search on it.
I have one to many association between jobs and companies and i have implemented a search form for jobs using sunspot gem but i want when i search a company_name i have all jobs results of the company searched how can i do this
this is my job model
class Job < ActiveRecord::Base
belongs_to :company
searchable do
text :job_title, boost: 4
text :profile_recherche
end
this is my company model
class Company < ActiveRecord::Base
has_many :jobs
this is my jobs search controller
def search
#jobs = Sunspot.search(Job) do
keywords params[:query]
fulltext params[:query]
paginate(page: params[:page], per_page: 1)
end.results
respond_to do |format|
format.html { render :action => "index" }
end
end
It sounds like you want to search Jobs by job_title, profile_reserche, and company.name. If I'm guessing what you want correctly, changing your searchable block like so should do it:
class Job < ActiveRecord::Base
belongs_to :company
searchable do
text :job_title, boost: 4
text :profile_recherche
text :company_name do
company.name
end
end
end
One caveat here is that if you have overlap in tokens, stems, n-grams, whatever between these various fields, you could have some interesting search results.
I have simple Rails app with a Post model that belongs to a creator (which is a User object) and I want to find posts that match the creator's first_name.
class Post < ActiveRecord::Base
include Tire::Model::Search
include Tire::Model::Callbacks
belongs_to :creator, polymorphic: true
mapping do
indexes :id, type: 'integer'
indexes :title, boost: 10
indexes :creator do
indexes :first_name
indexes :service_type
end
end
end
When I run search, there are no results:
Post.tire.search(load: true, page: params[:page], per_page: params[:per_page]) do
query do
match 'creator.first_name', 'Matt'
end
end
Even when I've run rake environment tire:import:all FORCE=true and verified that a Post exists with a creator that has a first name of 'Matt' in the database.
Is there something I am missing? Thanks!
UPDATE:
Adding the following to Post.rb did the trick:
def to_indexed_json
as_json.merge(
creator: creator.as_indexed_json
).to_json
end
Apparently, you need to specify the association in the to_indexed_json to make it work.
I have a model User and Listing in my rails app. User has many listings and listing belongs to user. I also have a attribute name rating in user table. What I want is to search the keyword in Listing model and order it based on rating attribute of User model.
This is what I have in Listing model
searchable do
text :title, :default_boost => 3
text :description, :default_boost => 2
integer :category_id, :references => Category
integer :subcategory_id, :references => Subcategory
string :zipcode
time :created_at
double :user do
user.rating
end
end
And this is how I am trying to search
#search = Sunspot.search(Listing) do
keywords params[:q] do
fields :title
end
order_by THIS IS WHERE I NEED HELP
paginate :page => params[:page], :per_page => 20
end
You will need to add the keyword and rating attributes to the listing searachable method.
class Listing < ActiveRecord::Base
belongs_to :user
searchable do
text :keyword
integer :rating { user.rating }
end
end
Then in your search action in your controller
Listing.search do
fulltext params[:q]
order_by :rating, :desc
end
See http://sunspot.github.com/ for more examples.
Looking at your code, you need to change in your searchable method
double :user do
user.rating
end
to
double :rating do
user.rating
end
class Office < ActiveRecord::Base
has_many :users
searchable do
text :name
location :coordinates do
Sunspot::Util::Coordinates.new(latitude, longitude)
end
end
end
class User < ActiveRecord::Base
belongs_to :office
searchable do
text :name, :default_boost => 2
text :description
end
end
With this kind of a setup, how can I search using SunSpot (on Solr) on Rails for a user within a given lat/long? For example, I want to be able to do this:
#search = User.search() do
fulltext(params[:q])
with(:coordinates).near(#lat, #long, :precision => 5)
end
The following works just fine:
#search = Office.search() do
fulltext(params[:q])
with(:coordinates).near(#lat, #long, :precision => 5)
end
What is the best way to accomplish this given that the lat/long for each User really lives in the Office class?
The office association should be in scope inside your User's searchable block.
Given that, here's what I would start with (untested, off the top of my head, etc):
class User < ActiveRecord::Base
belongs_to :office
searchable do
text :name, :default_boost => 2
text :description
location :coordinates do
Sunspot::Util::Coordinates.new(office.latitude, office.longitude)
end
end
end
Fetching values for associated objects in a block like this is actually a pretty common pattern for handling denormalization with Sunspot.