mirror of
https://github.com/scm-manager/scm-manager.git
synced 2025-11-14 17:26:22 +01:00
Cleanup
- Mark PathBasedRepositoryLocationResolver as singleton so that other users will get the same instance and will not overwrite the paths set by migration. - Set path kept by InlineMigrationStrategy in location resolver to store the path. - Add logging - Add type of repository to migration web page
This commit is contained in:
@@ -13,8 +13,9 @@ public abstract class RepositoryLocationResolver {
|
||||
return create(type);
|
||||
}
|
||||
|
||||
@FunctionalInterface
|
||||
public interface RepositoryLocationResolverInstance<T> {
|
||||
T getLocation(String repositoryId);
|
||||
|
||||
void setLocation(String repositoryId, T location);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,6 +7,7 @@ import sonia.scm.repository.InternalRepositoryException;
|
||||
import sonia.scm.store.StoreConstants;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Singleton;
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
@@ -28,6 +29,7 @@ import static sonia.scm.ContextEntry.ContextBuilder.entity;
|
||||
*
|
||||
* @since 2.0.0
|
||||
*/
|
||||
@Singleton
|
||||
public class PathBasedRepositoryLocationResolver extends BasicRepositoryLocationResolver<Path> {
|
||||
|
||||
public static final String STORE_NAME = "repository-paths";
|
||||
@@ -64,19 +66,26 @@ public class PathBasedRepositoryLocationResolver extends BasicRepositoryLocation
|
||||
|
||||
@Override
|
||||
protected <T> RepositoryLocationResolverInstance<T> create(Class<T> type) {
|
||||
return repositoryId -> {
|
||||
return new RepositoryLocationResolverInstance<T>() {
|
||||
@Override
|
||||
public T getLocation(String repositoryId) {
|
||||
if (pathById.containsKey(repositoryId)) {
|
||||
return (T) contextProvider.resolve(pathById.get(repositoryId));
|
||||
} else {
|
||||
return (T) create(repositoryId);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLocation(String repositoryId, T location) {
|
||||
PathBasedRepositoryLocationResolver.this.setLocation(repositoryId, (Path) location);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
Path create(String repositoryId) {
|
||||
Path path = initialRepositoryLocationResolver.getPath(repositoryId);
|
||||
pathById.put(repositoryId, path);
|
||||
writePathDatabase();
|
||||
setLocation(repositoryId, path);
|
||||
Path resolvedPath = contextProvider.resolve(path);
|
||||
try {
|
||||
Files.createDirectories(resolvedPath);
|
||||
@@ -138,4 +147,9 @@ public class PathBasedRepositoryLocationResolver extends BasicRepositoryLocation
|
||||
.resolve(StoreConstants.CONFIG_DIRECTORY_NAME)
|
||||
.resolve(STORE_NAME.concat(StoreConstants.FILE_EXTENSION));
|
||||
}
|
||||
|
||||
public void setLocation(String repositoryId, Path repositoryBasePath) {
|
||||
pathById.put(repositoryId, repositoryBasePath);
|
||||
writePathDatabase();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import sonia.scm.io.DefaultFileSystem;
|
||||
import sonia.scm.io.FileSystem;
|
||||
import sonia.scm.repository.NamespaceAndName;
|
||||
import sonia.scm.repository.Repository;
|
||||
import sonia.scm.repository.RepositoryLocationResolver;
|
||||
import sonia.scm.repository.RepositoryPermission;
|
||||
|
||||
import java.io.IOException;
|
||||
@@ -56,7 +57,18 @@ class XmlRepositoryDAOTest {
|
||||
|
||||
@BeforeEach
|
||||
void createDAO(@TempDirectory.TempDir Path basePath) {
|
||||
when(locationResolver.create(Path.class)).thenReturn(locationResolver::create);
|
||||
when(locationResolver.create(Path.class)).thenReturn(
|
||||
new RepositoryLocationResolver.RepositoryLocationResolverInstance<Path>() {
|
||||
@Override
|
||||
public Path getLocation(String repositoryId) {
|
||||
return locationResolver.create(repositoryId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLocation(String repositoryId, Path location) {
|
||||
}
|
||||
}
|
||||
);
|
||||
when(locationResolver.create(anyString())).thenAnswer(invocation -> createMockedRepoPath(basePath, invocation));
|
||||
when(locationResolver.remove(anyString())).thenAnswer(invocation -> basePath.resolve(invocation.getArgument(0).toString()));
|
||||
}
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
package sonia.scm;
|
||||
|
||||
import sonia.scm.repository.BasicRepositoryLocationResolver;
|
||||
import sonia.scm.repository.RepositoryLocationResolver;
|
||||
|
||||
import java.io.File;
|
||||
import java.nio.file.Path;
|
||||
@@ -16,6 +15,16 @@ public class TempDirRepositoryLocationResolver extends BasicRepositoryLocationRe
|
||||
|
||||
@Override
|
||||
protected <T> RepositoryLocationResolverInstance<T> create(Class<T> type) {
|
||||
return repositoryId -> (T) tempDirectory.toPath();
|
||||
return new RepositoryLocationResolverInstance<T>() {
|
||||
@Override
|
||||
public T getLocation(String repositoryId) {
|
||||
return (T) tempDirectory.toPath();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLocation(String repositoryId, T location) {
|
||||
throw new UnsupportedOperationException("not implemented for tests");
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,14 +1,20 @@
|
||||
package sonia.scm.update;
|
||||
|
||||
import com.google.inject.servlet.ServletModule;
|
||||
import sonia.scm.update.repository.XmlRepositoryV1UpdateStep;
|
||||
|
||||
import java.util.List;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
class MigrationWizardModule extends ServletModule {
|
||||
|
||||
private static final Logger LOG = LoggerFactory.getLogger(MigrationWizardModule.class);
|
||||
|
||||
@Override
|
||||
protected void configureServlets() {
|
||||
LOG.info("==========================================================");
|
||||
LOG.info("= =");
|
||||
LOG.info("= STARTING MIGRATION SERVLET =");
|
||||
LOG.info("= =");
|
||||
LOG.info("==========================================================");
|
||||
serve("/*").with(MigrationWizardServlet.class);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
package sonia.scm.update.repository;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import sonia.scm.SCMContextProvider;
|
||||
import sonia.scm.repository.RepositoryDirectoryHandler;
|
||||
import sonia.scm.repository.RepositoryLocationResolver;
|
||||
@@ -10,6 +12,8 @@ import java.nio.file.Path;
|
||||
|
||||
class CopyMigrationStrategy extends BaseMigrationStrategy {
|
||||
|
||||
private static final Logger LOG = LoggerFactory.getLogger(CopyMigrationStrategy.class);
|
||||
|
||||
private final RepositoryLocationResolver locationResolver;
|
||||
|
||||
@Inject
|
||||
@@ -24,6 +28,7 @@ class CopyMigrationStrategy extends BaseMigrationStrategy {
|
||||
Path targetDataPath = repositoryBasePath
|
||||
.resolve(RepositoryDirectoryHandler.REPOSITORIES_NATIVE_DIRECTORY);
|
||||
Path sourceDataPath = getSourceDataPath(name, type);
|
||||
LOG.info("copying repository data from {} to {}", sourceDataPath, targetDataPath);
|
||||
copyData(sourceDataPath, targetDataPath);
|
||||
return repositoryBasePath;
|
||||
}
|
||||
|
||||
@@ -1,7 +1,10 @@
|
||||
package sonia.scm.update.repository;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import sonia.scm.SCMContextProvider;
|
||||
import sonia.scm.repository.RepositoryDirectoryHandler;
|
||||
import sonia.scm.repository.RepositoryLocationResolver;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import java.nio.file.Files;
|
||||
@@ -9,16 +12,23 @@ import java.nio.file.Path;
|
||||
|
||||
class InlineMigrationStrategy extends BaseMigrationStrategy {
|
||||
|
||||
private static final Logger LOG = LoggerFactory.getLogger(InlineMigrationStrategy.class);
|
||||
|
||||
private final RepositoryLocationResolver locationResolver;
|
||||
|
||||
@Inject
|
||||
public InlineMigrationStrategy(SCMContextProvider contextProvider) {
|
||||
public InlineMigrationStrategy(SCMContextProvider contextProvider, RepositoryLocationResolver locationResolver) {
|
||||
super(contextProvider);
|
||||
this.locationResolver = locationResolver;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Path migrate(String id, String name, String type) {
|
||||
Path repositoryBasePath = getSourceDataPath(name, type);
|
||||
locationResolver.forClass(Path.class).setLocation(id, repositoryBasePath);
|
||||
Path targetDataPath = repositoryBasePath
|
||||
.resolve(RepositoryDirectoryHandler.REPOSITORIES_NATIVE_DIRECTORY);
|
||||
LOG.info("moving repository data from {} to {}", repositoryBasePath, targetDataPath);
|
||||
moveData(repositoryBasePath, targetDataPath);
|
||||
return repositoryBasePath;
|
||||
}
|
||||
|
||||
@@ -32,6 +32,7 @@ class MoveMigrationStrategy extends BaseMigrationStrategy {
|
||||
Path targetDataPath = repositoryBasePath
|
||||
.resolve(RepositoryDirectoryHandler.REPOSITORIES_NATIVE_DIRECTORY);
|
||||
Path sourceDataPath = getSourceDataPath(name, type);
|
||||
LOG.info("moving repository data from {} to {}", sourceDataPath, targetDataPath);
|
||||
moveData(sourceDataPath, targetDataPath);
|
||||
deleteOldDataDir(getTypeDependentPath(type), name);
|
||||
return repositoryBasePath;
|
||||
|
||||
@@ -157,6 +157,7 @@ public class XmlRepositoryV1UpdateStep implements UpdateStep {
|
||||
|
||||
private Path handleDataDirectory(V1Repository v1Repository) {
|
||||
MigrationStrategy dataMigrationStrategy = readMigrationStrategy(v1Repository);
|
||||
LOG.info("using strategy {} to migrate repository {} with id {}", dataMigrationStrategy.getClass(), v1Repository.name, v1Repository.id);
|
||||
return dataMigrationStrategy.from(injector).migrate(v1Repository.id, v1Repository.name, v1Repository.type);
|
||||
}
|
||||
|
||||
@@ -231,6 +232,10 @@ public class XmlRepositoryV1UpdateStep implements UpdateStep {
|
||||
return name;
|
||||
}
|
||||
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public String getNewNamespace() {
|
||||
String[] nameParts = getNameParts(name);
|
||||
return nameParts.length > 1 ? nameParts[0] : type;
|
||||
|
||||
@@ -11,6 +11,7 @@ You have migrated from SCM-Manager v1 to SCM-Manager v2.
|
||||
<table>
|
||||
<tr>
|
||||
<th>original name</th>
|
||||
<th>type</th>
|
||||
<th>new namespace/name</th>
|
||||
<th>Strategy</th>
|
||||
</tr>
|
||||
@@ -19,6 +20,9 @@ You have migrated from SCM-Manager v1 to SCM-Manager v2.
|
||||
<td>
|
||||
{{name}}
|
||||
</td>
|
||||
<td>
|
||||
{{type}}
|
||||
</td>
|
||||
<td>
|
||||
{{newNamespace}}/{{newName}}
|
||||
</td>
|
||||
|
||||
@@ -7,11 +7,14 @@ import org.junitpioneer.jupiter.TempDirectory;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
import sonia.scm.SCMContextProvider;
|
||||
import sonia.scm.repository.RepositoryLocationResolver;
|
||||
import sonia.scm.repository.xml.PathBasedRepositoryLocationResolver;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Path;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
@ExtendWith(TempDirectory.class)
|
||||
@@ -20,9 +23,14 @@ class InlineMigrationStrategyTest {
|
||||
|
||||
@Mock
|
||||
SCMContextProvider contextProvider;
|
||||
@Mock
|
||||
PathBasedRepositoryLocationResolver locationResolver;
|
||||
@Mock
|
||||
RepositoryLocationResolver.RepositoryLocationResolverInstance locationResolverInstance;
|
||||
|
||||
@BeforeEach
|
||||
void mockContextProvider(@TempDirectory.TempDir Path tempDir) {
|
||||
when(locationResolver.forClass(Path.class)).thenReturn(locationResolverInstance);
|
||||
when(contextProvider.getBaseDirectory()).thenReturn(tempDir.toFile());
|
||||
}
|
||||
|
||||
@@ -33,13 +41,14 @@ class InlineMigrationStrategyTest {
|
||||
|
||||
@Test
|
||||
void shouldUseExistingDirectory(@TempDirectory.TempDir Path tempDir) {
|
||||
Path target = new InlineMigrationStrategy(contextProvider).migrate("b4f-a9f0-49f7-ad1f-37d3aae1c55f", "some/more/directories/than/one", "git");
|
||||
Path target = new InlineMigrationStrategy(contextProvider, locationResolver).migrate("b4f-a9f0-49f7-ad1f-37d3aae1c55f", "some/more/directories/than/one", "git");
|
||||
assertThat(target).isEqualTo(resolveOldDirectory(tempDir));
|
||||
verify(locationResolverInstance).setLocation("b4f-a9f0-49f7-ad1f-37d3aae1c55f", target);
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldMoveDataDirectory(@TempDirectory.TempDir Path tempDir) {
|
||||
new InlineMigrationStrategy(contextProvider).migrate("b4f-a9f0-49f7-ad1f-37d3aae1c55f", "some/more/directories/than/one", "git");
|
||||
new InlineMigrationStrategy(contextProvider, locationResolver).migrate("b4f-a9f0-49f7-ad1f-37d3aae1c55f", "some/more/directories/than/one", "git");
|
||||
assertThat(resolveOldDirectory(tempDir).resolve("data")).exists();
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user