Preference only_node with unknown nodeId returns useful exception

When the search preference is set to only node, but this node is not a
data (or does not exist), we return a search exception, which indicates,
that this is actually a server problem.

However specifying a non-existing node id is a client problem
and should return a more useful error message than
{"error":"SearchPhaseExecutionException[Failed to execute phase [query_fetch], all shards failed]","status":503}
This commit is contained in:
Alexander Reelsen 2013-12-10 16:09:45 +01:00
parent 7d3b78c293
commit c4f3da2b9d
2 changed files with 18 additions and 1 deletions

View File

@ -219,7 +219,9 @@ public class PlainOperationRouting extends AbstractComponent implements Operatio
return indexShard.onlyNodeActiveInitializingShardsIt(localNodeId); return indexShard.onlyNodeActiveInitializingShardsIt(localNodeId);
} }
if (preference.startsWith("_only_node:")) { if (preference.startsWith("_only_node:")) {
return indexShard.onlyNodeActiveInitializingShardsIt(preference.substring("_only_node:".length())); String nodeId = preference.substring("_only_node:".length());
ensureNodeIdExists(nodes, nodeId);
return indexShard.onlyNodeActiveInitializingShardsIt(nodeId);
} }
} }
// if not, then use it as the index // if not, then use it as the index
@ -284,4 +286,10 @@ public class PlainOperationRouting extends AbstractComponent implements Operatio
} }
return hashFunction.hash(type, id); return hashFunction.hash(type, id);
} }
private void ensureNodeIdExists(DiscoveryNodes nodes, String nodeId) {
if (!nodes.dataNodes().keys().contains(nodeId)) {
throw new ElasticSearchIllegalArgumentException("No data node with id[" + nodeId + "] found");
}
}
} }

View File

@ -19,6 +19,7 @@
package org.elasticsearch.search.preference; package org.elasticsearch.search.preference;
import org.elasticsearch.ElasticSearchIllegalArgumentException;
import org.elasticsearch.action.admin.cluster.health.ClusterHealthStatus; import org.elasticsearch.action.admin.cluster.health.ClusterHealthStatus;
import org.elasticsearch.action.search.SearchResponse; import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.action.search.SearchType; import org.elasticsearch.action.search.SearchType;
@ -96,4 +97,12 @@ public class SearchPreferenceTests extends ElasticsearchIntegrationTest {
searchResponse = client().prepareSearch().setQuery(matchAllQuery()).setPreference("1234").execute().actionGet(); searchResponse = client().prepareSearch().setQuery(matchAllQuery()).setPreference("1234").execute().actionGet();
assertThat(searchResponse.getHits().totalHits(), equalTo(1l)); assertThat(searchResponse.getHits().totalHits(), equalTo(1l));
} }
@Test (expected = ElasticSearchIllegalArgumentException.class)
public void testThatSpecifyingNonExistingNodesReturnsUsefulError() throws Exception {
createIndex("test");
ensureGreen();
client().prepareSearch().setQuery(matchAllQuery()).setPreference("_only_node:DOES-NOT-EXIST").execute().actionGet();
}
} }