* FEATURE: HyDE-powered semantic search. It relies on the new outlet added on discourse/discourse#23390 to display semantic search results in an unobtrusive way. We'll use a HyDE-backed approach for semantic search, which consists on generating an hypothetical document from a given keywords, which gets transformed into a vector and used in a asymmetric similarity topic search. This PR also reorganizes the internals to have less moving parts, maintaining one hierarchy of DAOish classes for vector-related operations like transformations and querying. Completions and vectors created by HyDE will remain cached on Redis for now, but we could later use Postgres instead. * Missing translation and rate limiting --------- Co-authored-by: Roman Rizzi <[email protected]>
38 lines
1.0 KiB
Ruby
38 lines
1.0 KiB
Ruby
# frozen_string_literal: true
|
|
|
|
module DiscourseAi
|
|
module Embeddings
|
|
class EmbeddingsController < ::ApplicationController
|
|
requires_plugin ::DiscourseAi::PLUGIN_NAME
|
|
|
|
SEMANTIC_SEARCH_TYPE = "semantic_search"
|
|
|
|
def search
|
|
query = params[:q]
|
|
|
|
grouped_results =
|
|
Search::GroupedSearchResults.new(
|
|
type_filter: SEMANTIC_SEARCH_TYPE,
|
|
term: query,
|
|
search_context: guardian,
|
|
use_pg_headlines_for_excerpt: false,
|
|
)
|
|
|
|
semantic_search = DiscourseAi::Embeddings::SemanticSearch.new(guardian)
|
|
|
|
if !semantic_search.cached_query?(query)
|
|
RateLimiter.new(current_user, "semantic-search", 4, 1.minutes).performed!
|
|
end
|
|
|
|
hijack do
|
|
semantic_search
|
|
.search_for_topics(query)
|
|
.each { |topic_post| grouped_results.add(topic_post) }
|
|
|
|
render_serialized(grouped_results, GroupedSearchResultSerializer, result: grouped_results)
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|