]> source.dussan.org Git - jgit.git/commitdiff
Support gitdir: refs in BaseRepositoryBuilder.findGitDir 39/6139/2
authorKevin Sawicki <kevin@github.com>
Thu, 10 May 2012 20:32:16 +0000 (13:32 -0700)
committerChris Aniszczyk <zx@twitter.com>
Mon, 4 Jun 2012 16:15:35 +0000 (09:15 -0700)
This allows findGitDir to be used for repositories containing
a .git file with a gitdir: ref to the repository's directory
such as submodule repositories that point to a folder under the
parent repository's .git/modules folder

Change-Id: I2f1ec7215a2208aa90511c065cadc7e816522f62
Signed-off-by: Chris Aniszczyk <zx@twitter.com>
org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/FileRepositoryBuilderTest.java
org.eclipse.jgit/src/org/eclipse/jgit/lib/BaseRepositoryBuilder.java

index aed48aa5fb3b9c282dd5fb3210fe79469bb06520..b6377482dca60939d7d82e7086cbad5539e2ab1c 100644 (file)
@@ -45,13 +45,16 @@ package org.eclipse.jgit.storage.file;
 
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
 import static org.junit.Assert.fail;
 
 import java.io.File;
+import java.io.FileWriter;
 import java.io.IOException;
 
 import org.eclipse.jgit.junit.LocalDiskRepositoryTestCase;
 import org.eclipse.jgit.lib.ConfigConstants;
+import org.eclipse.jgit.lib.Constants;
 import org.eclipse.jgit.util.FileUtils;
 import org.junit.Test;
 
@@ -108,4 +111,58 @@ public class FileRepositoryBuilderTest extends LocalDiskRepositoryTestCase {
                        assertNotNull(e.getMessage());
                }
        }
+
+       @Test
+       public void absoluteGitDirRef() throws Exception {
+               FileRepository repo1 = createWorkRepository();
+               File dir = createTempDirectory("dir");
+               File dotGit = new File(dir, Constants.DOT_GIT);
+               new FileWriter(dotGit).append(
+                               "gitdir: " + repo1.getDirectory().getAbsolutePath()).close();
+               FileRepositoryBuilder builder = new FileRepositoryBuilder();
+
+               builder.setWorkTree(dir);
+               builder.setMustExist(true);
+               FileRepository repo2 = builder.build();
+
+               assertEquals(repo1.getDirectory(), repo2.getDirectory());
+               assertEquals(dir, repo2.getWorkTree());
+       }
+
+       @Test
+       public void relativeGitDirRef() throws Exception {
+               FileRepository repo1 = createWorkRepository();
+               File dir = new File(repo1.getWorkTree(), "dir");
+               assertTrue(dir.mkdir());
+               File dotGit = new File(dir, Constants.DOT_GIT);
+               new FileWriter(dotGit).append("gitdir: ../" + Constants.DOT_GIT)
+                               .close();
+
+               FileRepositoryBuilder builder = new FileRepositoryBuilder();
+               builder.setWorkTree(dir);
+               builder.setMustExist(true);
+               FileRepository repo2 = builder.build();
+
+               assertEquals(repo1.getDirectory(), repo2.getDirectory());
+               assertEquals(dir, repo2.getWorkTree());
+       }
+
+       @Test
+       public void scanWithGitDirRef() throws Exception {
+               FileRepository repo1 = createWorkRepository();
+               File dir = createTempDirectory("dir");
+               File dotGit = new File(dir, Constants.DOT_GIT);
+               new FileWriter(dotGit).append(
+                               "gitdir: " + repo1.getDirectory().getAbsolutePath()).close();
+               FileRepositoryBuilder builder = new FileRepositoryBuilder();
+
+               builder.setWorkTree(dir);
+               builder.findGitDir(dir);
+               assertEquals(repo1.getDirectory(), builder.getGitDir());
+               builder.setMustExist(true);
+               FileRepository repo2 = builder.build();
+
+               assertEquals(repo1.getDirectory(), repo2.getDirectory());
+               assertEquals(dir, repo2.getWorkTree());
+       }
 }
index 17e06039b210331a2ee89348d080f10ad6532dcb..f80c803605e2471ea2801fa3bcf9b6853835d826 100644 (file)
@@ -100,6 +100,29 @@ public class BaseRepositoryBuilder<B extends BaseRepositoryBuilder, R extends Re
                                && ref[7] == ' ';
        }
 
+       private static File getSymRef(File workTree, File dotGit)
+                       throws IOException {
+               byte[] content = IO.readFully(dotGit);
+               if (!isSymRef(content))
+                       throw new IOException(MessageFormat.format(
+                                       JGitText.get().invalidGitdirRef, dotGit.getAbsolutePath()));
+
+               int pathStart = 8;
+               int lineEnd = RawParseUtils.nextLF(content, pathStart);
+               if (content[lineEnd - 1] == '\n')
+                       lineEnd--;
+               if (lineEnd == pathStart)
+                       throw new IOException(MessageFormat.format(
+                                       JGitText.get().invalidGitdirRef, dotGit.getAbsolutePath()));
+
+               String gitdirPath = RawParseUtils.decode(content, pathStart, lineEnd);
+               File gitdirFile = new File(gitdirPath);
+               if (gitdirFile.isAbsolute())
+                       return gitdirFile;
+               else
+                       return new File(workTree, gitdirPath).getCanonicalFile();
+       }
+
        private FS fs;
 
        private File gitDir;
@@ -491,7 +514,13 @@ public class BaseRepositoryBuilder<B extends BaseRepositoryBuilder, R extends Re
                                if (FileKey.isGitRepository(dir, tryFS)) {
                                        setGitDir(dir);
                                        break;
-                               }
+                               } else if (dir.isFile())
+                                       try {
+                                               setGitDir(getSymRef(current, dir));
+                                               break;
+                                       } catch (IOException ignored) {
+                                               // Continue searching if gitdir ref isn't found
+                                       }
 
                                current = current.getParentFile();
                                if (current != null && ceilingDirectories != null
@@ -567,30 +596,8 @@ public class BaseRepositoryBuilder<B extends BaseRepositoryBuilder, R extends Re
                        File dotGit = new File(getWorkTree(), DOT_GIT);
                        if (!dotGit.isFile())
                                setGitDir(dotGit);
-                       else {
-                               byte[] content = IO.readFully(dotGit);
-                               if (!isSymRef(content))
-                                       throw new IOException(MessageFormat.format(
-                                                       JGitText.get().invalidGitdirRef,
-                                                       dotGit.getAbsolutePath()));
-                               int pathStart = 8;
-                               int lineEnd = RawParseUtils.nextLF(content, pathStart);
-                               if (content[lineEnd - 1] == '\n')
-                                       lineEnd--;
-                               if (lineEnd == pathStart)
-                                       throw new IOException(MessageFormat.format(
-                                                       JGitText.get().invalidGitdirRef,
-                                                       dotGit.getAbsolutePath()));
-
-                               String gitdirPath = RawParseUtils.decode(content, pathStart,
-                                               lineEnd);
-                               File gitdirFile = new File(gitdirPath);
-                               if (gitdirFile.isAbsolute())
-                                       setGitDir(gitdirFile);
-                               else
-                                       setGitDir(new File(getWorkTree(), gitdirPath)
-                                                       .getCanonicalFile());
-                       }
+                       else
+                               setGitDir(getSymRef(getWorkTree(), dotGit));
                }
        }