使用Java Rest Client操做Elasticsearch

Elasticsearch做为一个成熟的开源框架,对主流的多种客户端语言都支持,好比Java,JavaScript ,PHP,.Net,Python,Ruby,CURL固然还有一些小众的语言,虽然es官网没支持,可是我的开发者也有一些开源的,具体的可在es官网clients地址查看:html

https://www.elastic.co/guide/en/elasticsearch/client/index.htmljava

开发过程当中,基本最经常使用的就是Java和curl的方式了,由于es自己就是使用java语言开发的,因此对Java的支持应该是最到位了,此外es也支持rest ful的DSL的访问方式,咱们能够在linux上轻松的使用curl命令来对es进行增删改查,curl的操做方式大多数都是临时的,实际开发的咱们仍是用编程语言来访问的:linux

es支持Java API的访问方式,支持很是全面,惟一的缺点就是依赖有点多,代码稍臃肿,有时候咱们想简单的开发一个很是小的功能,又不想使用java笨重的客户端方式,应该怎么办?apache

上文说到es支持rest的访问方式,那么咱们彻底可使用httpclient或者jsoup来直接发送http请求不就好了吗?实际上是能够的,使用httpclient和jsoup来发送curl的命令也能操做es,获取结果。这里面有一个须要注意的地方。编程

httpclient和jsoup都不直接支持发送DELETE方法带参数的请求,这一点是个小缺陷,若是这个不支持,意味着一些删除操做好比delete by query可能支持不太好。jsoup是彻底不支持,而在httpclient里面咱们能够经过继承重写HttpEntityEnclosingRequestBase来知足,删除请求带参数体,下面来看下如何使用:json

继承重写的代码:api

package tools;

import org.apache.http.client.methods.HttpEntityEnclosingRequestBase;

import java.net.URI;

public class MyHttpDelete extends HttpEntityEnclosingRequestBase {
    //
    public static final String METHOD_NAME = "DELETE";
    //
    public String getMethod() {
        return METHOD_NAME;
    }
    //
    public MyHttpDelete(final String uri) {
        super();
        setURI(URI.create(uri));
    }
    //
    public MyHttpDelete(final URI uri) {
        super();
        setURI(uri);
    }
    //
    public MyHttpDelete() {
        super();
    }
}

而后使用httpclient发送一个删除请求:多线程

//实例化http,删除id=1001的一条数据
    val client = HttpClients.createDefault()
    val httpdelete = new MyHttpDelete("http://localhost:9200/test_index/logs/_query")
    val s = new StringEntity("{  \"query\": 
{   \"query_string\": {     \"query\":  id:1001    "       }  }} ",ContentType.APPLICATION_JSON)
    httpdelete.setEntity(s)
    val rs=client.execute(httpdelete)//执行删除
    //解析响应结果
    val json = EntityUtils.toString(rs.getEntity(), "UTF-8")
    //释放资源
    client.close()

httpclient仍是比较强大的,可是上面的代码仍是有点复杂,并且涉及链接的地方是有问题的,咱们都知道es通常都是多台机器组成集群,而使用原生的httpclient请求创建的连接只能是某一台机器的ip这样一来,若是这台机器挂掉这个客户端程序就彻底不能使用了,因此风险仍是比较大的,不过也不用担忧,es官网也提供了ES Java RestClient的方式来访问es,这个库底层用的也是httpclient的组件,只不过es官网作了封装,支持多机器ip,以及对请求方法作了简化,因此想减小项目的依赖,又对支持功能要求比较健壮,咱们就可使用这个库来开发咱们的业务。框架

官网文档地址:curl

https://www.elastic.co/guide/en/elasticsearch/client/java-rest/current/index.html

maven依赖:

<dependency>
    <groupId>org.elasticsearch.client</groupId>
    <artifactId>rest</artifactId>
    <version>5.5.1</version>
</dependency>

下面来看下,如何使用ES的RestClient来操做ES:

//初始化RestClient实例
 static  RestClient restClient = RestClient.builder(
            new HttpHost("192.168.10.5", 9200, "http"),
            new HttpHost("192.168.10.6", 9200, "http"),
            new HttpHost("192.168.10.7", 9200, "http")).build()
            
     
  // (1) 执行一个基本的方法,验证es集群是否搭建成功
  
   Response response = restClient.performRequest("GET", "/", Collections.singletonMap("pretty", "true"));
        System.out.println(EntityUtils.toString(response.getEntity()));
        
  //输出结果:
  {
  "name" : "nd2",
  "cluster_name" : "search",
  "version" : {
    "number" : "2.3.4",
    "build_hash" : "e455fd0c13dceca8dbbdbb1665d068ae55dabe3f",
    "build_timestamp" : "2016-06-30T11:24:31Z",
    "build_snapshot" : false,
    "lucene_version" : "5.5.0"
  },
  "tagline" : "You Know, for Search"
}
            
// (2)验证es的某个索引是否存在

Response response = restClient.performRequest("HEAD","/product/pdt",Collections.<String, String>emptyMap());
        System.out.println(response.getStatusLine().getReasonPhrase().equals("OK"));
          
//输出结果:

true



// (3) 删除某个索引的指定条件的数据


  Map<String, String> paramMap = new HashMap<String, String>();
            paramMap.put("q", "id:"+id);
            paramMap.put("pretty", "true");
            Response response = restClient.performRequest("DELETE",  + "product/pdt/_query", paramMap);
            System.out.println(EntityUtils.toString(response.getEntity()));


//输出结果:

{
  "took" : 0,
  "timed_out" : false,
  "_indices" : {
    "_all" : {
      "found" : 1,
      "deleted" : 0,
      "missing" : 0,
      "failed" : 0
    }
  },
  "failures" : [ ]
}

总结:

ES官网提供的RestClient还支持nio实现的异步非阻塞的方式多线程多送请求,经过回调函数来处理响应的结果,固然了权限认证,超时中断,失败重试,线程数都有对应的设置选项,感兴趣的朋友可自行查阅尝试。

经过对比咱们发现官网封装的RestClient使用起来更加简单和健壮,比起来没有包装的httpclient原生的方式更加符合生产环境的标准,对于不想熟悉标准的java api的es操做方法,又想经过java来访问es的朋友们,RestClient是一个不错的选择。

相关文章
相关标签/搜索