This is an automated email from the ASF dual-hosted git repository.
rpuch pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/ignite-3.git
The following commit(s) were added to refs/heads/main by this push:
new aa9a4c82c4 IGNITE-22170 Destroy CMG Raft group storages on init
cancellation (#4287)
aa9a4c82c4 is described below
commit aa9a4c82c40199c23ef0b4caf4287ef7f4aaf85c
Author: Roman Puchkovskiy <[email protected]>
AuthorDate: Tue Aug 27 16:33:35 2024 +0400
IGNITE-22170 Destroy CMG Raft group storages on init cancellation (#4287)
---
modules/bytecode/build.gradle | 2 +
.../presto/bytecode/TestClassGenerator.java | 28 ++----
.../management/ClusterManagementGroupManager.java | 11 +-
.../apache/ignite/internal/raft/RaftManager.java | 9 ++
.../apache/ignite/internal/raft/ItLozaTest.java | 111 ++++++++++++++++-----
.../raft/ItTruncateSuffixAndRestartTest.java | 11 +-
.../internal/raft/CoreLogStorageBudgetsModule.java | 4 +-
.../java/org/apache/ignite/internal/raft/Loza.java | 19 +++-
.../ignite/internal/raft/server/RaftServer.java | 8 ++
.../internal/raft/server/impl/JraftServerImpl.java | 28 +++++-
.../internal/raft/storage/LogStorageFactory.java | 7 ++
.../storage/impl/DefaultLogStorageFactory.java | 11 ++
.../raft}/storage/impl/EntryCountBudget.java | 2 +-
.../raft/storage/impl/LocalLogStorageFactory.java | 5 +
.../raft}/storage/impl/LogStorageBudget.java | 2 +-
.../raft}/storage/impl/LogStorageException.java | 8 +-
.../jraft => internal/raft}/storage/impl/Logs.java | 25 ++---
.../raft}/storage/impl/OnHeapLogs.java | 2 +-
.../raft/storage/impl/RocksDbSharedLogStorage.java | 21 +++-
.../impl/RocksDbSharedLogStorageUtils.java} | 28 ++++--
.../raft}/storage/impl/RocksDbSpillout.java | 26 ++++-
.../raft}/storage/impl/UnlimitedBudget.java | 2 +-
.../raft}/storage/impl/VolatileLogStorage.java | 4 +-
.../storage/impl/VolatileLogStorageFactory.java | 16 ++-
.../storage/impl/VolatileRaftMetaStorage.java | 2 +-
.../raft/storage/logit/LogitLogStorageFactory.java | 13 +++
.../raft/jraft/core/LogStorageBudgetFactory.java | 4 +-
.../raft/jraft/core/LogStorageBudgetsModule.java | 2 +-
.../raft/CoreLogStorageBudgetsModuleTest.java | 11 +-
.../storage/impl/RocksDbSharedLogStorageTest.java | 25 ++++-
.../impl/SharedVsNonSharedLogStorageBenchmark.java | 23 +----
.../impl/VolatileLogStorageSpecificsTest.java | 2 +-
.../jraft/storage/impl/EntryCountBudgetTest.java | 1 +
.../jraft/storage/impl/UnlimitedBudgetTest.java | 1 +
.../impl/VolatileLogStorageBudgetingTest.java | 3 +
.../jraft/storage/impl/VolatileLogStorageTest.java | 3 +
.../storage/impl/VolatileRaftMetaStorageTest.java | 13 +--
.../jraft/storage/logit/LogitLogStorageTest.java | 23 ++++-
.../ignite/internal/replicator/ReplicaManager.java | 2 +-
39 files changed, 379 insertions(+), 139 deletions(-)
diff --git a/modules/bytecode/build.gradle b/modules/bytecode/build.gradle
index f095f31b50..f4e43932b2 100644
--- a/modules/bytecode/build.gradle
+++ b/modules/bytecode/build.gradle
@@ -22,6 +22,8 @@ apply from: "$rootDir/buildscripts/java-junit5.gradle"
description = 'ignite-bytecode'
dependencies {
+ implementation project(':ignite-core')
+
implementation libs.jetbrains.annotations
api libs.asm.core
api libs.asm.tree
diff --git
a/modules/bytecode/src/test/java/com/facebook/presto/bytecode/TestClassGenerator.java
b/modules/bytecode/src/test/java/com/facebook/presto/bytecode/TestClassGenerator.java
index fb88dd8a93..9cf07ab19d 100644
---
a/modules/bytecode/src/test/java/com/facebook/presto/bytecode/TestClassGenerator.java
+++
b/modules/bytecode/src/test/java/com/facebook/presto/bytecode/TestClassGenerator.java
@@ -16,14 +16,6 @@
*/
package com.facebook.presto.bytecode;
-import java.io.File;
-import java.io.StringWriter;
-import java.lang.reflect.Method;
-import java.nio.file.Files;
-import java.nio.file.Path;
-import java.util.List;
-import org.junit.jupiter.api.Test;
-
import static com.facebook.presto.bytecode.Access.FINAL;
import static com.facebook.presto.bytecode.Access.PUBLIC;
import static com.facebook.presto.bytecode.Access.STATIC;
@@ -33,9 +25,17 @@ import static com.facebook.presto.bytecode.Parameter.arg;
import static com.facebook.presto.bytecode.ParameterizedType.type;
import static com.facebook.presto.bytecode.expression.BytecodeExpressions.add;
import static java.nio.file.Files.createTempDirectory;
+import static org.apache.ignite.internal.util.IgniteUtils.deleteIfExists;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
+import java.io.StringWriter;
+import java.lang.reflect.Method;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.util.List;
+import org.junit.jupiter.api.Test;
+
public class TestClassGenerator {
@Test
public void testGenerator()
@@ -84,17 +84,7 @@ public class TestClassGenerator {
assertTrue(Files.isRegularFile(tempDir.resolve("test/Example.class")));
}
finally {
- deleteDirectory(tempDir.toFile());
- }
- }
-
- boolean deleteDirectory(File directoryToBeDeleted) {
- File[] allContents = directoryToBeDeleted.listFiles();
- if (allContents != null) {
- for (File file : allContents) {
- deleteDirectory(file);
- }
+ deleteIfExists(tempDir);
}
- return directoryToBeDeleted.delete();
}
}
diff --git
a/modules/cluster-management/src/main/java/org/apache/ignite/internal/cluster/management/ClusterManagementGroupManager.java
b/modules/cluster-management/src/main/java/org/apache/ignite/internal/cluster/management/ClusterManagementGroupManager.java
index 066d0c6128..cc355e6e1e 100644
---
a/modules/cluster-management/src/main/java/org/apache/ignite/internal/cluster/management/ClusterManagementGroupManager.java
+++
b/modules/cluster-management/src/main/java/org/apache/ignite/internal/cluster/management/ClusterManagementGroupManager.java
@@ -568,7 +568,7 @@ public class ClusterManagementGroupManager extends
AbstractEventProducer<Cluster
/** Delegates call to {@link #destroyCmg()} but fires the associated
events. */
private CompletableFuture<Void> destroyCmgWithEvents() {
- LOG.info("CMG cancellation procedure started");
+ LOG.info("CMG destruction procedure started");
return inBusyLockAsync(busyLock,
() ->
fireEvent(ClusterManagerGroupEvent.BEFORE_DESTROY_RAFT_GROUP,
EmptyEventParameters.INSTANCE)
.thenRunAsync(this::destroyCmg, this.scheduledExecutor)
@@ -593,6 +593,9 @@ public class ClusterManagementGroupManager extends
AbstractEventProducer<Cluster
raftManager.stopRaftNodes(CmgGroupId.INSTANCE);
+ RaftNodeId nodeId = raftNodeId(new
Peer(clusterService.nodeName()));
+ raftManager.destroyRaftNodeStorages(nodeId,
raftGroupOptionsConfigurer);
+
localStateStorage.clear();
} catch (Exception e) {
throw new IgniteInternalException("Error when cleaning the CMG
state", e);
@@ -712,7 +715,7 @@ public class ClusterManagementGroupManager extends
AbstractEventProducer<Cluster
try {
return raftManager
.startRaftGroupNodeAndWaitNodeReadyFuture(
- new RaftNodeId(CmgGroupId.INSTANCE, serverPeer),
+ raftNodeId(serverPeer),
raftConfiguration,
new CmgRaftGroupListener(clusterStateStorageMgr,
logicalTopology, validationManager,
this::onLogicalTopologyChanged),
@@ -725,6 +728,10 @@ public class ClusterManagementGroupManager extends
AbstractEventProducer<Cluster
}
}
+ private static RaftNodeId raftNodeId(Peer serverPeer) {
+ return new RaftNodeId(CmgGroupId.INSTANCE, serverPeer);
+ }
+
private void onLogicalTopologyChanged(long term) {
// We don't do it under lock to avoid deadlocks during node restart.
diff --git
a/modules/raft-api/src/main/java/org/apache/ignite/internal/raft/RaftManager.java
b/modules/raft-api/src/main/java/org/apache/ignite/internal/raft/RaftManager.java
index 5a77d61ebb..f990cc0804 100644
---
a/modules/raft-api/src/main/java/org/apache/ignite/internal/raft/RaftManager.java
+++
b/modules/raft-api/src/main/java/org/apache/ignite/internal/raft/RaftManager.java
@@ -180,4 +180,13 @@ public interface RaftManager extends IgniteComponent {
@Nullable Marshaller commandsMarshaller
) throws NodeStoppingException;
+ /**
+ * Destroys Raft group node storages (log storage, metadata storage and
snapshots storage).
+ *
+ * @param nodeId ID of the Raft node.
+ * @param raftGroupOptionsConfigurer Group options configurer.
+ * @throws NodeStoppingException If the node is already being stopped.
+ */
+ void destroyRaftNodeStorages(RaftNodeId nodeId, RaftGroupOptionsConfigurer
raftGroupOptionsConfigurer)
+ throws NodeStoppingException;
}
diff --git
a/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItLozaTest.java
b/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItLozaTest.java
index 1d9c71fe42..818c7638d1 100644
---
a/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItLozaTest.java
+++
b/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItLozaTest.java
@@ -26,6 +26,8 @@ import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.containsString;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.notNullValue;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyLong;
import static org.mockito.Mockito.doReturn;
@@ -36,6 +38,7 @@ import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import java.io.IOException;
+import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Iterator;
@@ -64,6 +67,7 @@ import
org.apache.ignite.internal.raft.service.RaftGroupListener;
import org.apache.ignite.internal.raft.service.RaftGroupService;
import org.apache.ignite.internal.raft.storage.LogStorageFactory;
import
org.apache.ignite.internal.raft.storage.impl.VolatileLogStorageFactoryCreator;
+import org.apache.ignite.internal.raft.storage.impl.VolatileRaftMetaStorage;
import org.apache.ignite.internal.raft.util.SharedLogStorageFactoryUtils;
import org.apache.ignite.internal.replicator.TestReplicationGroupId;
import org.apache.ignite.internal.testframework.IgniteAbstractTest;
@@ -74,7 +78,6 @@ import org.apache.ignite.network.NetworkAddress;
import org.apache.ignite.raft.jraft.Node;
import org.apache.ignite.raft.jraft.entity.LogEntry;
import org.apache.ignite.raft.jraft.storage.LogManager;
-import org.apache.ignite.raft.jraft.storage.impl.VolatileRaftMetaStorage;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.RepeatedTest;
@@ -236,30 +239,7 @@ public class ItLozaTest extends IgniteAbstractTest {
Peer peer = configuration.peer(nodeName);
- // Raft listener that simply drains the given iterators.
- RaftGroupListener raftGroupListener = new RaftGroupListener() {
- @Override
- public void onWrite(Iterator<CommandClosure<WriteCommand>>
iterator) {
- iterator.forEachRemaining(c -> c.result(null));
- }
-
- @Override
- public void onRead(Iterator<CommandClosure<ReadCommand>> iterator)
{
- }
-
- @Override
- public void onSnapshotSave(Path path, Consumer<Throwable> doneClo)
{
- }
-
- @Override
- public boolean onSnapshotLoad(Path path) {
- return true;
- }
-
- @Override
- public void onShutdown() {
- }
- };
+ RaftGroupListener raftGroupListener = new DrainingRaftGroupListener();
LogStorageBudgetView volatileCfg =
raftConfiguration.volatileRaft().logStorageBudget().value();
@@ -321,4 +301,85 @@ public class ItLozaTest extends IgniteAbstractTest {
assertThat(entry, is(notNullValue()));
}
+
+ @Test
+ void destroysRaftNodeStorages(@InjectConfiguration RaftConfiguration
raftConfiguration) throws Exception {
+ ComponentWorkingDir partitionsWorkDir = new
ComponentWorkingDir(workDir);
+
+ LogStorageFactory logStorageFactory =
SharedLogStorageFactoryUtils.create(
+ clusterService.nodeName(),
+ partitionsWorkDir.raftLogPath()
+ );
+ logStorageFactory = spy(logStorageFactory);
+
+ allComponents.add(logStorageFactory);
+
+ assertThat(logStorageFactory.startAsync(componentContext),
willCompleteSuccessfully());
+
+ loza = TestLozaFactory.create(clusterService, raftConfiguration, new
HybridClockImpl());
+
+ assertThat(loza.startAsync(componentContext),
willCompleteSuccessfully());
+
+ PeersAndLearners configuration =
PeersAndLearners.fromConsistentIds(Set.of(clusterService.nodeName()));
+ Peer peer = configuration.peer(clusterService.nodeName());
+
+ RaftGroupListener raftGroupListener = new DrainingRaftGroupListener();
+
+ var replicationGroupId = new TestReplicationGroupId("persistent");
+ var nodeId = new RaftNodeId(replicationGroupId, peer);
+
+ RaftGroupOptionsConfigurer configurer =
RaftGroupOptionsConfigHelper.configureProperties(
+ logStorageFactory,
+ partitionsWorkDir.metaPath()
+ );
+
+ CompletableFuture<RaftGroupService> startServiceFuture =
loza.startRaftGroupNode(
+ nodeId,
+ configuration,
+ raftGroupListener,
+ RaftGroupEventsListener.noopLsnr,
+ null,
+ configurer
+ );
+ assertThat(startServiceFuture, willCompleteSuccessfully());
+ RaftGroupService service = startServiceFuture.join();
+
+ assertThat(service.run(testWriteCommand("foo")),
willCompleteSuccessfully());
+
+ loza.stopRaftNodes(replicationGroupId);
+
+ String groupUri = nodeId.groupId().toString() + "_" +
nodeId.peer().consistentId() + "_" + nodeId.peer().idx();
+ Path groupRaftStoragesPath =
partitionsWorkDir.metaPath().resolve(groupUri);
+
+ assertTrue(Files.isDirectory(groupRaftStoragesPath));
+
+ loza.destroyRaftNodeStorages(nodeId, configurer);
+
+ verify(logStorageFactory).destroyLogStorage(groupUri);
+ assertFalse(Files.exists(groupRaftStoragesPath));
+ }
+
+ private static class DrainingRaftGroupListener implements
RaftGroupListener {
+ @Override
+ public void onWrite(Iterator<CommandClosure<WriteCommand>> iterator) {
+ iterator.forEachRemaining(c -> c.result(null));
+ }
+
+ @Override
+ public void onRead(Iterator<CommandClosure<ReadCommand>> iterator) {
+ }
+
+ @Override
+ public void onSnapshotSave(Path path, Consumer<Throwable> doneClo) {
+ }
+
+ @Override
+ public boolean onSnapshotLoad(Path path) {
+ return true;
+ }
+
+ @Override
+ public void onShutdown() {
+ }
+ }
}
diff --git
a/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItTruncateSuffixAndRestartTest.java
b/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItTruncateSuffixAndRestartTest.java
index 7d4161189b..b18d4bd7e3 100644
---
a/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItTruncateSuffixAndRestartTest.java
+++
b/modules/raft/src/integrationTest/java/org/apache/ignite/internal/raft/ItTruncateSuffixAndRestartTest.java
@@ -64,6 +64,9 @@ import org.apache.ignite.internal.raft.service.CommandClosure;
import org.apache.ignite.internal.raft.service.RaftGroupListener;
import org.apache.ignite.internal.raft.service.RaftGroupService;
import org.apache.ignite.internal.raft.storage.LogStorageFactory;
+import org.apache.ignite.internal.raft.storage.impl.OnHeapLogs;
+import org.apache.ignite.internal.raft.storage.impl.UnlimitedBudget;
+import org.apache.ignite.internal.raft.storage.impl.VolatileLogStorage;
import org.apache.ignite.internal.replicator.ReplicationGroupId;
import org.apache.ignite.internal.replicator.TestReplicationGroupId;
import org.apache.ignite.internal.testframework.BaseIgniteAbstractTest;
@@ -80,9 +83,6 @@ import org.apache.ignite.raft.jraft.entity.LogId;
import org.apache.ignite.raft.jraft.option.LogStorageOptions;
import org.apache.ignite.raft.jraft.option.RaftOptions;
import org.apache.ignite.raft.jraft.storage.LogStorage;
-import org.apache.ignite.raft.jraft.storage.impl.OnHeapLogs;
-import org.apache.ignite.raft.jraft.storage.impl.UnlimitedBudget;
-import org.apache.ignite.raft.jraft.storage.impl.VolatileLogStorage;
import org.jetbrains.annotations.Nullable;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
@@ -389,6 +389,11 @@ public class ItTruncateSuffixAndRestartTest extends
BaseIgniteAbstractTest {
return logStorage;
}
+ @Override
+ public void destroyLogStorage(String uri) {
+ // No-op.
+ }
+
@Override
public CompletableFuture<Void> startAsync(ComponentContext
componentContext) {
return nullCompletedFuture();
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModule.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModule.java
index 1862eb7835..734d99bf9a 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModule.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModule.java
@@ -22,10 +22,10 @@ import java.util.Map;
import
org.apache.ignite.internal.raft.configuration.EntryCountBudgetConfigurationSchema;
import org.apache.ignite.internal.raft.configuration.EntryCountBudgetView;
import
org.apache.ignite.internal.raft.configuration.UnlimitedBudgetConfigurationSchema;
+import org.apache.ignite.internal.raft.storage.impl.EntryCountBudget;
+import org.apache.ignite.internal.raft.storage.impl.UnlimitedBudget;
import org.apache.ignite.raft.jraft.core.LogStorageBudgetFactory;
import org.apache.ignite.raft.jraft.core.LogStorageBudgetsModule;
-import org.apache.ignite.raft.jraft.storage.impl.EntryCountBudget;
-import org.apache.ignite.raft.jraft.storage.impl.UnlimitedBudget;
/**
* Provides core budget factories.
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/Loza.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/Loza.java
index 982cdc150d..24d3a52ed8 100644
--- a/modules/raft/src/main/java/org/apache/ignite/internal/raft/Loza.java
+++ b/modules/raft/src/main/java/org/apache/ignite/internal/raft/Loza.java
@@ -199,7 +199,7 @@ public class Loza implements RaftManager {
PeersAndLearners configuration,
RaftGroupListener lsnr,
RaftGroupEventsListener eventsLsnr,
- RaftServiceFactory<T> factory,
+ @Nullable RaftServiceFactory<T> factory,
RaftGroupOptionsConfigurer groupOptionsConfigurer
) throws NodeStoppingException {
RaftGroupOptions groupOptions = RaftGroupOptions.defaults();
@@ -397,6 +397,23 @@ public class Loza implements RaftManager {
}
}
+ @Override
+ public void destroyRaftNodeStorages(RaftNodeId nodeId,
RaftGroupOptionsConfigurer raftGroupOptionsConfigurer)
+ throws NodeStoppingException {
+ if (!busyLock.enterBusy()) {
+ throw new NodeStoppingException();
+ }
+
+ try {
+ RaftGroupOptions groupOptions = RaftGroupOptions.defaults();
+ raftGroupOptionsConfigurer.configure(groupOptions);
+
+ raftServer.destroyRaftNodeStorages(nodeId, groupOptions);
+ } finally {
+ busyLock.leaveBusy();
+ }
+ }
+
private <T extends RaftGroupService> CompletableFuture<T>
startRaftGroupNodeInternal(
RaftNodeId nodeId,
PeersAndLearners configuration,
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/RaftServer.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/RaftServer.java
index 3f5b6795d6..17004e53d9 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/RaftServer.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/RaftServer.java
@@ -100,6 +100,14 @@ public interface RaftServer extends IgniteComponent {
*/
boolean stopRaftNodes(ReplicationGroupId groupId);
+ /**
+ * Destroys Raft group node storages (log storage, metadata storage and
snapshots storage).
+ *
+ * @param nodeId ID of the Raft node.
+ * @param groupOptions Options for this group.
+ */
+ void destroyRaftNodeStorages(RaftNodeId nodeId, RaftGroupOptions
groupOptions);
+
/**
* Returns local nodes running the given Raft group.
*
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/impl/JraftServerImpl.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/impl/JraftServerImpl.java
index 9532572482..ce499affeb 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/impl/JraftServerImpl.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/server/impl/JraftServerImpl.java
@@ -456,11 +456,7 @@ public class JraftServerImpl implements RaftServer {
nodeOptions.setLogUri(nodeIdStr(nodeId));
- Path dataPath = groupOptions.serverDataPath();
-
- assert dataPath != null : "Raft metadata path was not set.";
-
- Path serverDataPath = getServerDataPath(dataPath, nodeId);
+ Path serverDataPath = serverDataPathForNodeId(nodeId,
groupOptions);
if (!groupOptions.volatileStores()) {
try {
@@ -525,6 +521,14 @@ public class JraftServerImpl implements RaftServer {
}
}
+ private static Path serverDataPathForNodeId(RaftNodeId nodeId,
RaftGroupOptions groupOptions) {
+ Path dataPath = groupOptions.serverDataPath();
+
+ assert dataPath != null : "Raft metadata path was not set, nodeId is "
+ nodeId;
+
+ return getServerDataPath(dataPath, nodeId);
+ }
+
@Override
public boolean isStarted(RaftNodeId nodeId) {
return nodes.containsKey(nodeId);
@@ -559,6 +563,20 @@ public class JraftServerImpl implements RaftServer {
});
}
+ @Override
+ public void destroyRaftNodeStorages(RaftNodeId nodeId, RaftGroupOptions
groupOptions) {
+ // TODO: IGNITE-23079 - improve on what we do if it was not possible
to destroy any of the storages.
+ try {
+ String uri = nodeIdStr(nodeId);
+ groupOptions.getLogStorageFactory().destroyLogStorage(uri);
+ } finally {
+ Path serverDataPath = serverDataPathForNodeId(nodeId,
groupOptions);
+
+ // This destroys both meta storage and snapshots storage as they
are stored under serverDataPath.
+ IgniteUtils.deleteIfExists(serverDataPath);
+ }
+ }
+
/**
* Performs a {@code resetPeers} operation on raft node.
*
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/LogStorageFactory.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/LogStorageFactory.java
index 18a92846f9..ce06260e81 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/LogStorageFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/LogStorageFactory.java
@@ -33,4 +33,11 @@ public interface LogStorageFactory extends LogSyncer,
IgniteComponent {
* @return Log storage.
*/
LogStorage createLogStorage(String uri, RaftOptions raftOptions);
+
+ /**
+ * Destroys a log storage (that is, removes it from the disk).
+ *
+ * @param uri Log storage URI.
+ */
+ void destroyLogStorage(String uri);
}
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/DefaultLogStorageFactory.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/DefaultLogStorageFactory.java
index df28672b78..75e839b3ac 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/DefaultLogStorageFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/DefaultLogStorageFactory.java
@@ -19,6 +19,8 @@ package org.apache.ignite.internal.raft.storage.impl;
import static java.nio.charset.StandardCharsets.UTF_8;
import static java.util.concurrent.CompletableFuture.failedFuture;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupEndPrefix;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupStartPrefix;
import static
org.apache.ignite.internal.util.CompletableFutures.nullCompletedFuture;
import static org.rocksdb.RocksDB.DEFAULT_COLUMN_FAMILY;
@@ -212,6 +214,15 @@ public class DefaultLogStorageFactory implements
LogStorageFactory {
return new RocksDbSharedLogStorage(this, db, confHandle, dataHandle,
groupId, raftOptions, executorService);
}
+ @Override
+ public void destroyLogStorage(String uri) {
+ try {
+ RocksDbSharedLogStorage.destroyAllEntriesBetween(db, confHandle,
dataHandle, groupStartPrefix(uri), groupEndPrefix(uri));
+ } catch (RocksDBException e) {
+ throw new LogStorageException("Fail to destroy the log storage for
" + uri, e);
+ }
+ }
+
@Override
public void sync() throws RocksDBException {
if (!dbOptions.useFsync()) {
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudget.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/EntryCountBudget.java
similarity index 98%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudget.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/EntryCountBudget.java
index 34d74bad0f..65b400ec59 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudget.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/EntryCountBudget.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import java.util.List;
import org.apache.ignite.raft.jraft.entity.LogEntry;
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LocalLogStorageFactory.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LocalLogStorageFactory.java
index b9042225fc..6938fdb7a6 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LocalLogStorageFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LocalLogStorageFactory.java
@@ -45,6 +45,11 @@ public class LocalLogStorageFactory implements
LogStorageFactory {
return new LocalLogStorage(raftOptions);
}
+ @Override
+ public void destroyLogStorage(String uri) {
+ // This creates on-heap storages, nothing to destroy.
+ }
+
@Override
public void sync() {
// no-op
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/LogStorageBudget.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LogStorageBudget.java
similarity index 97%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/LogStorageBudget.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LogStorageBudget.java
index 11114a0787..060d3dab4e 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/LogStorageBudget.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LogStorageBudget.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import java.util.List;
import org.apache.ignite.raft.jraft.entity.LogEntry;
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/LogStorageException.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LogStorageException.java
similarity index 84%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/LogStorageException.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LogStorageException.java
index d01b1d5220..4c19447750 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/LogStorageException.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/LogStorageException.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import org.apache.ignite.internal.lang.IgniteInternalException;
import org.jetbrains.annotations.Nullable;
@@ -23,7 +23,11 @@ import org.jetbrains.annotations.Nullable;
/**
* Thrown if something wrong happens in the log storage.
*/
-class LogStorageException extends IgniteInternalException {
+public class LogStorageException extends IgniteInternalException {
+ public LogStorageException(String msg) {
+ super(msg);
+ }
+
public LogStorageException(String msg, @Nullable Throwable cause) {
super(msg, cause);
}
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/Logs.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/Logs.java
similarity index 65%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/Logs.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/Logs.java
index 98ff6d38d2..b80a755a24 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/Logs.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/Logs.java
@@ -14,7 +14,8 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+
+package org.apache.ignite.internal.raft.storage.impl;
import java.util.List;
import org.apache.ignite.raft.jraft.Lifecycle;
@@ -27,32 +28,32 @@ import org.apache.ignite.raft.jraft.storage.Storage;
*/
interface Logs extends Lifecycle<LogStorageOptions>, Storage {
/**
- * Get logEntry by index.
+ * Gets logEntry by index.
*/
- LogEntry getEntry(final long index);
+ LogEntry getEntry(long index);
/**
- * Append entries to log.
+ * Appends entries to log.
*/
- void appendEntry(final LogEntry entry);
+ void appendEntry(LogEntry entry);
/**
- * Append entries to log.
+ * Appends entries to log.
*/
- void appendEntries(final List<LogEntry> entries);
+ void appendEntries(List<LogEntry> entries);
/**
- * Delete logs from storage's head, [first_log_index, first_index_kept)
will be discarded.
+ * Deletes logs from storage's head, [first_log_index, first_index_kept)
will be discarded.
*/
- void truncatePrefix(final long firstIndexKept);
+ void truncatePrefix(long firstIndexKept);
/**
- * Delete uncommitted logs from storage's tail, (last_index_kept,
last_log_index] will be discarded.
+ * Deletes uncommitted logs from storage's tail, (last_index_kept,
last_log_index] will be discarded.
*/
- void truncateSuffix(final long lastIndexKept);
+ void truncateSuffix(long lastIndexKept);
/**
- * Drop all the existing logs and reset next log index to
|next_log_index|. This function is called after installing
+ * Drops all the existing logs and reset next log index to
|next_log_index|. This function is called after installing
* snapshot from leader.
*/
void reset();
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/OnHeapLogs.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/OnHeapLogs.java
similarity index 97%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/OnHeapLogs.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/OnHeapLogs.java
index 605ba3b5bd..696e369bb6 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/OnHeapLogs.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/OnHeapLogs.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import java.util.List;
import java.util.NavigableMap;
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorage.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorage.java
index 3c15dfc6a4..5d7e81a219 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorage.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorage.java
@@ -18,12 +18,13 @@
package org.apache.ignite.internal.raft.storage.impl;
import static java.util.Arrays.copyOfRange;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupEndPrefix;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupStartPrefix;
import java.io.IOException;
import java.lang.invoke.MethodHandles;
import java.lang.invoke.VarHandle;
import java.nio.ByteOrder;
-import java.nio.charset.StandardCharsets;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.Executor;
@@ -165,8 +166,8 @@ public class RocksDbSharedLogStorage implements LogStorage,
Describer {
this.confHandle = confHandle;
this.dataHandle = dataHandle;
this.executor = executor;
- this.groupStartPrefix = (groupId + (char)
0).getBytes(StandardCharsets.UTF_8);
- this.groupEndPrefix = (groupId + (char)
1).getBytes(StandardCharsets.UTF_8);
+ this.groupStartPrefix = groupStartPrefix(groupId);
+ this.groupEndPrefix = groupEndPrefix(groupId);
this.groupStartBound = new Slice(groupStartPrefix);
this.groupEndBound = new Slice(groupEndPrefix);
@@ -539,8 +540,7 @@ public class RocksDbSharedLogStorage implements LogStorage,
Describer {
try {
LogEntry entry = getEntry(nextLogIndex);
- db.deleteRange(dataHandle, groupStartPrefix, groupEndPrefix);
- db.deleteRange(confHandle, groupStartPrefix, groupEndPrefix);
+ destroyAllEntriesBetween(db, confHandle, dataHandle,
groupStartPrefix, groupEndPrefix);
onReset(nextLogIndex);
@@ -563,6 +563,17 @@ public class RocksDbSharedLogStorage implements
LogStorage, Describer {
}
}
+ static void destroyAllEntriesBetween(
+ RocksDB db,
+ ColumnFamilyHandle confHandle,
+ ColumnFamilyHandle dataHandle,
+ byte[] startPrefix,
+ byte[] endPrefix
+ ) throws RocksDBException {
+ db.deleteRange(dataHandle, startPrefix, endPrefix);
+ db.deleteRange(confHandle, startPrefix, endPrefix);
+ }
+
/** {@inheritDoc} */
@Override
public boolean truncatePrefix(long firstIndexKept) {
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageUtils.java
similarity index 59%
copy from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
copy to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageUtils.java
index dd8737d280..79b1c3ca20 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageUtils.java
@@ -15,20 +15,26 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.core;
+package org.apache.ignite.internal.raft.storage.impl;
-import org.apache.ignite.internal.raft.configuration.LogStorageBudgetView;
-import org.apache.ignite.raft.jraft.storage.impl.LogStorageBudget;
+import static java.nio.charset.StandardCharsets.UTF_8;
+
+class RocksDbSharedLogStorageUtils {
+ /**
+ * Returns start prefix for the group.
+ *
+ * @param groupId ID of the group.
+ */
+ static byte[] groupStartPrefix(String groupId) {
+ return (groupId + (char) 0).getBytes(UTF_8);
+ }
-/**
- * Factory for {@link
org.apache.ignite.raft.jraft.storage.impl.LogStorageBudget} instances.
- */
-public interface LogStorageBudgetFactory {
/**
- * Creates a new budget using the given config.
+ * Returns end prefix for the group.
*
- * @param config Budget config.
- * @return The created budget.
+ * @param groupId ID of the group.
*/
- LogStorageBudget create(LogStorageBudgetView config);
+ static byte[] groupEndPrefix(String groupId) {
+ return (groupId + (char) 1).getBytes(UTF_8);
+ }
}
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/RocksDbSpillout.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSpillout.java
similarity index 92%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/RocksDbSpillout.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSpillout.java
index 8b284028f3..9a4c22b2dc 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/RocksDbSpillout.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSpillout.java
@@ -15,13 +15,15 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
+
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupEndPrefix;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupStartPrefix;
import java.io.IOException;
import java.lang.invoke.MethodHandles;
import java.lang.invoke.VarHandle;
import java.nio.ByteOrder;
-import java.nio.charset.StandardCharsets;
import java.util.List;
import java.util.concurrent.Executor;
import java.util.concurrent.locks.Lock;
@@ -138,8 +140,8 @@ public class RocksDbSpillout implements Logs {
this.db = db;
this.columnFamily = columnFamily;
this.executor = executor;
- this.groupStartPrefix = (groupId + (char)
0).getBytes(StandardCharsets.UTF_8);
- this.groupEndPrefix = (groupId + (char)
1).getBytes(StandardCharsets.UTF_8);
+ this.groupStartPrefix = groupStartPrefix(groupId);
+ this.groupEndPrefix = groupEndPrefix(groupId);
this.groupStartBound = new Slice(groupStartPrefix);
this.groupEndBound = new Slice(groupEndPrefix);
@@ -296,7 +298,21 @@ public class RocksDbSpillout implements Logs {
}
private void deleteWholeGroupRange() throws RocksDBException {
- db.deleteRange(columnFamily, groupStartPrefix, groupEndPrefix);
+ deleteAllEntriesBetween(db, columnFamily, groupStartPrefix,
groupEndPrefix);
+ }
+
+ /**
+ * Deletes all entries starting with start prefix and not ending with end
prefix.
+ *
+ * @param db The DB.
+ * @param columnFamily The column family.
+ * @param startPrefix Start prefix.
+ * @param endPrefix End prefix.
+ * @throws RocksDBException If something goes wrong.
+ */
+ public static void deleteAllEntriesBetween(RocksDB db, ColumnFamilyHandle
columnFamily, byte[] startPrefix, byte[] endPrefix)
+ throws RocksDBException {
+ db.deleteRange(columnFamily, startPrefix, endPrefix);
}
@Override
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudget.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/UnlimitedBudget.java
similarity index 95%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudget.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/UnlimitedBudget.java
index 642b5d9198..8223d2fcd5 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudget.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/UnlimitedBudget.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import org.apache.ignite.raft.jraft.entity.LogEntry;
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorage.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorage.java
similarity index 99%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorage.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorage.java
index e52e322138..f0751549a8 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorage.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorage.java
@@ -14,7 +14,8 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+
+package org.apache.ignite.internal.raft.storage.impl;
import java.util.List;
import java.util.concurrent.locks.Lock;
@@ -57,6 +58,7 @@ public class VolatileLogStorage implements LogStorage,
Describer, VolatileStorag
private volatile boolean initialized = false;
+ /** Constructor. */
public VolatileLogStorage(LogStorageBudget inMemoryBudget, Logs
inMemoryLogs, Logs spiltOnDisk) {
this.inMemoryBudget = inMemoryBudget;
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageFactory.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageFactory.java
index fcfb614187..2765ff4caf 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageFactory.java
@@ -17,6 +17,8 @@
package org.apache.ignite.internal.raft.storage.impl;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupEndPrefix;
+import static
org.apache.ignite.internal.raft.storage.impl.RocksDbSharedLogStorageUtils.groupStartPrefix;
import static
org.apache.ignite.internal.util.CompletableFutures.nullCompletedFuture;
import java.util.HashMap;
@@ -34,12 +36,9 @@ import
org.apache.ignite.raft.jraft.core.LogStorageBudgetFactory;
import org.apache.ignite.raft.jraft.core.LogStorageBudgetsModule;
import org.apache.ignite.raft.jraft.option.RaftOptions;
import org.apache.ignite.raft.jraft.storage.LogStorage;
-import org.apache.ignite.raft.jraft.storage.impl.LogStorageBudget;
-import org.apache.ignite.raft.jraft.storage.impl.OnHeapLogs;
-import org.apache.ignite.raft.jraft.storage.impl.RocksDbSpillout;
-import org.apache.ignite.raft.jraft.storage.impl.VolatileLogStorage;
import org.rocksdb.ColumnFamilyHandle;
import org.rocksdb.RocksDB;
+import org.rocksdb.RocksDBException;
/**
* Log storage factory based on {@link VolatileLogStorage}.
@@ -118,6 +117,15 @@ public class VolatileLogStorageFactory implements
LogStorageFactory {
return new VolatileLogStorage(createLogStorageBudget(), new
OnHeapLogs(), spiltOnDisk);
}
+ @Override
+ public void destroyLogStorage(String uri) {
+ try {
+ RocksDbSpillout.deleteAllEntriesBetween(db, columnFamily,
groupStartPrefix(uri), groupEndPrefix(uri));
+ } catch (RocksDBException e) {
+ throw new LogStorageException("Fail to destroy the log storage
spillout for " + uri, e);
+ }
+ }
+
private LogStorageBudget createLogStorageBudget() {
return newBudget(logStorageBudgetConfig);
}
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorage.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileRaftMetaStorage.java
similarity index 97%
rename from
modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorage.java
rename to
modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileRaftMetaStorage.java
index dc44f3fe0a..aed8e8108d 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorage.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/impl/VolatileRaftMetaStorage.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import org.apache.ignite.raft.jraft.entity.PeerId;
import org.apache.ignite.raft.jraft.option.RaftMetaStorageOptions;
diff --git
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/logit/LogitLogStorageFactory.java
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/logit/LogitLogStorageFactory.java
index 2ca87823a9..a620868f2e 100644
---
a/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/logit/LogitLogStorageFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/internal/raft/storage/logit/LogitLogStorageFactory.java
@@ -28,8 +28,10 @@ import org.apache.ignite.internal.logger.IgniteLogger;
import org.apache.ignite.internal.logger.Loggers;
import org.apache.ignite.internal.manager.ComponentContext;
import org.apache.ignite.internal.raft.storage.LogStorageFactory;
+import org.apache.ignite.internal.raft.storage.impl.LogStorageException;
import org.apache.ignite.internal.thread.NamedThreadFactory;
import org.apache.ignite.internal.util.FeatureChecker;
+import org.apache.ignite.internal.util.IgniteUtils;
import org.apache.ignite.raft.jraft.option.RaftOptions;
import org.apache.ignite.raft.jraft.storage.LogStorage;
import org.apache.ignite.raft.jraft.storage.logit.option.StoreOptions;
@@ -99,6 +101,17 @@ public class LogitLogStorageFactory implements
LogStorageFactory {
return new LogitLogStorage(storagePath, storeOptions, raftOptions,
checkpointExecutor);
}
+ @Override
+ public void destroyLogStorage(String uri) {
+ Requires.requireTrue(StringUtils.isNotBlank(uri), "Blank log storage
uri.");
+
+ Path storagePath = resolveLogStoragePath(uri);
+
+ if (!IgniteUtils.deleteIfExists(storagePath)) {
+ throw new LogStorageException("Cannot delete directory " +
storagePath);
+ }
+ }
+
@Override
public void sync() {
// TODO: https://issues.apache.org/jira/browse/IGNITE-21955
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
b/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
index dd8737d280..6e47119a2d 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
+++
b/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetFactory.java
@@ -18,10 +18,10 @@
package org.apache.ignite.raft.jraft.core;
import org.apache.ignite.internal.raft.configuration.LogStorageBudgetView;
-import org.apache.ignite.raft.jraft.storage.impl.LogStorageBudget;
+import org.apache.ignite.internal.raft.storage.impl.LogStorageBudget;
/**
- * Factory for {@link
org.apache.ignite.raft.jraft.storage.impl.LogStorageBudget} instances.
+ * Factory for {@link LogStorageBudget} instances.
*/
public interface LogStorageBudgetFactory {
/**
diff --git
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetsModule.java
b/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetsModule.java
index 819c4af608..7800f5063e 100644
---
a/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetsModule.java
+++
b/modules/raft/src/main/java/org/apache/ignite/raft/jraft/core/LogStorageBudgetsModule.java
@@ -18,7 +18,7 @@
package org.apache.ignite.raft.jraft.core;
import java.util.Map;
-import org.apache.ignite.raft.jraft.storage.impl.LogStorageBudget;
+import org.apache.ignite.internal.raft.storage.impl.LogStorageBudget;
/**
* Used to add {@link LogStorageBudget} factories using {@link
java.util.ServiceLoader}.
diff --git
a/modules/raft/src/test/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModuleTest.java
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModuleTest.java
index 0ade6bf420..11b928ccb6 100644
---
a/modules/raft/src/test/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModuleTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/CoreLogStorageBudgetsModuleTest.java
@@ -21,16 +21,19 @@ import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.instanceOf;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.notNullValue;
+import static org.mockito.Mockito.mock;
import
org.apache.ignite.internal.raft.configuration.EntryCountBudgetConfigurationSchema;
import org.apache.ignite.internal.raft.configuration.EntryCountBudgetView;
+import org.apache.ignite.internal.raft.configuration.LogStorageBudgetView;
import
org.apache.ignite.internal.raft.configuration.UnlimitedBudgetConfigurationSchema;
+import org.apache.ignite.internal.raft.storage.impl.EntryCountBudget;
+import org.apache.ignite.internal.raft.storage.impl.UnlimitedBudget;
+import org.apache.ignite.internal.testframework.BaseIgniteAbstractTest;
import org.apache.ignite.raft.jraft.core.LogStorageBudgetFactory;
-import org.apache.ignite.raft.jraft.storage.impl.EntryCountBudget;
-import org.apache.ignite.raft.jraft.storage.impl.UnlimitedBudget;
import org.junit.jupiter.api.Test;
-class CoreLogStorageBudgetsModuleTest {
+class CoreLogStorageBudgetsModuleTest extends BaseIgniteAbstractTest {
private final CoreLogStorageBudgetsModule module = new
CoreLogStorageBudgetsModule();
@Test
@@ -39,7 +42,7 @@ class CoreLogStorageBudgetsModuleTest {
assertThat(factory, is(notNullValue()));
- assertThat(factory.create(null),
is(instanceOf(UnlimitedBudget.class)));
+ assertThat(factory.create(mock(LogStorageBudgetView.class)),
is(instanceOf(UnlimitedBudget.class)));
}
@Test
diff --git
a/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageTest.java
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageTest.java
index 5fb0f3cba7..94c6e5123a 100644
---
a/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/RocksDbSharedLogStorageTest.java
@@ -19,13 +19,17 @@ package org.apache.ignite.internal.raft.storage.impl;
import static
org.apache.ignite.internal.testframework.matchers.CompletableFutureMatcher.willCompleteSuccessfully;
import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.nullValue;
import org.apache.ignite.internal.manager.ComponentContext;
import org.apache.ignite.raft.jraft.option.RaftOptions;
import org.apache.ignite.raft.jraft.storage.LogStorage;
import org.apache.ignite.raft.jraft.storage.impl.BaseLogStorageTest;
+import org.apache.ignite.raft.jraft.test.TestUtils;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
/** Shared log storage test. */
public class RocksDbSharedLogStorageTest extends BaseLogStorageTest {
@@ -54,6 +58,25 @@ public class RocksDbSharedLogStorageTest extends
BaseLogStorageTest {
/** {@inheritDoc} */
@Override
protected LogStorage newLogStorage() {
- return logStorageProvider.createLogStorage("test", new RaftOptions());
+ return logStorageProvider.createLogStorage(uri(), new RaftOptions());
+ }
+
+ private static String uri() {
+ return "test";
+ }
+
+ @Test
+ public void destroysData() {
+ logStorage.appendEntries(TestUtils.mockEntries(15));
+ logStorage.shutdown();
+
+ logStorageProvider.destroyLogStorage(uri());
+
+ logStorage = newLogStorage();
+ logStorage.init(newLogStorageOptions());
+
+ assertThat(logStorage.getFirstLogIndex(), is(1L));
+ assertThat(logStorage.getLastLogIndex(), is(0L));
+ assertThat(logStorage.getEntry(1), is(nullValue()));
}
}
diff --git
a/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/SharedVsNonSharedLogStorageBenchmark.java
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/SharedVsNonSharedLogStorageBenchmark.java
index 7cb0eaa04d..d7a591c53d 100644
---
a/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/SharedVsNonSharedLogStorageBenchmark.java
+++
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/SharedVsNonSharedLogStorageBenchmark.java
@@ -19,9 +19,9 @@ package org.apache.ignite.internal.raft.storage.impl;
import static java.util.stream.Collectors.toList;
import static
org.apache.ignite.internal.testframework.matchers.CompletableFutureMatcher.willCompleteSuccessfully;
+import static org.apache.ignite.internal.util.IgniteUtils.deleteIfExists;
import static org.hamcrest.MatcherAssert.assertThat;
-import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
@@ -211,7 +211,7 @@ public class SharedVsNonSharedLogStorageBenchmark {
sharedStorages.forEach(Lifecycle::shutdown);
assertThat(provider.stopAsync(new ComponentContext()),
willCompleteSuccessfully());
- deleteDirectory(benchmarkPath.toFile());
+ deleteIfExists(benchmarkPath);
}
private static void testIsolated(int batchSize, int logSize, int
totalLogs, List<String> grps) throws IOException {
@@ -239,23 +239,6 @@ public class SharedVsNonSharedLogStorageBenchmark {
isolatedStorages.forEach(Lifecycle::shutdown);
- deleteDirectory(benchmarkPath.toFile());
- }
-
- private static void deleteDirectory(File directory) {
- // if the file is directory or not
- if (directory.isDirectory()) {
- File[] files = directory.listFiles();
-
- // if the directory contains any file
- if (files != null) {
- for (File file : files) {
- // recursive call if the subdirectory is non-empty
- deleteDirectory(file);
- }
- }
- }
-
- directory.delete();
+ deleteIfExists(benchmarkPath);
}
}
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageSpecificsTest.java
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageSpecificsTest.java
similarity index 99%
rename from
modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageSpecificsTest.java
rename to
modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageSpecificsTest.java
index 9ea79be049..802953e938 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageSpecificsTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/internal/raft/storage/impl/VolatileLogStorageSpecificsTest.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.ignite.raft.jraft.storage.impl;
+package org.apache.ignite.internal.raft.storage.impl;
import static org.apache.ignite.raft.jraft.test.TestUtils.mockEntry;
import static org.hamcrest.MatcherAssert.assertThat;
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudgetTest.java
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudgetTest.java
index 9c789f8c9a..4ea8244ea8 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudgetTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/EntryCountBudgetTest.java
@@ -21,6 +21,7 @@ import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import java.util.List;
+import org.apache.ignite.internal.raft.storage.impl.EntryCountBudget;
import org.apache.ignite.raft.jraft.entity.LogEntry;
import org.apache.ignite.raft.jraft.entity.LogId;
import org.junit.jupiter.api.Test;
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudgetTest.java
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudgetTest.java
index 6e079facc7..08daccbdb2 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudgetTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/UnlimitedBudgetTest.java
@@ -19,6 +19,7 @@ package org.apache.ignite.raft.jraft.storage.impl;
import static org.junit.jupiter.api.Assertions.assertTrue;
+import org.apache.ignite.internal.raft.storage.impl.UnlimitedBudget;
import org.apache.ignite.raft.jraft.entity.LogEntry;
import org.junit.jupiter.api.Test;
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageBudgetingTest.java
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageBudgetingTest.java
index 831706c587..161443f5e9 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageBudgetingTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageBudgetingTest.java
@@ -21,6 +21,9 @@ import static org.hamcrest.Matchers.is;
import java.util.ArrayList;
import java.util.List;
+import org.apache.ignite.internal.raft.storage.impl.LogStorageBudget;
+import org.apache.ignite.internal.raft.storage.impl.OnHeapLogs;
+import org.apache.ignite.internal.raft.storage.impl.VolatileLogStorage;
import org.apache.ignite.raft.jraft.conf.ConfigurationManager;
import org.apache.ignite.raft.jraft.entity.LogEntry;
import org.apache.ignite.raft.jraft.entity.LogId;
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageTest.java
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageTest.java
index 04bef1a70a..51ad12b120 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileLogStorageTest.java
@@ -16,6 +16,9 @@
*/
package org.apache.ignite.raft.jraft.storage.impl;
+import org.apache.ignite.internal.raft.storage.impl.OnHeapLogs;
+import org.apache.ignite.internal.raft.storage.impl.UnlimitedBudget;
+import org.apache.ignite.internal.raft.storage.impl.VolatileLogStorage;
import org.apache.ignite.raft.jraft.storage.LogStorage;
class VolatileLogStorageTest extends BaseLogStorageTest {
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorageTest.java
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorageTest.java
index f4e50e634b..59021d2da9 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorageTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/impl/VolatileRaftMetaStorageTest.java
@@ -17,11 +17,6 @@
package org.apache.ignite.raft.jraft.storage.impl;
-import org.apache.ignite.raft.jraft.entity.PeerId;
-import org.apache.ignite.raft.jraft.option.RaftMetaStorageOptions;
-import org.apache.ignite.raft.jraft.storage.VolatileStorage;
-import org.junit.jupiter.api.Test;
-
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.instanceOf;
import static org.hamcrest.Matchers.is;
@@ -29,6 +24,12 @@ import static org.hamcrest.Matchers.sameInstance;
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
import static org.junit.jupiter.api.Assertions.assertTrue;
+import org.apache.ignite.internal.raft.storage.impl.VolatileRaftMetaStorage;
+import org.apache.ignite.raft.jraft.entity.PeerId;
+import org.apache.ignite.raft.jraft.option.RaftMetaStorageOptions;
+import org.apache.ignite.raft.jraft.storage.VolatileStorage;
+import org.junit.jupiter.api.Test;
+
class VolatileRaftMetaStorageTest {
private final VolatileRaftMetaStorage storage = new
VolatileRaftMetaStorage();
@@ -86,4 +87,4 @@ class VolatileRaftMetaStorageTest {
void isInstanceOfVolatileStorage() {
assertThat(storage, is(instanceOf(VolatileStorage.class)));
}
-}
\ No newline at end of file
+}
diff --git
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/logit/LogitLogStorageTest.java
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/logit/LogitLogStorageTest.java
index a5d90c6f26..e890b7d4d0 100644
---
a/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/logit/LogitLogStorageTest.java
+++
b/modules/raft/src/test/java/org/apache/ignite/raft/jraft/storage/logit/LogitLogStorageTest.java
@@ -21,7 +21,11 @@ import static
org.apache.ignite.internal.testframework.matchers.CompletableFutur
import static org.apache.ignite.raft.jraft.entity.PeerId.emptyPeer;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+import java.nio.file.Files;
+import java.nio.file.Path;
import java.util.List;
import org.apache.ignite.internal.manager.ComponentContext;
import org.apache.ignite.internal.raft.storage.logit.LogitLogStorageFactory;
@@ -75,7 +79,11 @@ public class LogitLogStorageTest extends BaseLogStorageTest {
@Override
protected LogStorage newLogStorage() {
- return logStorageFactory.createLogStorage(this.path.toString(), new
RaftOptions());
+ return logStorageFactory.createLogStorage(uri(), new RaftOptions());
+ }
+
+ private String uri() {
+ return this.path.toString();
}
/************************ Test consistency between dbs
***********************************/
@@ -130,4 +138,17 @@ public class LogitLogStorageTest extends
BaseLogStorageTest {
assertEquals(i, entry.getId().getIndex());
}
}
+
+ @Test
+ public void destroysData() {
+ logStorage.appendEntries(TestUtils.mockEntries(15));
+ logStorage.shutdown();
+
+ Path storagePath = logStorageFactory.resolveLogStoragePath(uri());
+ assertTrue(Files.isDirectory(storagePath));
+
+ logStorageFactory.destroyLogStorage(uri());
+
+ assertFalse(Files.exists(storagePath));
+ }
}
diff --git
a/modules/replicator/src/main/java/org/apache/ignite/internal/replicator/ReplicaManager.java
b/modules/replicator/src/main/java/org/apache/ignite/internal/replicator/ReplicaManager.java
index 26483f17cd..e96854b17e 100644
---
a/modules/replicator/src/main/java/org/apache/ignite/internal/replicator/ReplicaManager.java
+++
b/modules/replicator/src/main/java/org/apache/ignite/internal/replicator/ReplicaManager.java
@@ -96,6 +96,7 @@ import
org.apache.ignite.internal.raft.service.RaftGroupListener;
import org.apache.ignite.internal.raft.service.RaftGroupService;
import org.apache.ignite.internal.raft.storage.SnapshotStorageFactory;
import org.apache.ignite.internal.raft.storage.impl.LogStorageFactoryCreator;
+import org.apache.ignite.internal.raft.storage.impl.VolatileRaftMetaStorage;
import
org.apache.ignite.internal.replicator.exception.ExpectedReplicationException;
import
org.apache.ignite.internal.replicator.exception.ReplicaIsAlreadyStartedException;
import
org.apache.ignite.internal.replicator.exception.ReplicaStoppingException;
@@ -116,7 +117,6 @@ import org.apache.ignite.internal.thread.NamedThreadFactory;
import org.apache.ignite.internal.util.IgniteSpinBusyLock;
import org.apache.ignite.internal.util.PendingComparableValuesTracker;
import org.apache.ignite.network.ClusterNode;
-import org.apache.ignite.raft.jraft.storage.impl.VolatileRaftMetaStorage;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.annotations.TestOnly;
import org.jetbrains.annotations.VisibleForTesting;