001package co.codewizards.cloudstore.client; 002 003import static co.codewizards.cloudstore.core.oio.OioFileFactory.*; 004 005import java.io.IOException; 006import java.util.UUID; 007 008import org.kohsuke.args4j.Argument; 009import org.kohsuke.args4j.Option; 010 011import co.codewizards.cloudstore.core.oio.File; 012import co.codewizards.cloudstore.core.repo.local.LocalRepoManager; 013import co.codewizards.cloudstore.core.repo.local.LocalRepoManagerFactory; 014import co.codewizards.cloudstore.core.repo.local.LocalRepoRegistry; 015import co.codewizards.cloudstore.core.repo.local.LocalRepoRegistryImpl; 016import co.codewizards.cloudstore.core.util.IOUtil; 017 018/** 019 * {@link SubCommand} implementation for creating a repository in the local file system. 020 * 021 * @author Marco หงุ่ยตระกูล-Schulze - marco at nightlabs dot de 022 */ 023public class CreateRepoSubCommand extends SubCommand 024{ 025 @Argument(metaVar="<localRoot>", required=true, usage="The path of the repository's root in the local file system. This must be an existing directory. If it does not exist and the '-createDir' option is set, it is automatically created.") 026 private String localRoot; 027 028 private File localRootFile; 029 030 @Option(name="-createDir", required=false, usage="Whether to create the repository's root directory, if it does not yet exist. If specified, all parent-directories are created, too, if needed.") 031 private boolean createDir; 032 033 @Option(name="-noAlias", required=false, usage="Whether to suppress the automatic creation of a repository-alias with the local root's name.") 034 private boolean noAlias; 035 036 @Option(name="-alias", metaVar="<alias>", required=false, usage="Specify a different alias. By default, the root directory's name is used. For example, if the repository's root is '/home/user/Documents', the alias 'Documents' is chosen. If this option is present, the specified <alias> is used instead.") 037 private String alias; 038 039 @Override 040 public String getSubCommandDescription() { 041 return "Create a new repository."; 042 } 043 044 @Override 045 public void prepare() throws Exception { 046 super.prepare(); 047 048 if (localRoot == null) 049 localRootFile = createFile("").getAbsoluteFile(); 050 else 051 localRootFile = createFile(localRoot).getAbsoluteFile(); 052 053 localRoot = localRootFile.getPath(); 054 055 if (!noAlias && (alias == null || alias.isEmpty())) { // empty alias means the same as alias not specified. 056 final String simplified = IOUtil.simplifyPath(localRootFile); 057 alias = createFile(simplified).getName(); 058 } 059 060 if (alias != null && alias.isEmpty()) 061 alias = null; 062 } 063 064 @Override 065 public void run() throws Exception { 066 if (alias != null && noAlias) { 067 System.err.println("ERROR: You specified both '-alias' and '-noAlias'. These options exclude each other and cannot be combined!"); 068 System.exit(101); 069 } 070 071 if (!localRootFile.exists() && createDir) { 072 localRootFile.mkdirs(); 073 074 if (!localRootFile.exists()) 075 throw new IOException("Could not create directory (permissions?): " + localRoot); 076 } 077 078 final LocalRepoManager localRepoManager = LocalRepoManagerFactory.Helper.getInstance().createLocalRepoManagerForNewRepository(localRootFile); 079 try { 080 if (!noAlias && alias != null) { 081 final LocalRepoRegistry localRepoRegistry = LocalRepoRegistryImpl.getInstance(); 082 UUID oldRepositoryId = localRepoRegistry.getRepositoryId(alias); 083 084 File oldLocalRoot = null; 085 if (oldRepositoryId != null) { 086 oldLocalRoot = localRepoRegistry.getLocalRoot(oldRepositoryId); 087 if (oldLocalRoot == null || !oldLocalRoot.exists()) { 088 // orphaned entry to be ignored (should be cleaned up after a while, anyway) 089 oldRepositoryId = null; 090 oldLocalRoot = null; 091 } 092 } 093 094 if (oldRepositoryId != null) 095 System.err.println(String.format("WARNING: There is already a repository registered with the alias '%s'! Skipping automatic alias registration. The existing repository's ID is '%s' and its local-root is '%s'.", alias, oldRepositoryId, oldLocalRoot)); 096 else 097 localRepoManager.putRepositoryAlias(alias); 098 } 099 } finally { 100 localRepoManager.close(); 101 } 102 103 new RepoInfoSubCommand(localRootFile).run(); 104 } 105}