ElasticSearch - Sniff ! Sniff!
Note: Below is a brief discussion of the issues i have encountered using Elasticsearch's Client behind a VIP.
As I had written previously, I had to setup an Elasticsearch cluster. In order to take advantage of balancing the load between the nodes of the cluster. I used a DNS pointed to VIP that does a round-robin load balancing among the nodes. The reason i choose this is because I can add servers to the VIP without changing the Transport Addresses in the Elasticsearch Client java code which uses a TransportClient. Without the VIP I need a coding change and deploy to add the new Transport Address.
The cluster would not be really useful if I cannot take away nodes and add nodes to the cluster as I wish without any coding change.
The drawback in hiding the cluster behind the VIP is that you don't know which node the java code client is going to get in order to process a search request.
This is causing an issue in the client code. Since I only have one Transport Address defined in my TransportClient it is throwing a NoNodeAvailableException when the TransportClient hits the only TransportAddress i have added to it and this server's request queue is filled up.
The TransportClient is not forwarding or using the other nodes to process the request. The reason for this is that if there is only one TransportAddress in the TransportClient a second attempt to reconnect or retry the request will throw the exception (NoNodeAvailableException). In order for the TransportClient forward the request to any node of the cluster you can do one of the following things:
1. Add all the Transport addresses for each of the nodes to the TransportClient.
- TransportClient uses a SimpleNodeSampler that basically gets the list of TransportAddress added to the TransportClient and try to forward the request to any of the transport Addresses. (BUT this does not work for my setup because it defeats the purpose of my cluster hiding behind a VIP - enter the sniff)
2. Set the"client.transport.sniff" property in the TransportClient Settings equal to true
Sample Settings:
Settings elasticSettings = ImmutableSettings.settingsBuilder()
.put("cluster.name", this.clusterName)
.put("client.transport.sniff", true)
.put("client.transport.ping_timeout", "30s")
.put("client.transport.nodes_sampler_interval", "10s")
.build();
When this property is set to true, the TransportClient will try and sniff out the rest of the nodes' addresses so that it can be used to forward request to without explicitly adding the addresses to a TransportClient.
Tip: As you can see above I have set the setting of the ping timeout and nodes sample interval. This is to make sure that the TransportClient is going to be able to forward request to the nodes properly.
As I had written previously, I had to setup an Elasticsearch cluster. In order to take advantage of balancing the load between the nodes of the cluster. I used a DNS pointed to VIP that does a round-robin load balancing among the nodes. The reason i choose this is because I can add servers to the VIP without changing the Transport Addresses in the Elasticsearch Client java code which uses a TransportClient. Without the VIP I need a coding change and deploy to add the new Transport Address.
The cluster would not be really useful if I cannot take away nodes and add nodes to the cluster as I wish without any coding change.
The drawback in hiding the cluster behind the VIP is that you don't know which node the java code client is going to get in order to process a search request.
This is causing an issue in the client code. Since I only have one Transport Address defined in my TransportClient it is throwing a NoNodeAvailableException when the TransportClient hits the only TransportAddress i have added to it and this server's request queue is filled up.
The TransportClient is not forwarding or using the other nodes to process the request. The reason for this is that if there is only one TransportAddress in the TransportClient a second attempt to reconnect or retry the request will throw the exception (NoNodeAvailableException). In order for the TransportClient forward the request to any node of the cluster you can do one of the following things:
1. Add all the Transport addresses for each of the nodes to the TransportClient.
- TransportClient uses a SimpleNodeSampler that basically gets the list of TransportAddress added to the TransportClient and try to forward the request to any of the transport Addresses. (BUT this does not work for my setup because it defeats the purpose of my cluster hiding behind a VIP - enter the sniff)
2. Set the"client.transport.sniff" property in the TransportClient Settings equal to true
Sample Settings:
Settings elasticSettings = ImmutableSettings.settingsBuilder()
.put("cluster.name", this.clusterName)
.put("client.transport.sniff", true)
.put("client.transport.ping_timeout", "30s")
.put("client.transport.nodes_sampler_interval", "10s")
.build();
When this property is set to true, the TransportClient will try and sniff out the rest of the nodes' addresses so that it can be used to forward request to without explicitly adding the addresses to a TransportClient.
Tip: As you can see above I have set the setting of the ping timeout and nodes sample interval. This is to make sure that the TransportClient is going to be able to forward request to the nodes properly.
Comments