Package sagan.search.support

Source Code of sagan.search.support.SearchQueryBuilder

package sagan.search.support;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.elasticsearch.common.joda.time.format.ISODateTimeFormat;
import org.elasticsearch.index.query.AndFilterBuilder;
import org.elasticsearch.index.query.OrFilterBuilder;
import org.elasticsearch.index.query.QueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.index.query.RangeFilterBuilder;
import org.elasticsearch.index.query.TermsFilterBuilder;
import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.search.facet.terms.TermsFacet;
import org.elasticsearch.search.facet.terms.TermsFacetBuilder;
import org.elasticsearch.search.highlight.HighlightBuilder;

import org.springframework.data.domain.Pageable;

import io.searchbox.core.Search;

class SearchQueryBuilder {
    private static final String BOOST_CURRENT_VERSION_SCRIPT = "_score * (_source.current ? 1.1 : 1.0)";
    private static final String BOOSTED_TITLE_FIELD = "title^10";
    private static final String RAW_CONTENT_FIELD = "rawContent";

    SearchQueryBuilder() {
    }

    Search.Builder forEmptyQuery(Pageable pageable, List<String> filters) {
        QueryBuilder query = QueryBuilders.boolQuery().should(QueryBuilders.matchAllQuery());

        String search = buildSearch(query, filters, pageable);
        return new Search.Builder(search);
    }

    Search.Builder forQuery(String queryTerm, Pageable pageable, List<String> filters) {
        QueryBuilder query = QueryBuilders.multiMatchQuery(queryTerm, BOOSTED_TITLE_FIELD, RAW_CONTENT_FIELD);
        query = QueryBuilders.customScoreQuery(query).script(BOOST_CURRENT_VERSION_SCRIPT);

        String search = buildSearch(query, filters, pageable);
        return new Search.Builder(search);
    }

    private String buildSearch(QueryBuilder query, List<String> filters, Pageable pageable) {
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();

        addPagination(pageable, searchSourceBuilder);
        addQuery(query, searchSourceBuilder);
        addFilters(filters, searchSourceBuilder);
        addFacetPathsResult(searchSourceBuilder);
        addHighlights(searchSourceBuilder);

        return searchSourceBuilder.toString();
    }

    private void addPagination(Pageable pageable, SearchSourceBuilder searchSourceBuilder) {
        searchSourceBuilder.from(pageable.getOffset());
        searchSourceBuilder.size(pageable.getPageSize());
    }

    private SearchSourceBuilder addQuery(QueryBuilder query, SearchSourceBuilder searchSourceBuilder) {
        return searchSourceBuilder.query(query);
    }

    private void addFilters(List<String> filters, SearchSourceBuilder searchSourceBuilder) {
        AndFilterBuilder andFilterBuilder = new AndFilterBuilder();
        filterFutureResults(andFilterBuilder);
        filterFacets(filters, andFilterBuilder);
        searchSourceBuilder.filter(andFilterBuilder);
    }

    private void filterFutureResults(AndFilterBuilder filterBuilder) {
        String formattedDate = ISODateTimeFormat.dateTimeNoMillis().print(new Date().getTime());
        RangeFilterBuilder rangeFilterBuilder =
                new RangeFilterBuilder("publishAt").to(formattedDate).includeLower(true).includeUpper(true);

        filterBuilder.add(rangeFilterBuilder);
    }

    private void filterFacets(List<String> filters, AndFilterBuilder filterBuilder) {
        if (filters != null && !filters.isEmpty()) {

            Map<String, List<String>> splitFilters = splitFilters(filters);
            List<String> projects = splitFilters.get("projects");
            List<String> apiRef = splitFilters.get("apiRef");
            List<String> otherFacetPaths = splitFilters.get("others");

            AndFilterBuilder projectApiRefAnded = new AndFilterBuilder();
            if (apiRef.size() > 0) {
                projectApiRefAnded.add(new TermsFilterBuilder("facetPaths", apiRef).execution("or"));
            }

            if (projects.size() > 0) {
                projectApiRefAnded.add(new TermsFilterBuilder("facetPaths", projects).execution("or"));
            }

            OrFilterBuilder outermostFilter = new OrFilterBuilder();
            outermostFilter.add(projectApiRefAnded);
            if (otherFacetPaths.size() > 0) {
                outermostFilter.add(new TermsFilterBuilder("facetPaths", otherFacetPaths).execution("or"));
            }

            filterBuilder.add(outermostFilter);
        }
    }

    private Map<String, List<String>> splitFilters(List<String> filters) {
        ArrayList<String> projects = new ArrayList<>();
        ArrayList<String> apiRef = new ArrayList<>();
        ArrayList<String> others = new ArrayList<>();

        for (String filter : filters) {
            if (filter.startsWith("Projects")) {
                if (filter.equals("Projects/Api") || filter.equals("Projects/Reference")) {
                    apiRef.add(filter);
                } else {
                    projects.add(filter);
                }
            } else {
                others.add(filter);
            }
        }

        HashMap<String, List<String>> splitFilters = new HashMap<>();
        splitFilters.put("projects", projects);
        splitFilters.put("apiRef", apiRef);
        splitFilters.put("others", others);
        return splitFilters;
    }

    private void addFacetPathsResult(SearchSourceBuilder searchSourceBuilder) {
        TermsFacetBuilder facetBuilder = new TermsFacetBuilder("facet_paths_result")
                .field("facetPaths")
                .order(TermsFacet.ComparatorType.TERM).size(100000);

        searchSourceBuilder.facet(facetBuilder);
    }

    private void addHighlights(SearchSourceBuilder searchSourceBuilder) {
        HighlightBuilder highlightBuilder =
                new HighlightBuilder().order("score").requireFieldMatch(false).field("rawContent", 300, 1);

        searchSourceBuilder.highlight(highlightBuilder);
    }

}
TOP

Related Classes of sagan.search.support.SearchQueryBuilder

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.