ES高级查询,高亮显示

来源:互联网 发布:微老板软件 编辑:程序博客网 时间:2024/06/07 08:12
package xxx.xxx.xxx.xxx;import org.elasticsearch.action.search.SearchType;import org.elasticsearch.action.search.SearchResponse;import org.elasticsearch.common.text.Text;import org.elasticsearch.search.aggregations.AggregationBuilders;import org.elasticsearch.search.aggregations.Aggregation;import org.elasticsearch.search.aggregations.metrics.avg.InternalAvg;import org.elasticsearch.client.transport.TransportClient;import org.elasticsearch.common.settings.Settings;import org.elasticsearch.common.transport.InetSocketTransportAddress;import org.elasticsearch.common.transport.TransportAddress;import org.elasticsearch.index.query.QueryBuilder;import org.elasticsearch.index.query.QueryBuilders;import org.elasticsearch.search.SearchHit;import org.elasticsearch.search.SearchHits;import org.elasticsearch.search.aggregations.AbstractAggregationBuilder;import org.elasticsearch.search.aggregations.Aggregations;import org.elasticsearch.search.highlight.HighlightField;import org.elasticsearch.search.sort.SortOrder;import org.junit.After;import org.junit.Before;import org.junit.Test;import java.net.InetAddress;import java.net.UnknownHostException;import java.util.Map;/** * ElasticSearch高级查询基本操作 * *  操作的入口TransportClient */public class ElasticSearchQuery {    private TransportClient tc;    private int port = 9300;    private String clusterName = "bigdata";    private String node_1 = "hadoop01";    private String node_2 = "hadoop02";    private String node_3 = "hadoop03";    private String[] indices = {"bigdata","bank"};    @Before    public void setUp() throws UnknownHostException {        Settings setting = Settings.builder()                .put("cluster.name",clusterName)                .put("analyzer","ik")                .build();        tc = TransportClient.builder().settings(setting).build();        TransportAddress hadoop = new InetSocketTransportAddress(InetAddress.getByName(node_1),port);        TransportAddress spark = new InetSocketTransportAddress(InetAddress.getByName(node_2),port);        TransportAddress storm = new InetSocketTransportAddress(InetAddress.getByName(node_3),port);        tc.addTransportAddresses(hadoop,spark,storm);    }    /**     * 查找包涵Apache的数据信息     */    @Test    public void testSearch(){//        tc.prepareSearch(indices)//                .setSearchType(SearchType.DEFAULT)//                .setQuery(QueryBuilders.matchQuery("author", "Apache"))//                .get();        SearchResponse response = tc.prepareSearch(indices)//设置要进行查询的方式,有4中查询方式:QUERY_AND_FETCH、QUERY_THEN_FETCH、DFS_QUERY_AND_FETCH、DFS_QUERY_THEN_FETCH                .setSearchType(SearchType.DEFAULT)//设置查询的内容,和在哪些字段中进行查询,要通过QueryBuilders来进行设置                .setQuery(QueryBuilders.matchQuery("author", "Apache"))                .get();        SearchHits hits = response.getHits();        long totalHits = hits.getTotalHits();        System.out.println("老王为您找到相关结果约 " + totalHits);        for(SearchHit searchHit:hits){            printSearchHit(searchHit);        }    }    @Test    public void testSearch_02(){        SearchResponse searchResponse = tc.prepareSearch(indices)                .setSearchType(SearchType.DEFAULT)                .setQuery(QueryBuilders.prefixQuery("name", "h"))                .addSort("name", SortOrder.DESC)                .setFrom(0)                .setSize(10)                .get();        SearchHits hits = searchResponse.getHits();        long totalHits = hits.getTotalHits();        System.out.println("老王为您找到相关结果约 " + totalHits);        for(SearchHit searchHit: hits){            printSearchHit(searchHit);        }    }    /**     * 查询年龄在35到40之间的成员信息     */    @Test    public void testSearch_03(){        SearchResponse searchResponse = tc.prepareSearch(indices)                .setSearchType(SearchType.DEFAULT)                .setQuery(QueryBuilders.rangeQuery("age").gte(35).lte(40))                .addSort("balance", SortOrder.DESC)                .setFrom(0)                .setSize(2)                .get();        SearchHits hits = searchResponse.getHits();        long totalHits = hits.getTotalHits();        System.out.println("老王为您找到相关结果约 " + totalHits);        for(SearchHit searchHit:hits){            printSearchHit(searchHit);        }    }    /**     * 执行聚合操作     * 查询年龄在35到40之间的平均年龄     */    @Test    public void testSearch_04(){        SearchResponse searchResponse = tc.prepareSearch(indices)                .setSearchType(SearchType.DEFAULT)                .setQuery(QueryBuilders.rangeQuery("age").gte(35).lte(40))                .addAggregation(AggregationBuilders.avg("avg_age").field("age"))                .get();        SearchHits hits = searchResponse.getHits();        long totalHits = hits.getTotalHits();        System.out.println("老王为您找到相关结果约 " + totalHits);        Aggregations aggregations = searchResponse.getAggregations();        Map<String, Aggregation> aggregationMap = aggregations.asMap();        for(Map.Entry<String, Aggregation> map:aggregationMap.entrySet()){            String key = map.getKey();            //由Aggregations---->强转为InternalAvg,才拿到平均值            InternalAvg aggregation = (InternalAvg)map.getValue();            System.out.println("key = " + key);            System.out.println("aggregation = " + aggregation.getValue());        }    }    /**     * 代码的高亮显示     * HighLight     * <font color='red'>keyword</font>     * 对于这种高亮显示,就是在查询关键字之前和之后分别追加前缀和后缀     * 前缀:pre     * 后缀:post     *     * 设置高亮注意的地方:     *  1、设置高亮字段:addHighlightedField     *  2、设置高亮的前缀和后缀:     *      setHighlighterPreTags("<font color='red'>")     *      setHighlighterPostTags("</font>")     *  3、获取高亮数据     *      searchHit.getHighlightFields()中的fragment获取     */    @Test    public void testSearch_05(){        SearchResponse response = tc.prepareSearch(indices)                .setSearchType(SearchType.DEFAULT)                .setQuery(QueryBuilders.matchQuery("name", "hadoop02"))                .addHighlightedField("name")                .setHighlighterPreTags("<font color='red'>")                .setHighlighterPostTags("</font>")                .get();        SearchHits searchHits = response.getHits();        long totalHits = searchHits.getTotalHits();        System.out.println("老王为您找到相关结果约 " + totalHits);        for(SearchHit searchHit : searchHits){            System.out.println(" ================== " );            Map<String, HighlightField> highlightFields = searchHit.getHighlightFields();            for(Map.Entry<String, HighlightField> me : highlightFields.entrySet()){                String key = me.getKey();                System.out.println("key = " + key);                HighlightField highlightField = me.getValue();                String name = highlightField.getName();                System.out.println("name = " + name);                Text[] fragments = highlightField.getFragments();                String hightStr = "";                for(Text text : fragments){                    hightStr += text.toString();                }                System.out.println("hightStr = " + hightStr);            }        }    }    /**     * 查询中文     *     * 分词:     *  我们发现设置Query为termQuery,QueryBuilders.termQuery("author", "孙")有结果     *  而Query为termQuery,QueryBuilders.termQuery("author", "孙鹏")没有结果     *  这是因为中文分词的原因,英文分词非常简单:就是通过一个个的空格进行拆分,而汉字的拆分默认情况下就是一个字一个字的拆     *     *  我们要想查询孙鹏 或者鹏飞这些词组的时候,默认的拆分方式就提供不了数据了,为了满足用户的需要,在软件发展过程中就有非常多的     *  各种各样的分词法(庖丁解牛分词法,IK分词法)     *     *  如果使用了IK等分词法,对索引库中已经存在的数据不执行相应的分词,只有对新增的数据才会执行相应的分词!!!     */    @Test    public void testSearch_Chinese(){        indices = new String[]{"bigdata"};        SearchResponse response = tc.prepareSearch(indices)                .setSearchType(SearchType.DEFAULT)      //奥利猫(ik之前)    法拉狗                .setQuery(QueryBuilders.termQuery("author", "奥利"))                .get();        SearchHits hits = response.getHits();        long totalHits = hits.getTotalHits();        System.out.println("老王为您找到相关结果约 " + totalHits);        for(SearchHit searchHit : hits){            printSearchHit(searchHit);        }    }    private void printSearchHit(SearchHit searchHit){        String index = searchHit.getIndex();        String type = searchHit.getType();        String id = searchHit.getId();        long version = searchHit.getVersion();        float score = searchHit.getScore();        Map<String, Object> source = searchHit.getSource();        System.out.println("index "+index);        System.out.println("type "+type);        System.out.println("id "+id);        System.out.println("version "+version);        System.out.println("score "+score);        System.out.println("source "+source);    }    @After    public void cleanUp(){        if(tc != null){            tc.close();        }    }}

原创粉丝点击