When checking if an index tombstone can be applied, use both the index
name and uuid because the cluster state may contain an active index of the same name (but different uuid). Closes #18058 Closes #18054
This commit is contained in:
parent
7aca1389e2
commit
a31b94e237
|
@ -681,8 +681,8 @@ public class IndicesService extends AbstractLifecycleComponent<IndicesService> i
|
||||||
*/
|
*/
|
||||||
@Nullable
|
@Nullable
|
||||||
public IndexMetaData verifyIndexIsDeleted(final Index index, final ClusterState clusterState) {
|
public IndexMetaData verifyIndexIsDeleted(final Index index, final ClusterState clusterState) {
|
||||||
// this method should only be called when we know the index is not part of the cluster state
|
// this method should only be called when we know the index (name + uuid) is not part of the cluster state
|
||||||
if (clusterState.metaData().hasIndex(index.getName())) {
|
if (clusterState.metaData().index(index) != null) {
|
||||||
throw new IllegalStateException("Cannot delete index [" + index + "], it is still part of the cluster state.");
|
throw new IllegalStateException("Cannot delete index [" + index + "], it is still part of the cluster state.");
|
||||||
}
|
}
|
||||||
if (nodeEnv.hasNodeFile() && FileSystemUtils.exists(nodeEnv.indexPaths(index))) {
|
if (nodeEnv.hasNodeFile() && FileSystemUtils.exists(nodeEnv.indexPaths(index))) {
|
||||||
|
|
|
@ -21,8 +21,10 @@ package org.elasticsearch.indices;
|
||||||
import org.apache.lucene.store.LockObtainFailedException;
|
import org.apache.lucene.store.LockObtainFailedException;
|
||||||
import org.elasticsearch.Version;
|
import org.elasticsearch.Version;
|
||||||
import org.elasticsearch.action.admin.indices.alias.IndicesAliasesRequest;
|
import org.elasticsearch.action.admin.indices.alias.IndicesAliasesRequest;
|
||||||
|
import org.elasticsearch.cluster.ClusterName;
|
||||||
import org.elasticsearch.cluster.ClusterState;
|
import org.elasticsearch.cluster.ClusterState;
|
||||||
import org.elasticsearch.cluster.metadata.AliasAction;
|
import org.elasticsearch.cluster.metadata.AliasAction;
|
||||||
|
import org.elasticsearch.cluster.metadata.IndexGraveyard;
|
||||||
import org.elasticsearch.cluster.metadata.IndexMetaData;
|
import org.elasticsearch.cluster.metadata.IndexMetaData;
|
||||||
import org.elasticsearch.cluster.metadata.MetaData;
|
import org.elasticsearch.cluster.metadata.MetaData;
|
||||||
import org.elasticsearch.cluster.service.ClusterService;
|
import org.elasticsearch.cluster.service.ClusterService;
|
||||||
|
@ -283,6 +285,36 @@ public class IndicesServiceTests extends ESSingleNodeTestCase {
|
||||||
indicesService.deleteIndex(test.index(), "finished with test");
|
indicesService.deleteIndex(test.index(), "finished with test");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This test checks an edge case where, if a node had an index (lets call it A with UUID 1), then
|
||||||
|
* deleted it (so a tombstone entry for A will exist in the cluster state), then created
|
||||||
|
* a new index A with UUID 2, then shutdown, when the node comes back online, it will look at the
|
||||||
|
* tombstones for deletions, and it should proceed with trying to delete A with UUID 1 and not
|
||||||
|
* throw any errors that the index still exists in the cluster state. This is a case of ensuring
|
||||||
|
* that tombstones that have the same name as current valid indices don't cause confusion by
|
||||||
|
* trying to delete an index that exists.
|
||||||
|
* See https://github.com/elastic/elasticsearch/issues/18054
|
||||||
|
*/
|
||||||
|
public void testIndexAndTombstoneWithSameNameOnStartup() throws Exception {
|
||||||
|
final String indexName = "test";
|
||||||
|
final Index index = new Index(indexName, UUIDs.randomBase64UUID());
|
||||||
|
final IndicesService indicesService = getIndicesService();
|
||||||
|
final Settings idxSettings = Settings.builder().put(IndexMetaData.SETTING_VERSION_CREATED, Version.CURRENT)
|
||||||
|
.put(IndexMetaData.SETTING_INDEX_UUID, index.getUUID())
|
||||||
|
.build();
|
||||||
|
final IndexMetaData indexMetaData = new IndexMetaData.Builder(index.getName())
|
||||||
|
.settings(idxSettings)
|
||||||
|
.numberOfShards(1)
|
||||||
|
.numberOfReplicas(0)
|
||||||
|
.build();
|
||||||
|
final Index tombstonedIndex = new Index(indexName, UUIDs.randomBase64UUID());
|
||||||
|
final IndexGraveyard graveyard = IndexGraveyard.builder().addTombstone(tombstonedIndex).build();
|
||||||
|
final MetaData metaData = MetaData.builder().put(indexMetaData, true).indexGraveyard(graveyard).build();
|
||||||
|
final ClusterState clusterState = new ClusterState.Builder(new ClusterName("testCluster")).metaData(metaData).build();
|
||||||
|
// if all goes well, this won't throw an exception, otherwise, it will throw an IllegalStateException
|
||||||
|
indicesService.verifyIndexIsDeleted(tombstonedIndex, clusterState);
|
||||||
|
}
|
||||||
|
|
||||||
private static class DanglingListener implements LocalAllocateDangledIndices.Listener {
|
private static class DanglingListener implements LocalAllocateDangledIndices.Listener {
|
||||||
final CountDownLatch latch = new CountDownLatch(1);
|
final CountDownLatch latch = new CountDownLatch(1);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue