ShardId equality and hash code inconsistency

This commit fixes an inconsistency between ShardId#equals(Object),
ShardId#hashCode, and ShardId#compareTo(ShardId). In particular,
ShardId#equals(Object) compared only the numerical shard ID and the
index name, but did not compare the index UUID; a similar situation
applies to ShardId#compareTo(ShardId). However, ShardId#hashCode
incorporated the indexUUID into its calculation. This can lead to
situations where two ShardIds compare as equal yet have different hash
codes.

Closes #16319
This commit is contained in:
Jason Tedor 2016-01-29 13:57:18 -05:00
parent 01b80b100e
commit 24a841a075
2 changed files with 9 additions and 4 deletions

View File

@ -76,7 +76,7 @@ public class ShardId implements Streamable, Comparable<ShardId> {
if (this == o) return true;
if (o == null) return false;
ShardId shardId1 = (ShardId) o;
return shardId == shardId1.shardId && index.getName().equals(shardId1.index.getName());
return shardId == shardId1.shardId && index.equals(shardId1.index);
}
@Override
@ -112,7 +112,11 @@ public class ShardId implements Streamable, Comparable<ShardId> {
@Override
public int compareTo(ShardId o) {
if (o.getId() == shardId) {
return index.getName().compareTo(o.getIndex().getName());
int compare = index.getName().compareTo(o.getIndex().getName());
if (compare != 0) {
return compare;
}
return index.getUUID().compareTo(o.getIndex().getUUID());
}
return Integer.compare(shardId, o.getId());
}

View File

@ -68,6 +68,7 @@ import org.elasticsearch.common.xcontent.XContentFactory;
import org.elasticsearch.env.Environment;
import org.elasticsearch.env.NodeEnvironment;
import org.elasticsearch.env.ShardLock;
import org.elasticsearch.index.Index;
import org.elasticsearch.index.IndexService;
import org.elasticsearch.index.IndexSettings;
import org.elasticsearch.index.NodeServicesProvider;
@ -250,7 +251,7 @@ public class IndexShardTests extends ESSingleNodeTestCase {
ShardStateMetaData shardStateMetaData = load(logger, env.availableShardPaths(shard.shardId));
assertEquals(shardStateMetaData, getShardStateMetadata(shard));
routing = TestShardRouting.newShardRouting(shard.shardId.getIndexName(), shard.shardId.id(), routing.currentNodeId(), null, routing.primary(), ShardRoutingState.INITIALIZING, shard.shardRouting.allocationId(), shard.shardRouting.version() + 1);
routing = TestShardRouting.newShardRouting(shard.shardId.getIndex(), shard.shardId.id(), routing.currentNodeId(), null, routing.primary(), ShardRoutingState.INITIALIZING, shard.shardRouting.allocationId(), shard.shardRouting.version() + 1);
shard.updateRoutingEntry(routing, true);
shard.deleteShardState();