Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
129 changes: 30 additions & 99 deletions app/api/srch/search.rb
Original file line number Diff line number Diff line change
Expand Up @@ -5,28 +5,22 @@ module Srch
class Search < Grape::API
include Skylight::Helpers

# we are using a group of reusable parameters using a shared params helper
# see /app/api/srch/shared_params.rb
# Using shared parameters defined in a helper module
helpers SharedParams

include Grape::Rails::Cache

# Endpoint definitions
# Basic implementation from classic plots2 SearchController
# Main API resource for search-related endpoints
resource :srch do
# Request URL should be /api/srch/all?query=QRY
desc 'Perform a search of all available resources', hidden: false,
is_array: false,
nickname: 'search_all'
params do
use :common
end

# Endpoint to search across all available resources (profiles, notes, tags, etc.)
get :all do
search_request = SearchRequest.from_request(params)
results = Search.execute(:all, params)
results_list = []

if results.present?
# Mapping profile results
results_list << results[:profiles].map do |model|
DocResult.new(
doc_type: 'USERS',
Expand All @@ -35,6 +29,7 @@ class Search < Grape::API
)
end

# Mapping notes results
results_list << results[:notes].map do |model|
DocResult.new(
doc_id: model.nid,
Expand All @@ -44,6 +39,7 @@ class Search < Grape::API
)
end

# Mapping wiki results
results_list << results[:wikis].map do |model|
DocResult.new(
doc_id: model.nid,
Expand All @@ -53,6 +49,7 @@ class Search < Grape::API
)
end

# Mapping tag results
results_list << results[:tags].map do |model|
DocResult.new(
doc_id: model.nid,
Expand All @@ -62,6 +59,7 @@ class Search < Grape::API
)
end

# Mapping map/location results
results_list << results[:maps].map do |model|
DocResult.new(
doc_id: model.nid,
Expand All @@ -71,6 +69,7 @@ class Search < Grape::API
)
end

# Mapping question results with score based on comments
results_list << results[:questions].map do |model|
DocResult.new(
doc_id: model.nid,
Expand All @@ -80,23 +79,18 @@ class Search < Grape::API
score: model.comments.length
)
end

DocList.new(results_list.flatten, search_request)
else
DocList.new('', search_request)
end
end

# Request URL should be /api/srch/profiles?query=QRY[&sort_by=recent&order_direction=desc&field=username]
desc 'Perform a search of profiles', hidden: false,
is_array: false,
nickname: 'search_profiles'

params do
use :common, :sorting, :ordering, :field
end
# Endpoint to search user profiles
get :profiles do
search_request = SearchRequest.from_request(params)
# TODO: evaluate if disabling this caching action actually speeds things up?

# Caching results for performance improvement
cache(key: "api:profiles:#{params[:query]}:#{params[:limit]}:#{params[:sort_by]}:#{params[:order_direction]}:#{params[:field]}", expires_in: 2.day) do
results = Search.execute(:profiles, params)

Expand All @@ -118,14 +112,7 @@ class Search < Grape::API
end
end

# Request URL should be /api/srch/notes?query=QRY
desc 'Perform a search of research notes', hidden: false,
is_array: false,
nickname: 'search_notes'

params do
use :common
end
# Endpoint to search research notes
get :notes do
search_request = SearchRequest.from_request(params)
results = Search.execute(:notes, params)
Expand All @@ -139,27 +126,20 @@ class Search < Grape::API
doc_title: model.title
)
end

DocList.new(docs, search_request)
else
DocList.new('', search_request)
end
end

# Request URL should be /api/srch/content?query=QRY
desc 'Perform a search of nodes and tags', hidden: false,
is_array: false,
nickname: 'search_content'

params do
use :common
end
# Endpoint to search tags and notes together
get :content do
search_request = SearchRequest.from_request(params)
results = Search.execute(:content, params)
results_list = []

if results.present?
# Mapping tag names
results_list << results[:tags].map do |tagname|
DocResult.new(
doc_id: tagname,
Expand All @@ -168,6 +148,8 @@ class Search < Grape::API
doc_title: tagname
)
end

# Mapping note results
results_list << results[:notes].map do |model|
DocResult.new(
doc_id: model.nid,
Expand All @@ -176,20 +158,14 @@ class Search < Grape::API
doc_title: model.title
)
end

DocList.new(results_list.flatten, search_request)
else
DocList.new('', search_request)
end
end

# Request URL should be /api/srch/nodes?query=QRY
desc 'Perform a search of nodes', hidden: false,
is_array: false,
nickname: 'search_content'

