Websites/app/logical/e621_pool_query_builder.rb

77 lines
2.4 KiB
Ruby

# frozen_string_literal: true
class E621PoolQueryBuilder
attr_accessor :params, :must, :must_not, :should, :order
def initialize(params)
@params = params
@must = []
@must_not = []
@should = []
@order = []
end
def add_tag_string_search(query)
tag_list = query.split
aliases = E621::TagAlias.where(antecedent_name: tag_list.map { |t| t.sub(/\A([-~])/, "") })
tag_list.map do |tag|
type = :must
if tag =~ /\A([-~])/
tag = tag[1..]
type = $1 == "~" ? :should : :must_not
end
if (aliased = aliases.find { |a| a.antecedent_name == tag })
tag = aliased.consequent_name
end
case type
when :must
must << { term: { tags: tag } }
when :must_not
must_not << { term: { tags: tag } }
when :should
should << { term: { tags: tag } }
end
end
end
def add_other_search
must << { match_phrase_prefix: { name: params[:name_matches] } } if params[:name_matches].present?
must << { match_phrase_prefix: { description: params[:description_matches] } } if params[:description_matches].present?
must << { term: { creator_id: params[:creator_id] } } if params[:creator_id].present?
must << { term: { creator_id: Requests::E621.name_to_id(params[:creator_name]) } } if params[:creator_name].present?
must << { term: { is_active: params[:is_active] } } if params[:is_active].present?
must << { term: { category: params[:category] } } if params[:category].present?
must << { term: { id: params[:id] } } if params[:id].present?
end
def add_order
case params[:order]
when "name"
order << { name_kw: :asc }
when "created_at"
order << { created_at: :desc }
when "post_count"
order << { post_count: :desc }
when "id_asc"
order << { id: :asc }
else
order << { id: :desc }
end
end
def search_sql
q = E621::Pool.all
q = q.where("string_to_array(tag_string, ' ') @> ARRAY[?]", must) if must.any?
q = q.where("NOT(string_to_array(tag_string, ' ') && ARRAY[?])", must_not) if must_not.any?
q = q.where("string_to_array(tag_string, ' ') && ARRAY[?]", should) if should.any?
q
end
def search(page = 1, limit = 100)
add_tag_string_search(params[:tags]) if params[:tags].present?
add_other_search
add_order
PoolIndex.search(page, limit, must: must, must_not: must_not, should: should, order: order)
end
end