承接上文,使用Java客户端操做elasticsearch,本文主要介绍 常见的配置 和Sniffer(集群探测) 的使用。html
前面已介绍过,RestClientBuilder支持同时提供一个RequestConfigCallback和一个HttpClientConfigCallback,你能够定制 the Apache Async Http Client 公开的配置。这两个回调函数能够修改某些特定的行为,而不会覆盖RestClient初始化的全部其余默认配置。 本节介绍一些须要为客户端进行额外配置的常见场景。java
啥都不说了,直接上代码。该例子演示了链接超时(默认为1秒)和套接字超时(默认为30秒)。 也相应地调整最大重试超时时间(默认为30秒)。apache
RestClientBuilder builder = RestClient.builder(new HttpHost("localhost", 9200)) .setRequestConfigCallback(new RestClientBuilder.RequestConfigCallback() { //该方法接收一个RequestConfig.Builder对象,对该对象进行修改后而后返回。 @Override public RequestConfig.Builder customizeRequestConfig(RequestConfig.Builder requestConfigBuilder) { return requestConfigBuilder.setConnectTimeout(5000) //链接超时(默认为1秒) .setSocketTimeout(60000);//套接字超时(默认为30秒) } }) .setMaxRetryTimeoutMillis(60000);//调整最大重试超时时间(默认为30秒)
The Apache Http Async Client默认启动一个dispatcher线程和供链接管理器使用的多个worker线程,与本地检测到的处理器数量同样多(取决于Runtime.getRuntime().availableProcessors()的返回值)。 修改线程数能够以下操做:json
RestClientBuilder builder = RestClient.builder(new HttpHost("localhost", 9200)) .setHttpClientConfigCallback(new RestClientBuilder.HttpClientConfigCallback() { @Override public HttpAsyncClientBuilder customizeHttpClient(HttpAsyncClientBuilder httpClientBuilder) { return httpClientBuilder.setDefaultIOReactorConfig( IOReactorConfig.custom().setIoThreadCount(1).build()); } });
一样直接上代码api
final CredentialsProvider credentialsProvider = new BasicCredentialsProvider(); credentialsProvider.setCredentials(AuthScope.ANY, new UsernamePasswordCredentials("user", "password")); RestClientBuilder builder = RestClient.builder(new HttpHost("localhost", 9200)) .setHttpClientConfigCallback(new RestClientBuilder.HttpClientConfigCallback() { // 该方法接收HttpAsyncClientBuilder的实例做为参数,对其修改后进行返回 @Override public HttpAsyncClientBuilder customizeHttpClient(HttpAsyncClientBuilder httpClientBuilder) { return httpClientBuilder.setDefaultCredentialsProvider(credentialsProvider);//提供一个默认凭据 } });
抢占式认证能够被禁用,这意味着每一个请求都将被发送,不用去看受权请求头,在收到HTTP 401响应后,会再次发送相同的请求,此次会带上基本的身份认证头,若是你想这样作,那么你能够经过HttpAsyncClientBuilder来禁用它:缓存
final CredentialsProvider credentialsProvider = new BasicCredentialsProvider(); credentialsProvider.setCredentials(AuthScope.ANY, new UsernamePasswordCredentials("user", "password")); RestClientBuilder builder = RestClient.builder(new HttpHost("localhost", 9200)) .setHttpClientConfigCallback(new RestClientBuilder.HttpClientConfigCallback() { @Override public HttpAsyncClientBuilder customizeHttpClient(HttpAsyncClientBuilder httpClientBuilder) { httpClientBuilder.disableAuthCaching(); //禁用抢占式身份验证 return httpClientBuilder.setDefaultCredentialsProvider(credentialsProvider); } });
加密通讯也能够经过HttpClientConfigCallback进行配置。 参数HttpAsyncClientBuilder公开了配置加密通讯的多种方法:安全
setSSLContext,setSSLSessionStrategy和setConnectionManager,重要性依次增长。 如下是一个例子: KeyStore truststore = KeyStore.getInstance("jks"); try (InputStream is = Files.newInputStream(keyStorePath)) { truststore.load(is, keyStorePass.toCharArray()); } SSLContextBuilder sslBuilder = SSLContexts.custom().loadTrustMaterial(truststore, null); final SSLContext sslContext = sslBuilder.build(); RestClientBuilder builder = RestClient.builder(new HttpHost("localhost", 9200, "https")) .setHttpClientConfigCallback(new RestClientBuilder.HttpClientConfigCallback() { @Override public HttpAsyncClientBuilder customizeHttpClient(HttpAsyncClientBuilder httpClientBuilder) { return httpClientBuilder.setSSLContext(sslContext); } });
若是未提供明确的配置,则将使用系统默认配置。服务器
若是对其余配置须要修改,能够参考Apache HttpAsyncClient文档:https://hc.apache.org/httpcomponents-asyncclient-4.1.x/ oracle
若是您的应用程序在安全管理器下运行,可能会采用JVM默认缓存策略:async
若是客户端链接到的主机的地址随时间变化,那么可能你想修改默认的JVM行为。这些能够经过添加 networkaddress.cache.ttl=<timeout> 和 networkaddress.cache.negative.ttl=<timeout> 到您的Java安全策略进行修改。
从运行的Elasticsearch集群中自动发现节点,并将其设置到现有的RestClient实例。 默认状况下,它将使用Nodes Info api来检索属于集群的节点,并使用jackson解析响应的json数据。看完以后仍是不清除说的个啥?那就仔细说说吧。以前咱们都是像下面这样建立客户端实例的。
RestClient restClient = RestClient.builder( new HttpHost("localhost", 9200, "http"), new HttpHost("localhost", 9201, "http")).build();
假设一个集群有100个节点,若是手动 new HttpHost("localhost", 9200, "http") 这样建立100个HttpHost也能够,可是可能会写到手软,出错几率极大。因此就出现了sniffer,它来帮你作这件事。
the REST client sniffer 兼容Elasticsearch 2.x及以上版本。能够在这里找到它的javadoc。
The REST client sniffer 与Elasticsearch的发布周期相同。 发布的初版为5.0.0-alpha4。一样,你也能够自由替换成你想要的版本。 它和通信的Elasticsearch版本之间没有关联。sniffer 支持从Elasticsearch 2.x及其之后的版本获取节点列表。
Maven配置
如下是使用maven做为依赖管理器。 将如下内容添加到您的pom.xml文件中:
<dependency> <groupId>org.elasticsearch.client</groupId> <artifactId>elasticsearch-rest-client-sniffer</artifactId> <version>6.2.3</version> </dependency>
如下是使用gradle做为依赖管理器。 将如下内容添加到您的build.gradle文件中:
dependencies {
compile 'org.elasticsearch.client:elasticsearch-rest-client-sniffer:6.2.3'
}
RestClient实例建立后,就能够将一个Sniffer关联到它。Sniffer使用RestClient按期(默认每5分钟)从集群中获取当前全部节点的列表,并经过调用RestClient的setHosts方法来更新。
RestClient restClient = RestClient.builder( new HttpHost("localhost", 9200, "http")) .build(); Sniffer sniffer = Sniffer.builder(restClient).build();
关闭Sniffer是很是重要的,这样它的后台线程才能正常关闭并释放全部资源。 Sniffer对象的生命周期应与RestClient相同,并在客户端以前关闭:
sniffer.close();
restClient.close();
Sniffer默认每5分钟更新一次节点。 该时间间隔也能够自定义(以毫秒为单位),以下所示:
RestClient restClient = RestClient.builder( new HttpHost("localhost", 9200, "http")) .build(); Sniffer sniffer = Sniffer.builder(restClient) .setSniffIntervalMillis(60000).build();
也能够在失败时启用嗅探,这意味着在每次失败后,节点列表将被直接更新。 此种方式须要首先建立SniffOnFailureListener,并在建立RestClient时提供。 一样,一旦Sniffer被建立,它须要与同一个SniffOnFailureListener实例相关联,SniffOnFailureListener实例将在每次失败时通知,而且会使用该Sniffer再执行一轮嗅探。
Elasticsearch Nodes Info api在链接到节点时不会返回使用的协议,而只会返回它们的host:port键对,所以默认状况下使用http。 若是想使用https,则必须手动建立ElasticsearchHostsSniffer实例,可按以下方式:
RestClient restClient = RestClient.builder( new HttpHost("localhost", 9200, "http")) .build(); HostsSniffer hostsSniffer = new ElasticsearchHostsSniffer( restClient, ElasticsearchHostsSniffer.DEFAULT_SNIFF_REQUEST_TIMEOUT, ElasticsearchHostsSniffer.Scheme.HTTPS); Sniffer sniffer = Sniffer.builder(restClient) .setHostsSniffer(hostsSniffer).build();
一样也能够自定义sniffRequestTimeout,默认为1秒。 在调用the Nodes Info api时timeout参数使用querystring方式传递,以便当服务器端的超时时,仍然会返回有效的响应,尽管它可能只包含群集一部分的节点 。
RestClient restClient = RestClient.builder( new HttpHost("localhost", 9200, "http")) .build(); HostsSniffer hostsSniffer = new ElasticsearchHostsSniffer( restClient, TimeUnit.SECONDS.toMillis(5), ElasticsearchHostsSniffer.Scheme.HTTP); Sniffer sniffer = Sniffer.builder(restClient) .setHostsSniffer(hostsSniffer).build();
此外,咱们可能须要从外部源获取主机,而不是从Elasticsearch获取主机。则能够自定义实现HostsSniffer。
RestClient restClient = RestClient.builder( new HttpHost("localhost", 9200, "http")) .build(); HostsSniffer hostsSniffer = new HostsSniffer() { @Override public List<HttpHost> sniffHosts() throws IOException { return null;//从外部获取主机 } }; Sniffer sniffer = Sniffer.builder(restClient) .setHostsSniffer(hostsSniffer).build();
官方文档:https://www.elastic.co/guide/en/elasticsearch/client/java-rest/current/_common_configuration.html