Skip to content

Commit 0830b7d

Browse files
ywelschDaveCTurner
andauthored
Use single directory for metadata (#50639)
Earlier PRs for #48701 introduced a separate directory for the cluster state. This is not needed though, and introduces an additional unnecessary cognitive burden to the users. Co-Authored-By: David Turner <[email protected]>
1 parent 09b95f4 commit 0830b7d

File tree

7 files changed

+33
-31
lines changed

7 files changed

+33
-31
lines changed

server/src/main/java/org/elasticsearch/env/NodeEnvironment.java

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,6 @@
5050
import org.elasticsearch.common.util.set.Sets;
5151
import org.elasticsearch.common.xcontent.NamedXContentRegistry;
5252
import org.elasticsearch.core.internal.io.IOUtils;
53-
import org.elasticsearch.gateway.PersistedClusterStateService;
5453
import org.elasticsearch.gateway.MetaDataStateFormat;
5554
import org.elasticsearch.index.Index;
5655
import org.elasticsearch.index.IndexSettings;
@@ -384,12 +383,9 @@ private static boolean upgradeLegacyNodeFolders(Logger logger, Settings settings
384383
final Set<String> folderNames = new HashSet<>();
385384
final Set<String> expectedFolderNames = new HashSet<>(Arrays.asList(
386385

387-
// node state directory, also containing MetaDataStateFormat-based global metadata
386+
// node state directory, containing MetaDataStateFormat-based node metadata as well as cluster state
388387
MetaDataStateFormat.STATE_DIR_NAME,
389388

390-
// Lucene-based metadata folder
391-
PersistedClusterStateService.METADATA_DIRECTORY_NAME,
392-
393389
// indices
394390
INDICES_FOLDER));
395391

server/src/main/java/org/elasticsearch/env/NodeRepurposeCommand.java

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,8 @@
3131
import org.elasticsearch.common.settings.Settings;
3232
import org.elasticsearch.common.util.set.Sets;
3333
import org.elasticsearch.core.internal.io.IOUtils;
34-
import org.elasticsearch.gateway.PersistedClusterStateService;
3534
import org.elasticsearch.gateway.MetaDataStateFormat;
35+
import org.elasticsearch.gateway.PersistedClusterStateService;
3636

3737
import java.io.IOException;
3838
import java.nio.file.Path;
@@ -117,8 +117,6 @@ private void processNoMasterNoDataNode(Terminal terminal, Path[] dataPaths, Envi
117117

118118
removePaths(terminal, indexPaths); // clean-up shard dirs
119119
// clean-up all metadata dirs
120-
IOUtils.rm(Stream.of(dataPaths).map(path -> path.resolve(PersistedClusterStateService.METADATA_DIRECTORY_NAME))
121-
.toArray(Path[]::new));
122120
MetaDataStateFormat.deleteMetaState(dataPaths);
123121
IOUtils.rm(Stream.of(dataPaths).map(path -> path.resolve(INDICES_FOLDER)).toArray(Path[]::new));
124122

server/src/main/java/org/elasticsearch/gateway/PersistedClusterStateService.java

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@
5454
import org.elasticsearch.common.io.stream.ReleasableBytesStreamOutput;
5555
import org.elasticsearch.common.lease.Releasable;
5656
import org.elasticsearch.common.logging.Loggers;
57+
import org.elasticsearch.common.lucene.Lucene;
5758
import org.elasticsearch.common.util.BigArrays;
5859
import org.elasticsearch.common.xcontent.LoggingDeprecationHandler;
5960
import org.elasticsearch.common.xcontent.NamedXContentRegistry;
@@ -117,7 +118,7 @@ public class PersistedClusterStateService {
117118
private static final String INDEX_UUID_FIELD_NAME = "index_uuid";
118119
private static final int COMMIT_DATA_SIZE = 4;
119120

120-
public static final String METADATA_DIRECTORY_NAME = "_metadata";
121+
public static final String METADATA_DIRECTORY_NAME = MetaDataStateFormat.STATE_DIR_NAME;
121122

122123
private final Path[] dataPaths;
123124
private final String nodeId;
@@ -177,6 +178,16 @@ public Writer createWriter() throws IOException {
177178
return new Writer(metaDataIndexWriters, nodeId, bigArrays);
178179
}
179180

181+
/**
182+
* Remove all persisted cluster states from the given data paths, for use in tests. Should only be called when there is no open
183+
* {@link Writer} on these paths.
184+
*/
185+
public static void deleteAll(Path[] dataPaths) throws IOException {
186+
for (Path dataPath : dataPaths) {
187+
Lucene.cleanLuceneIndex(new SimpleFSDirectory(dataPath.resolve(METADATA_DIRECTORY_NAME)));
188+
}
189+
}
190+
180191
// exposed for tests
181192
Directory createDirectory(Path path) throws IOException {
182193
// it is possible to disable the use of MMapDirectory for indices, and it may be surprising to users that have done so if we still

server/src/test/java/org/elasticsearch/cluster/coordination/CoordinatorTests.java

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -991,17 +991,18 @@ public void testCannotJoinClusterWithDifferentUUID() throws IllegalAccessExcepti
991991
cluster1.runRandomly();
992992
cluster1.stabilise();
993993

994-
final ClusterNode newNode;
994+
final ClusterNode nodeInOtherCluster;
995995
try (Cluster cluster2 = new Cluster(3)) {
996996
cluster2.runRandomly();
997997
cluster2.stabilise();
998998

999-
final ClusterNode nodeInOtherCluster = randomFrom(cluster2.clusterNodes);
1000-
newNode = cluster1.new ClusterNode(nextNodeIndex.getAndIncrement(),
1001-
nodeInOtherCluster.getLocalNode(), n -> cluster1.new MockPersistedState(n, nodeInOtherCluster.persistedState,
1002-
Function.identity(), Function.identity()), nodeInOtherCluster.nodeSettings);
999+
nodeInOtherCluster = randomFrom(cluster2.clusterNodes);
10031000
}
10041001

1002+
final ClusterNode newNode = cluster1.new ClusterNode(nextNodeIndex.getAndIncrement(),
1003+
nodeInOtherCluster.getLocalNode(), n -> cluster1.new MockPersistedState(n, nodeInOtherCluster.persistedState,
1004+
Function.identity(), Function.identity()), nodeInOtherCluster.nodeSettings);
1005+
10051006
cluster1.clusterNodes.add(newNode);
10061007

10071008
MockLogAppender mockAppender = new MockLogAppender();

server/src/test/java/org/elasticsearch/cluster/coordination/UnsafeBootstrapAndDetachCommandIT.java

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,6 @@
2525
import org.elasticsearch.cluster.ClusterState;
2626
import org.elasticsearch.cluster.metadata.MetaData;
2727
import org.elasticsearch.common.settings.Settings;
28-
import org.elasticsearch.core.internal.io.IOUtils;
2928
import org.elasticsearch.env.Environment;
3029
import org.elasticsearch.env.NodeEnvironment;
3130
import org.elasticsearch.env.NodeMetaData;
@@ -36,11 +35,9 @@
3635
import org.elasticsearch.test.InternalTestCluster;
3736

3837
import java.io.IOException;
39-
import java.nio.file.Path;
4038
import java.util.ArrayList;
4139
import java.util.List;
4240
import java.util.Locale;
43-
import java.util.stream.Stream;
4441

4542
import static org.elasticsearch.action.support.WriteRequest.RefreshPolicy.IMMEDIATE;
4643
import static org.elasticsearch.index.query.QueryBuilders.matchAllQuery;
@@ -175,9 +172,7 @@ public void testBootstrapNoClusterState() throws IOException {
175172
internalCluster().stopRandomDataNode();
176173
Environment environment = TestEnvironment.newEnvironment(
177174
Settings.builder().put(internalCluster().getDefaultSettings()).put(dataPathSettings).build());
178-
IOUtils.rm(Stream.of(nodeEnvironment.nodeDataPaths())
179-
.map(path -> path.resolve(PersistedClusterStateService.METADATA_DIRECTORY_NAME))
180-
.toArray(Path[]::new));
175+
PersistedClusterStateService.deleteAll(nodeEnvironment.nodeDataPaths());
181176

182177
expectThrows(() -> unsafeBootstrap(environment), ElasticsearchNodeCommand.CS_MISSING_MSG);
183178
}
@@ -191,9 +186,7 @@ public void testDetachNoClusterState() throws IOException {
191186
internalCluster().stopRandomDataNode();
192187
Environment environment = TestEnvironment.newEnvironment(
193188
Settings.builder().put(internalCluster().getDefaultSettings()).put(dataPathSettings).build());
194-
IOUtils.rm(Stream.of(nodeEnvironment.nodeDataPaths())
195-
.map(path -> path.resolve(PersistedClusterStateService.METADATA_DIRECTORY_NAME))
196-
.toArray(Path[]::new));
189+
PersistedClusterStateService.deleteAll(nodeEnvironment.nodeDataPaths());
197190

198191
expectThrows(() -> detachCluster(environment), ElasticsearchNodeCommand.CS_MISSING_MSG);
199192
}

server/src/test/java/org/elasticsearch/gateway/PersistedClusterStateServiceTests.java

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@
4040
import org.elasticsearch.core.internal.io.IOUtils;
4141
import org.elasticsearch.env.Environment;
4242
import org.elasticsearch.env.NodeEnvironment;
43+
import org.elasticsearch.env.NodeMetaData;
4344
import org.elasticsearch.gateway.PersistedClusterStateService.Writer;
4445
import org.elasticsearch.index.Index;
4546
import org.elasticsearch.indices.breaker.NoneCircuitBreakerService;
@@ -201,9 +202,7 @@ public void testFailsOnMismatchedNodeIds() throws IOException {
201202
}
202203
}
203204

204-
for (Path dataPath : dataPaths2) {
205-
IOUtils.rm(dataPath.resolve(MetaDataStateFormat.STATE_DIR_NAME));
206-
}
205+
NodeMetaData.FORMAT.cleanupOldFiles(Long.MAX_VALUE, dataPaths2);
207206

208207
final Path[] combinedPaths = Stream.concat(Arrays.stream(dataPaths1), Arrays.stream(dataPaths2)).toArray(Path[]::new);
209208

test/framework/src/main/java/org/elasticsearch/cluster/coordination/AbstractCoordinatorTestCase.java

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -56,13 +56,15 @@
5656
import org.elasticsearch.common.settings.Settings;
5757
import org.elasticsearch.common.transport.TransportAddress;
5858
import org.elasticsearch.common.unit.TimeValue;
59+
import org.elasticsearch.common.util.BigArrays;
5960
import org.elasticsearch.common.util.concurrent.PrioritizedEsThreadPoolExecutor;
6061
import org.elasticsearch.discovery.DiscoveryModule;
6162
import org.elasticsearch.discovery.SeedHostsProvider;
6263
import org.elasticsearch.env.NodeEnvironment;
6364
import org.elasticsearch.gateway.ClusterStateUpdaters;
6465
import org.elasticsearch.gateway.GatewayService;
6566
import org.elasticsearch.gateway.MockGatewayMetaState;
67+
import org.elasticsearch.gateway.PersistedClusterStateService;
6668
import org.elasticsearch.node.Node;
6769
import org.elasticsearch.test.ESTestCase;
6870
import org.elasticsearch.test.disruption.DisruptableMockTransport;
@@ -740,12 +742,14 @@ class MockPersistedState implements CoordinationState.PersistedState {
740742
if (oldState.nodeEnvironment != null) {
741743
nodeEnvironment = oldState.nodeEnvironment;
742744
final MetaData updatedMetaData = adaptGlobalMetaData.apply(oldState.getLastAcceptedState().metaData());
743-
if (updatedMetaData != oldState.getLastAcceptedState().metaData()) {
744-
throw new AssertionError("TODO adapting persistent metadata is not supported yet");
745-
}
746745
final long updatedTerm = adaptCurrentTerm.apply(oldState.getCurrentTerm());
747-
if (updatedTerm != oldState.getCurrentTerm()) {
748-
throw new AssertionError("TODO adapting persistent current term is not supported yet");
746+
if (updatedMetaData != oldState.getLastAcceptedState().metaData() || updatedTerm != oldState.getCurrentTerm()) {
747+
try (PersistedClusterStateService.Writer writer =
748+
new PersistedClusterStateService(nodeEnvironment, xContentRegistry(), BigArrays.NON_RECYCLING_INSTANCE)
749+
.createWriter()) {
750+
writer.writeFullStateAndCommit(updatedTerm,
751+
ClusterState.builder(oldState.getLastAcceptedState()).metaData(updatedMetaData).build());
752+
}
749753
}
750754
final MockGatewayMetaState gatewayMetaState = new MockGatewayMetaState(newLocalNode);
751755
gatewayMetaState.start(Settings.EMPTY, nodeEnvironment, xContentRegistry());

0 commit comments

Comments
 (0)