params do
use :common
end
# Endpoint to search nodes
get :nodes do
search_request = SearchRequest.from_request(params)
results = Search.execute(:nodes, params)
Expand All @@ -203,21 +179,13 @@ class Search < Grape::API
doc_title: model.title
)
end

DocList.new(docs, search_request)
else
DocList.new('', search_request)
end
end

# Request URL should be /api/srch/wikis?query=QRY
desc 'Perform a search of wikis pages', hidden: false,
is_array: false,
nickname: 'search_wikis'

params do
use :common
end
# Endpoint to search wiki pages
get :wikis do
search_request = SearchRequest.from_request(params)
results = Search.execute(:wikis, params)
Expand All @@ -231,21 +199,13 @@ class Search < Grape::API
doc_title: model.title
)
end

DocList.new(docs, search_request)
else
DocList.new('', search_request)
end
end

# Request URL should be /api/srch/questions?query=QRY
desc 'Perform a search of questions tables', hidden: false,
is_array: false,
nickname: 'search_questions'

params do
use :common, :sorting, :ordering
end
# Endpoint to search questions
get :questions do
search_request = SearchRequest.from_request(params)
results = Search.execute(:questions, params)
Expand All @@ -260,21 +220,13 @@ class Search < Grape::API
score: model.comments.length
)
end

DocList.new(docs, search_request)
else
DocList.new('', search_request)
end
end

# Request URL should be /api/srch/tags?query=QRY
desc 'Perform a search of documents associated with tags within the system', hidden: false,
is_array: false,
nickname: 'search_tags'

params do
use :common
end
# Endpoint to search tags
get :tags do
Skylight.instrument title: "Tags search" do
search_request = SearchRequest.from_request(params)
Expand All @@ -289,22 +241,14 @@ class Search < Grape::API
doc_title: model.title
)
end

DocList.new(docs, search_request)
else
DocList.new('', search_request)
end
end
end

# Request URL should be /api/srch/taglocations?nwlat=200.0&selat=0.0&nwlng=0.0&selng=200.0[&tag=awesome]
desc 'Perform a search of documents having nearby latitude and longitude tag values', hidden: false,
is_array: false,
nickname: 'search_tag_locations'

params do
use :geographical, :additional, :period, :sorting, :ordering
end
# Endpoint to search locations based on geographical bounds
get :taglocations do
search_request = SearchRequest.from_request(params)
results = Search.execute(:taglocations, params)
Expand All @@ -313,6 +257,7 @@ class Search < Grape::API
docs = results.map do |model|
doctype = model.has_power_tag('question') ? 'QUESTION' : 'NOTE'
doctype = 'WIKI' if model.type == 'page'

DocResult.new(
doc_id: model.nid,
doc_type: doctype,
Expand All @@ -326,8 +271,6 @@ class Search < Grape::API
blurred: model.blurred?,
place_name: model.has_power_tag('place') ? model.power_tag('place') : '',
created_at: model.created_at
# time_since: distance_of_time_in_words(model.created_at, Time.current, { include_seconds: false, scope: 'datetime.time_ago_in_words' }), # works, but really slows down the search results
# comment_count: model.comments_viewable_by(current_user).length # causes an error because of current_user?
)
end
DocList.new(docs, search_request)
Expand All @@ -336,13 +279,7 @@ class Search < Grape::API
end
end

# Request URL should be /api/srch/nearbyPeople?nwlat=200.0&selat=0.0&nwlng=0.0&selng=200.0[&tag=awesome&sort_by=recent]
desc 'Perform a search to show people nearby a given location', hidden: false,
is_array: false,
nickname: 'search_nearby_people'
params do
use :geographical, :additional, :field, :period, :sorting, :ordering
end
# Endpoint to find nearby people based on location
get :nearbyPeople do
search_request = SearchRequest.from_request(params)
results = Search.execute(:nearbyPeople, params)
Expand All @@ -367,14 +304,7 @@ class Search < Grape::API
end
end

# Request URL should be /api/srch/places?query=QRY
desc 'Perform a search of places', hidden: false,
is_array: false,
nickname: 'search_places'

params do
use :common
end
# Endpoint to search places
get :places do
search_request = SearchRequest.from_request(params)
results = Search.execute(:places, params)
Expand All @@ -388,18 +318,19 @@ class Search < Grape::API
doc_title: model.title
)
end

DocList.new(docs, search_request)
else
DocList.new('', search_request)
end
end
end

# Executes search based on endpoint type and validated criteria
def self.execute(endpoint, params)
search_type = endpoint
search_criteria = SearchCriteria.new(params)
search_criteria.validate_period_from_to

if search_criteria.valid?
ExecuteSearch.new.by(search_type, search_criteria)
else
Expand Down