diff options
82 files changed, 852 insertions, 455 deletions
diff --git a/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitCloneTask.java b/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitCloneTask.java index f40b7b1e23..8d12ce3ad4 100644 --- a/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitCloneTask.java +++ b/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitCloneTask.java @@ -110,7 +110,7 @@ public class GitCloneTask extends Task { try { clone.setURI(uri).setDirectory(destination).setBranch(branch).setBare(bare); clone.call(); - } catch (RuntimeException e) { + } catch (Exception e) { log("Could not clone repository: " + e, e, Project.MSG_ERR); throw new BuildException("Could not clone repository: " + e.getMessage(), e); } diff --git a/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitInitTask.java b/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitInitTask.java index 7b1610eebe..efdab42aaa 100644 --- a/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitInitTask.java +++ b/org.eclipse.jgit.ant/src/org/eclipse/jgit/ant/tasks/GitInitTask.java @@ -91,7 +91,7 @@ public class GitInitTask extends Task { InitCommand init = Git.init(); init.setBare(bare).setDirectory(destination); init.call(); - } catch (JGitInternalException e) { + } catch (Exception e) { throw new BuildException("Could not initialize repository", e); } } diff --git a/org.eclipse.jgit.http.test/META-INF/MANIFEST.MF b/org.eclipse.jgit.http.test/META-INF/MANIFEST.MF index f015d7b24a..18b9d869d7 100644 --- a/org.eclipse.jgit.http.test/META-INF/MANIFEST.MF +++ b/org.eclipse.jgit.http.test/META-INF/MANIFEST.MF @@ -8,19 +8,20 @@ Bundle-Localization: plugin Bundle-RequiredExecutionEnvironment: J2SE-1.5 Import-Package: javax.servlet;version="[2.5.0,3.0.0)", javax.servlet.http;version="[2.5.0,3.0.0)", - org.eclipse.jetty.continuation;version="[7.1.0,7.6.0)", - org.eclipse.jetty.http;version="[7.1.0,7.6.0)", - org.eclipse.jetty.http.security;version="[7.1.0,7.6.0)", - org.eclipse.jetty.io;version="[7.1.0,7.6.0)", - org.eclipse.jetty.security;version="[7.1.0,7.6.0)", - org.eclipse.jetty.security.authentication;version="[7.1.0,7.6.0)", - org.eclipse.jetty.server;version="[7.1.0,7.6.0)", - org.eclipse.jetty.server.handler;version="[7.1.0,7.6.0)", - org.eclipse.jetty.server.nio;version="[7.1.0,7.6.0)", - org.eclipse.jetty.servlet;version="[7.1.0,7.6.0)", - org.eclipse.jetty.util.component;version="[7.1.0,7.6.0)", - org.eclipse.jetty.util.log;version="[7.1.0,7.6.0)", - org.eclipse.jetty.util.thread;version="[7.1.0,7.6.0)", + org.eclipse.jetty.continuation;version="[7.6.0,8.0.0)", + org.eclipse.jetty.http;version="[7.6.0,8.0.0)", + org.eclipse.jetty.io;version="[7.6.0,8.0.0)", + org.eclipse.jetty.security;version="[7.6.0,8.0.0)", + org.eclipse.jetty.security.authentication;version="[7.6.0,8.0.0)", + org.eclipse.jetty.server;version="[7.6.0,8.0.0)", + org.eclipse.jetty.server.handler;version="[7.6.0,8.0.0)", + org.eclipse.jetty.server.nio;version="[7.6.0,8.0.0)", + org.eclipse.jetty.servlet;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.component;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.log;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.security;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.thread;version="[7.6.0,8.0.0)", org.eclipse.jgit.errors;version="[2.0.0,2.1.0)", org.eclipse.jgit.http.server;version="[2.0.0,2.1.0)", org.eclipse.jgit.http.server.glue;version="[2.0.0,2.1.0)", diff --git a/org.eclipse.jgit.http.test/tst/org/eclipse/jgit/http/test/GitServletInitTest.java b/org.eclipse.jgit.http.test/tst/org/eclipse/jgit/http/test/GitServletInitTest.java index 78db5747f7..9dfb199425 100644 --- a/org.eclipse.jgit.http.test/tst/org/eclipse/jgit/http/test/GitServletInitTest.java +++ b/org.eclipse.jgit.http.test/tst/org/eclipse/jgit/http/test/GitServletInitTest.java @@ -43,7 +43,6 @@ package org.eclipse.jgit.http.test; -import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; @@ -53,6 +52,7 @@ import javax.servlet.ServletException; import org.eclipse.jetty.servlet.ServletContextHandler; import org.eclipse.jetty.servlet.ServletHolder; +import org.eclipse.jetty.util.MultiException; import org.eclipse.jgit.http.server.GitServlet; import org.eclipse.jgit.junit.http.AppServer; import org.eclipse.jgit.junit.http.MockServletConfig; @@ -100,15 +100,28 @@ public class GitServletInitTest { ServletContextHandler app = server.addContext("/"); ServletHolder s = app.addServlet(GitServlet.class, "/git"); s.setInitOrder(1); + s.getServletHandler().setStartWithUnavailable(false); - server.setUp(); - - List<RecordingLogger.Warning> events = RecordingLogger.getWarnings(); - assertFalse("Servlet started without base-path", events.isEmpty()); - - Throwable why = events.get(0).getCause(); - assertTrue("Caught ServletException", why instanceof ServletException); - assertTrue("Wanted base-path", why.getMessage().contains("base-path")); + try { + server.setUp(); + } catch (Exception e) { + Throwable why = null; + if (e instanceof MultiException) { + MultiException multi = (MultiException) e; + List<Throwable> reasons = multi.getThrowables(); + why = reasons.get(0); + assertTrue("Expected ServletException", + why instanceof ServletException); + } else if (e instanceof ServletException) + why = e; + + if (why != null) { + assertTrue("Wanted base-path", + why.getMessage().contains("base-path")); + return; + } + } + fail("Expected ServletException complaining about unset base-path"); } @Test diff --git a/org.eclipse.jgit.junit.http/META-INF/MANIFEST.MF b/org.eclipse.jgit.junit.http/META-INF/MANIFEST.MF index 5257d7f9fd..5413590f4f 100644 --- a/org.eclipse.jgit.junit.http/META-INF/MANIFEST.MF +++ b/org.eclipse.jgit.junit.http/META-INF/MANIFEST.MF @@ -9,19 +9,19 @@ Bundle-ActivationPolicy: lazy Bundle-RequiredExecutionEnvironment: J2SE-1.5 Import-Package: javax.servlet;version="[2.5.0,3.0.0)", javax.servlet.http;version="[2.5.0,3.0.0)", - org.eclipse.jetty.continuation;version="[7.1.0,7.6.0)", - org.eclipse.jetty.http;version="[7.1.0,7.6.0)", - org.eclipse.jetty.http.security;version="[7.1.0,7.6.0)", - org.eclipse.jetty.io;version="[7.1.0,7.6.0)", - org.eclipse.jetty.security;version="[7.1.0,7.6.0)", - org.eclipse.jetty.security.authentication;version="[7.1.0,7.6.0)", - org.eclipse.jetty.server;version="[7.1.0,7.6.0)", - org.eclipse.jetty.server.handler;version="[7.1.0,7.6.0)", - org.eclipse.jetty.server.nio;version="[7.1.0,7.6.0)", - org.eclipse.jetty.servlet;version="[7.1.0,7.6.0)", - org.eclipse.jetty.util.component;version="[7.1.0,7.6.0)", - org.eclipse.jetty.util.log;version="[7.1.0,7.6.0)", - org.eclipse.jetty.util.thread;version="[7.1.0,7.6.0)", + org.eclipse.jetty.continuation;version="[7.6.0,8.0.0)", + org.eclipse.jetty.http;version="[7.6.0,8.0.0)", + org.eclipse.jetty.io;version="[7.6.0,8.0.0)", + org.eclipse.jetty.security;version="[7.6.0,8.0.0)", + org.eclipse.jetty.security.authentication;version="[7.6.0,8.0.0)", + org.eclipse.jetty.server;version="[7.6.0,8.0.0)", + org.eclipse.jetty.server.handler;version="[7.6.0,8.0.0)", + org.eclipse.jetty.server.nio;version="[7.6.0,8.0.0)", + org.eclipse.jetty.servlet;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.component;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.log;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.security;version="[7.6.0,8.0.0)", + org.eclipse.jetty.util.thread;version="[7.6.0,8.0.0)", org.eclipse.jgit.errors;version="[2.0.0,2.1.0)", org.eclipse.jgit.http.server;version="[2.0.0,2.1.0)", org.eclipse.jgit.http.server.resolver;version="[2.0.0,2.1.0)", diff --git a/org.eclipse.jgit.junit.http/src/org/eclipse/jgit/junit/http/AppServer.java b/org.eclipse.jgit.junit.http/src/org/eclipse/jgit/junit/http/AppServer.java index 1e7a6e79aa..6b0e0603e9 100644 --- a/org.eclipse.jgit.junit.http/src/org/eclipse/jgit/junit/http/AppServer.java +++ b/org.eclipse.jgit.junit.http/src/org/eclipse/jgit/junit/http/AppServer.java @@ -1,5 +1,5 @@ /* - * Copyright (C) 2010, Google Inc. + * Copyright (C) 2010, 2012 Google Inc. * and other copyright owners as documented in the project's IP log. * * This program and the accompanying materials are made available @@ -54,8 +54,6 @@ import java.net.UnknownHostException; import java.util.ArrayList; import java.util.List; -import org.eclipse.jetty.http.security.Constraint; -import org.eclipse.jetty.http.security.Password; import org.eclipse.jetty.security.Authenticator; import org.eclipse.jetty.security.ConstraintMapping; import org.eclipse.jetty.security.ConstraintSecurityHandler; @@ -67,7 +65,8 @@ import org.eclipse.jetty.server.UserIdentity; import org.eclipse.jetty.server.handler.ContextHandlerCollection; import org.eclipse.jetty.server.nio.SelectChannelConnector; import org.eclipse.jetty.servlet.ServletContextHandler; -import org.eclipse.jetty.util.thread.QueuedThreadPool; +import org.eclipse.jetty.util.security.Constraint; +import org.eclipse.jetty.util.security.Password; import org.eclipse.jgit.transport.URIish; /** @@ -112,17 +111,6 @@ public class AppServer { throw new RuntimeException("Cannot find localhost", e); } - // We need a handful of threads in the thread pool, otherwise - // our tests will deadlock when they can't open enough requests. - // In theory we only need 1 concurrent connection at a time, but - // I suspect the JRE isn't doing request pipelining on existing - // connections like we want it to. - // - final QueuedThreadPool pool = new QueuedThreadPool(); - pool.setMinThreads(1); - pool.setMaxThreads(4); - pool.setMaxQueued(8); - contexts = new ContextHandlerCollection(); log = new TestRequestLog(); @@ -130,11 +118,7 @@ public class AppServer { server = new Server(); server.setConnectors(new Connector[] { connector }); - server.setThreadPool(pool); server.setHandler(log); - - server.setStopAtShutdown(false); - server.setGracefulShutdown(0); } /** diff --git a/org.eclipse.jgit.packaging/org.eclipse.jgit.feature/pom.xml b/org.eclipse.jgit.packaging/org.eclipse.jgit.feature/pom.xml index f6a1bbe9bb..326f68dc8c 100644 --- a/org.eclipse.jgit.packaging/org.eclipse.jgit.feature/pom.xml +++ b/org.eclipse.jgit.packaging/org.eclipse.jgit.feature/pom.xml @@ -63,7 +63,7 @@ <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> </dependencies> diff --git a/org.eclipse.jgit.packaging/org.eclipse.jgit.junit.feature/pom.xml b/org.eclipse.jgit.packaging/org.eclipse.jgit.junit.feature/pom.xml index b811608a2e..4c1aea78c9 100644 --- a/org.eclipse.jgit.packaging/org.eclipse.jgit.junit.feature/pom.xml +++ b/org.eclipse.jgit.packaging/org.eclipse.jgit.junit.feature/pom.xml @@ -63,17 +63,17 @@ <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit.junit</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit.junit.http</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit.http.server</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> </dependencies> diff --git a/org.eclipse.jgit.packaging/org.eclipse.jgit.repository/pom.xml b/org.eclipse.jgit.packaging/org.eclipse.jgit.repository/pom.xml index f088af1953..e87f4498da 100644 --- a/org.eclipse.jgit.packaging/org.eclipse.jgit.repository/pom.xml +++ b/org.eclipse.jgit.packaging/org.eclipse.jgit.repository/pom.xml @@ -64,22 +64,22 @@ <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit.junit</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit.junit.http</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit.http.server</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> </dependency> </dependencies> diff --git a/org.eclipse.jgit.packaging/pom.xml b/org.eclipse.jgit.packaging/pom.xml index 3fb354e915..d3a9563077 100644 --- a/org.eclipse.jgit.packaging/pom.xml +++ b/org.eclipse.jgit.packaging/pom.xml @@ -60,6 +60,7 @@ <properties> <tycho-version>0.14.1</tycho-version> + <jetty-version>7.6.0.v20120127</jetty-version> <eclipse-site>http://download.eclipse.org/releases/indigo</eclipse-site> </properties> @@ -76,6 +77,11 @@ <layout>p2</layout> <url>${eclipse-site}</url> </repository> + <repository> + <id>jetty</id> + <layout>p2</layout> + <url>http://download.eclipse.org/jetty/updates/jetty-bundles-7.x/${jetty-version}/</url> + </repository> </repositories> <dependencies> @@ -83,7 +89,7 @@ <dependency> <groupId>org.eclipse.jgit</groupId> <artifactId>org.eclipse.jgit</artifactId> - <version>2.0.0-SNAPSHOT</version> + <version>${project.version}</version> <classifier>sources</classifier> </dependency> </dependencies> diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/AddCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/AddCommandTest.java index 2fb228e01d..fd74098496 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/AddCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/AddCommandTest.java @@ -52,6 +52,7 @@ import java.io.FileInputStream; import java.io.IOException; import java.io.PrintWriter; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.NoFilepatternException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheBuilder; @@ -72,7 +73,7 @@ import org.junit.Test; public class AddCommandTest extends RepositoryTestCase { @Test - public void testAddNothing() { + public void testAddNothing() throws GitAPIException { Git git = new Git(db); try { @@ -85,7 +86,7 @@ public class AddCommandTest extends RepositoryTestCase { } @Test - public void testAddNonExistingSingleFile() throws NoFilepatternException { + public void testAddNonExistingSingleFile() throws GitAPIException { Git git = new Git(db); DirCache dc = git.add().addFilepattern("a.txt").call(); @@ -94,7 +95,7 @@ public class AddCommandTest extends RepositoryTestCase { } @Test - public void testAddExistingSingleFile() throws IOException, NoFilepatternException { + public void testAddExistingSingleFile() throws IOException, GitAPIException { File file = new File(db.getWorkTree(), "a.txt"); FileUtils.createNewFile(file); PrintWriter writer = new PrintWriter(file); @@ -112,7 +113,7 @@ public class AddCommandTest extends RepositoryTestCase { @Test public void testAddExistingSingleSmallFileWithNewLine() throws IOException, - NoFilepatternException { + GitAPIException { File file = new File(db.getWorkTree(), "a.txt"); FileUtils.createNewFile(file); PrintWriter writer = new PrintWriter(file); @@ -136,7 +137,7 @@ public class AddCommandTest extends RepositoryTestCase { @Test public void testAddExistingSingleMediumSizeFileWithNewLine() - throws IOException, NoFilepatternException { + throws IOException, GitAPIException { File file = new File(db.getWorkTree(), "a.txt"); FileUtils.createNewFile(file); StringBuilder data = new StringBuilder(); @@ -165,7 +166,7 @@ public class AddCommandTest extends RepositoryTestCase { @Test public void testAddExistingSingleBinaryFile() throws IOException, - NoFilepatternException { + GitAPIException { File file = new File(db.getWorkTree(), "a.txt"); FileUtils.createNewFile(file); PrintWriter writer = new PrintWriter(file); @@ -188,7 +189,8 @@ public class AddCommandTest extends RepositoryTestCase { } @Test - public void testAddExistingSingleFileInSubDir() throws IOException, NoFilepatternException { + public void testAddExistingSingleFileInSubDir() throws IOException, + GitAPIException { FileUtils.mkdir(new File(db.getWorkTree(), "sub")); File file = new File(db.getWorkTree(), "sub/a.txt"); FileUtils.createNewFile(file); @@ -206,7 +208,8 @@ public class AddCommandTest extends RepositoryTestCase { } @Test - public void testAddExistingSingleFileTwice() throws IOException, NoFilepatternException { + public void testAddExistingSingleFileTwice() throws IOException, + GitAPIException { File file = new File(db.getWorkTree(), "a.txt"); FileUtils.createNewFile(file); PrintWriter writer = new PrintWriter(file); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/BranchCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/BranchCommandTest.java index 32d2e01b24..b000fe24e5 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/BranchCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/BranchCommandTest.java @@ -466,9 +466,7 @@ public class BranchCommandTest extends RepositoryTestCase { public Ref createBranch(Git actGit, String name, boolean force, String startPoint, SetupUpstreamMode mode) - throws JGitInternalException, RefAlreadyExistsException, - RefNotFoundException, - InvalidRefNameException { + throws JGitInternalException, GitAPIException { CreateBranchCommand cmd = actGit.branchCreate(); cmd.setName(name); cmd.setForce(force); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CheckoutCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CheckoutCommandTest.java index b1cac3a54d..9060cd5307 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CheckoutCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CheckoutCommandTest.java @@ -56,11 +56,11 @@ import java.io.FileInputStream; import java.io.IOException; import org.eclipse.jgit.api.CheckoutResult.Status; -import org.eclipse.jgit.api.errors.CheckoutConflictException; -import org.eclipse.jgit.api.errors.InvalidRefNameException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; -import org.eclipse.jgit.api.errors.RefAlreadyExistsException; import org.eclipse.jgit.api.errors.RefNotFoundException; +import org.eclipse.jgit.dircache.DirCache; +import org.eclipse.jgit.dircache.DirCacheEntry; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Ref; import org.eclipse.jgit.lib.RefUpdate; @@ -127,9 +127,7 @@ public class CheckoutCommandTest extends RepositoryTestCase { } @Test - public void testCheckoutToNonExistingBranch() throws JGitInternalException, - RefAlreadyExistsException, InvalidRefNameException, - CheckoutConflictException { + public void testCheckoutToNonExistingBranch() throws GitAPIException { try { git.checkout().setName("badbranch").call(); fail("Should have failed"); @@ -223,8 +221,7 @@ public class CheckoutCommandTest extends RepositoryTestCase { @Test public void testDetachedHeadOnCheckout() throws JGitInternalException, - RefAlreadyExistsException, RefNotFoundException, - InvalidRefNameException, IOException, CheckoutConflictException { + IOException, GitAPIException { CheckoutCommand co = git.checkout(); co.setName("master").call(); @@ -236,4 +233,41 @@ public class CheckoutCommandTest extends RepositoryTestCase { assertFalse(head.isSymbolic()); assertSame(head, head.getTarget()); } + + @Test + public void testUpdateSmudgedEntries() throws Exception { + git.branchCreate().setName("test2").call(); + RefUpdate rup = db.updateRef(Constants.HEAD); + rup.link("refs/heads/test2"); + + File file = new File(db.getWorkTree(), "Test.txt"); + long size = file.length(); + long mTime = file.lastModified() - 5000L; + assertTrue(file.setLastModified(mTime)); + + DirCache cache = DirCache.lock(db.getIndexFile(), db.getFS()); + DirCacheEntry entry = cache.getEntry("Test.txt"); + assertNotNull(entry); + entry.setLength(0); + entry.setLastModified(0); + cache.write(); + assertTrue(cache.commit()); + + cache = DirCache.read(db.getIndexFile(), db.getFS()); + entry = cache.getEntry("Test.txt"); + assertNotNull(entry); + assertEquals(0, entry.getLength()); + assertEquals(0, entry.getLastModified()); + + db.getIndexFile().setLastModified( + db.getIndexFile().lastModified() - 5000); + + assertNotNull(git.checkout().setName("test").call()); + + cache = DirCache.read(db.getIndexFile(), db.getFS()); + entry = cache.getEntry("Test.txt"); + assertNotNull(entry); + assertEquals(size, entry.getLength()); + assertEquals(mTime, entry.getLastModified()); + } } diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CleanCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CleanCommandTest.java index a660a5292b..07387e4fa6 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CleanCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CleanCommandTest.java @@ -44,10 +44,10 @@ package org.eclipse.jgit.api; import static org.junit.Assert.assertTrue; -import java.io.IOException; import java.util.Set; import java.util.TreeSet; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.errors.NoWorkTreeException; import org.eclipse.jgit.lib.RepositoryTestCase; import org.junit.Before; @@ -75,7 +75,7 @@ public class CleanCommandTest extends RepositoryTestCase { } @Test - public void testClean() throws NoWorkTreeException, IOException { + public void testClean() throws NoWorkTreeException, GitAPIException { // create status StatusCommand command = git.status(); Status status = command.call(); @@ -94,7 +94,8 @@ public class CleanCommandTest extends RepositoryTestCase { } @Test - public void testCleanWithPaths() throws NoWorkTreeException, IOException { + public void testCleanWithPaths() throws NoWorkTreeException, + GitAPIException { // create status StatusCommand command = git.status(); Status status = command.call(); @@ -114,7 +115,8 @@ public class CleanCommandTest extends RepositoryTestCase { } @Test - public void testCleanWithDryRun() throws NoWorkTreeException, IOException { + public void testCleanWithDryRun() throws NoWorkTreeException, + GitAPIException { // create status StatusCommand command = git.status(); Status status = command.call(); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CloneCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CloneCommandTest.java index 906a8966fa..4441ea9301 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CloneCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CloneCommandTest.java @@ -55,6 +55,7 @@ import java.util.List; import java.util.Map; import org.eclipse.jgit.api.ListBranchCommand.ListMode; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.junit.TestRepository; import org.eclipse.jgit.lib.ConfigConstants; @@ -103,7 +104,8 @@ public class CloneCommandTest extends RepositoryTestCase { } @Test - public void testCloneRepository() throws IOException { + public void testCloneRepository() throws IOException, + JGitInternalException, GitAPIException { File directory = createTempDirectory("testCloneRepository"); CloneCommand command = Git.cloneRepository(); command.setDirectory(directory); @@ -131,7 +133,8 @@ public class CloneCommandTest extends RepositoryTestCase { } @Test - public void testCloneRepositoryWithBranch() throws IOException { + public void testCloneRepositoryWithBranch() throws IOException, + JGitInternalException, GitAPIException { File directory = createTempDirectory("testCloneRepositoryWithBranch"); CloneCommand command = Git.cloneRepository(); command.setBranch("refs/heads/master"); @@ -178,7 +181,8 @@ public class CloneCommandTest extends RepositoryTestCase { } @Test - public void testCloneRepositoryOnlyOneBranch() throws IOException { + public void testCloneRepositoryOnlyOneBranch() throws IOException, + JGitInternalException, GitAPIException { File directory = createTempDirectory("testCloneRepositoryWithBranch"); CloneCommand command = Git.cloneRepository(); command.setBranch("refs/heads/master"); @@ -222,7 +226,7 @@ public class CloneCommandTest extends RepositoryTestCase { @Test public void testCloneRepositoryWhenDestinationDirectoryExistsAndIsNotEmpty() - throws IOException { + throws IOException, JGitInternalException, GitAPIException { String dirName = "testCloneTargetDirectoryNotEmpty"; File directory = createTempDirectory(dirName); CloneCommand command = Git.cloneRepository(); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitAndLogCommandTests.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitAndLogCommandTests.java index e6b6a096fa..ed32e27b0a 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitAndLogCommandTests.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitAndLogCommandTests.java @@ -50,15 +50,12 @@ import static org.junit.Assert.fail; import java.io.File; import java.io.IOException; import java.io.PrintWriter; -import org.eclipse.jgit.api.errors.ConcurrentRefUpdateException; + +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; -import org.eclipse.jgit.api.errors.NoFilepatternException; -import org.eclipse.jgit.api.errors.NoHeadException; import org.eclipse.jgit.api.errors.NoMessageException; -import org.eclipse.jgit.api.errors.WrongRepositoryStateException; import org.eclipse.jgit.errors.IncorrectObjectTypeException; import org.eclipse.jgit.errors.MissingObjectException; -import org.eclipse.jgit.errors.UnmergedPathException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.ObjectId; import org.eclipse.jgit.lib.PersonIdent; @@ -77,9 +74,8 @@ import org.junit.Test; */ public class CommitAndLogCommandTests extends RepositoryTestCase { @Test - public void testSomeCommits() throws NoHeadException, NoMessageException, - ConcurrentRefUpdateException, JGitInternalException, - WrongRepositoryStateException, IOException { + public void testSomeCommits() throws JGitInternalException, IOException, + GitAPIException { // do 4 commits Git git = new Git(db); @@ -115,9 +111,8 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testLogWithFilter() throws IOException, NoFilepatternException, - NoHeadException, NoMessageException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void testLogWithFilter() throws IOException, JGitInternalException, + GitAPIException { Git git = new Git(db); @@ -170,9 +165,7 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { // try to do a commit without specifying a message. Should fail! @Test - public void testWrongParams() throws UnmergedPathException, - NoHeadException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void testWrongParams() throws GitAPIException { Git git = new Git(db); try { git.commit().setAuthor(author).call(); @@ -185,10 +178,7 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { // try to work with Commands after command has been invoked. Should throw // exceptions @Test - public void testMultipleInvocations() throws NoHeadException, - ConcurrentRefUpdateException, NoMessageException, - UnmergedPathException, JGitInternalException, - WrongRepositoryStateException { + public void testMultipleInvocations() throws GitAPIException { Git git = new Git(db); CommitCommand commitCmd = git.commit(); commitCmd.setMessage("initial commit").call(); @@ -211,9 +201,8 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testMergeEmptyBranches() throws IOException, NoHeadException, - NoMessageException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void testMergeEmptyBranches() throws IOException, + JGitInternalException, GitAPIException { Git git = new Git(db); git.commit().setMessage("initial commit").call(); RefUpdate r = db.updateRef("refs/heads/side"); @@ -235,10 +224,8 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testAddUnstagedChanges() throws IOException, NoHeadException, - NoMessageException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException, - NoFilepatternException { + public void testAddUnstagedChanges() throws IOException, + JGitInternalException, GitAPIException { File file = new File(db.getWorkTree(), "a.txt"); FileUtils.createNewFile(file); PrintWriter writer = new PrintWriter(file); @@ -268,9 +255,7 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testModeChange() throws IOException, NoFilepatternException, - NoHeadException, NoMessageException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void testModeChange() throws IOException, GitAPIException { Git git = new Git(db); // create file @@ -298,10 +283,9 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testCommitRange() throws NoHeadException, NoMessageException, - UnmergedPathException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException, - IncorrectObjectTypeException, MissingObjectException { + public void testCommitRange() throws GitAPIException, + JGitInternalException, MissingObjectException, + IncorrectObjectTypeException { // do 4 commits and set the range to the second and fourth one Git git = new Git(db); git.commit().setMessage("first commit").call(); @@ -334,9 +318,8 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testCommitAmend() throws NoHeadException, NoMessageException, - ConcurrentRefUpdateException, JGitInternalException, - WrongRepositoryStateException, IOException { + public void testCommitAmend() throws JGitInternalException, IOException, + GitAPIException { Git git = new Git(db); git.commit().setMessage("first comit").call(); // typo git.commit().setAmend(true).setMessage("first commit").call(); @@ -357,10 +340,8 @@ public class CommitAndLogCommandTests extends RepositoryTestCase { } @Test - public void testInsertChangeId() throws NoHeadException, - NoMessageException, - UnmergedPathException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void testInsertChangeId() throws JGitInternalException, + GitAPIException { Git git = new Git(db); String messageHeader = "Some header line\n\nSome detail explanation\n"; String changeIdTemplate = "\nChange-Id: I" diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitCommandTest.java index b9f5882d50..3aec611f44 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/CommitCommandTest.java @@ -50,6 +50,7 @@ import java.io.File; import java.util.List; import org.eclipse.jgit.diff.DiffEntry; +import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.lib.ConfigConstants; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.FileMode; @@ -258,4 +259,110 @@ public class CommitCommandTest extends RepositoryTestCase { assertEquals(path, subDiff.getNewPath()); assertEquals(path, subDiff.getOldPath()); } + + @Test + public void commitUpdatesSmudgedEntries() throws Exception { + Git git = new Git(db); + + File file1 = writeTrashFile("file1.txt", "content1"); + assertTrue(file1.setLastModified(file1.lastModified() - 5000)); + File file2 = writeTrashFile("file2.txt", "content2"); + assertTrue(file2.setLastModified(file2.lastModified() - 5000)); + File file3 = writeTrashFile("file3.txt", "content3"); + assertTrue(file3.setLastModified(file3.lastModified() - 5000)); + + assertNotNull(git.add().addFilepattern("file1.txt") + .addFilepattern("file2.txt").addFilepattern("file3.txt").call()); + RevCommit commit = git.commit().setMessage("add files").call(); + assertNotNull(commit); + + DirCache cache = DirCache.read(db.getIndexFile(), db.getFS()); + int file1Size = cache.getEntry("file1.txt").getLength(); + int file2Size = cache.getEntry("file2.txt").getLength(); + int file3Size = cache.getEntry("file3.txt").getLength(); + ObjectId file2Id = cache.getEntry("file2.txt").getObjectId(); + ObjectId file3Id = cache.getEntry("file3.txt").getObjectId(); + assertTrue(file1Size > 0); + assertTrue(file2Size > 0); + assertTrue(file3Size > 0); + + // Smudge entries + cache = DirCache.lock(db.getIndexFile(), db.getFS()); + cache.getEntry("file1.txt").setLength(0); + cache.getEntry("file2.txt").setLength(0); + cache.getEntry("file3.txt").setLength(0); + cache.write(); + assertTrue(cache.commit()); + + // Verify entries smudged + cache = DirCache.read(db.getIndexFile(), db.getFS()); + assertEquals(0, cache.getEntry("file1.txt").getLength()); + assertEquals(0, cache.getEntry("file2.txt").getLength()); + assertEquals(0, cache.getEntry("file3.txt").getLength()); + + long indexTime = db.getIndexFile().lastModified(); + db.getIndexFile().setLastModified(indexTime - 5000); + + write(file1, "content4"); + assertTrue(file1.setLastModified(file1.lastModified() + 1000)); + assertNotNull(git.commit().setMessage("edit file").setOnly("file1.txt") + .call()); + + cache = db.readDirCache(); + assertEquals(file1Size, cache.getEntry("file1.txt").getLength()); + assertEquals(file2Size, cache.getEntry("file2.txt").getLength()); + assertEquals(file3Size, cache.getEntry("file3.txt").getLength()); + assertEquals(file2Id, cache.getEntry("file2.txt").getObjectId()); + assertEquals(file3Id, cache.getEntry("file3.txt").getObjectId()); + } + + @Test + public void commitIgnoresSmudgedEntryWithDifferentId() throws Exception { + Git git = new Git(db); + + File file1 = writeTrashFile("file1.txt", "content1"); + assertTrue(file1.setLastModified(file1.lastModified() - 5000)); + File file2 = writeTrashFile("file2.txt", "content2"); + assertTrue(file2.setLastModified(file2.lastModified() - 5000)); + + assertNotNull(git.add().addFilepattern("file1.txt") + .addFilepattern("file2.txt").call()); + RevCommit commit = git.commit().setMessage("add files").call(); + assertNotNull(commit); + + DirCache cache = DirCache.read(db.getIndexFile(), db.getFS()); + int file1Size = cache.getEntry("file1.txt").getLength(); + int file2Size = cache.getEntry("file2.txt").getLength(); + assertTrue(file1Size > 0); + assertTrue(file2Size > 0); + + writeTrashFile("file2.txt", "content3"); + assertNotNull(git.add().addFilepattern("file2.txt").call()); + writeTrashFile("file2.txt", "content4"); + + // Smudge entries + cache = DirCache.lock(db.getIndexFile(), db.getFS()); + cache.getEntry("file1.txt").setLength(0); + cache.getEntry("file2.txt").setLength(0); + cache.write(); + assertTrue(cache.commit()); + + // Verify entries smudged + cache = db.readDirCache(); + assertEquals(0, cache.getEntry("file1.txt").getLength()); + assertEquals(0, cache.getEntry("file2.txt").getLength()); + + long indexTime = db.getIndexFile().lastModified(); + db.getIndexFile().setLastModified(indexTime - 5000); + + write(file1, "content5"); + assertTrue(file1.setLastModified(file1.lastModified() + 1000)); + + assertNotNull(git.commit().setMessage("edit file").setOnly("file1.txt") + .call()); + + cache = db.readDirCache(); + assertEquals(file1Size, cache.getEntry("file1.txt").getLength()); + assertEquals(0, cache.getEntry("file2.txt").getLength()); + } } diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/GitConstructionTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/GitConstructionTest.java index 8031769204..d8e1a058f7 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/GitConstructionTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/GitConstructionTest.java @@ -48,6 +48,8 @@ import static org.junit.Assert.fail; import java.io.IOException; import org.eclipse.jgit.api.ListBranchCommand.ListMode; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.RepositoryNotFoundException; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.RepositoryTestCase; @@ -84,7 +86,7 @@ public class GitConstructionTest extends RepositoryTestCase { } @Test - public void testWrap() { + public void testWrap() throws JGitInternalException, GitAPIException { Git git = Git.wrap(db); assertEquals(1, git.branchList().call().size()); @@ -101,7 +103,8 @@ public class GitConstructionTest extends RepositoryTestCase { } @Test - public void testOpen() throws IOException { + public void testOpen() throws IOException, JGitInternalException, + GitAPIException { Git git = Git.open(db.getDirectory()); assertEquals(1, git.branchList().call().size()); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/InitCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/InitCommandTest.java index 28236369e4..7db9ce71c1 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/InitCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/InitCommandTest.java @@ -48,6 +48,8 @@ import static org.junit.Assert.assertTrue; import java.io.File; import java.io.IOException; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.RepositoryTestCase; import org.junit.Before; @@ -62,7 +64,8 @@ public class InitCommandTest extends RepositoryTestCase { } @Test - public void testInitRepository() throws IOException { + public void testInitRepository() throws IOException, JGitInternalException, + GitAPIException { File directory = createTempDirectory("testInitRepository"); InitCommand command = new InitCommand(); command.setDirectory(directory); @@ -72,7 +75,8 @@ public class InitCommandTest extends RepositoryTestCase { } @Test - public void testInitNonEmptyRepository() throws IOException { + public void testInitNonEmptyRepository() throws IOException, + JGitInternalException, GitAPIException { File directory = createTempDirectory("testInitRepository2"); File someFile = new File(directory, "someFile"); someFile.createNewFile(); @@ -86,7 +90,8 @@ public class InitCommandTest extends RepositoryTestCase { } @Test - public void testInitBareRepository() throws IOException { + public void testInitBareRepository() throws IOException, + JGitInternalException, GitAPIException { File directory = createTempDirectory("testInitBareRepository"); InitCommand command = new InitCommand(); command.setDirectory(directory); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RebaseCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RebaseCommandTest.java index 648ef6f01b..cf2dead5a4 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RebaseCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RebaseCommandTest.java @@ -293,7 +293,8 @@ public class RebaseCommandTest extends RepositoryTestCase { // change third line in topic branch writeTrashFile(FILE1, "1\n2\n3\ntopic\n"); git.add().addFilepattern(FILE1).call(); - git.commit().setMessage("change file1 in topic").call(); + RevCommit origHead = git.commit().setMessage("change file1 in topic") + .call(); RebaseResult res = git.rebase().setUpstream("refs/heads/master").call(); assertEquals(Status.OK, res.getStatus()); @@ -302,6 +303,7 @@ public class RebaseCommandTest extends RepositoryTestCase { assertEquals("refs/heads/topic", db.getFullBranch()); assertEquals(lastMasterChange, new RevWalk(db).parseCommit( db.resolve(Constants.HEAD)).getParent(0)); + assertEquals(origHead, db.readOrigHead()); } @Test diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/ResetCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/ResetCommandTest.java index 27c3549be3..0806cf0dd0 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/ResetCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/ResetCommandTest.java @@ -54,12 +54,8 @@ import java.io.IOException; import java.io.PrintWriter; import org.eclipse.jgit.api.ResetCommand.ResetType; -import org.eclipse.jgit.api.errors.ConcurrentRefUpdateException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; -import org.eclipse.jgit.api.errors.NoFilepatternException; -import org.eclipse.jgit.api.errors.NoHeadException; -import org.eclipse.jgit.api.errors.NoMessageException; -import org.eclipse.jgit.api.errors.WrongRepositoryStateException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEntry; import org.eclipse.jgit.errors.AmbiguousObjectException; @@ -87,9 +83,8 @@ public class ResetCommandTest extends RepositoryTestCase { private DirCacheEntry prestage; - public void setupRepository() throws IOException, NoFilepatternException, - NoHeadException, NoMessageException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void setupRepository() throws IOException, JGitInternalException, + GitAPIException { // create initial commit git = new Git(db); @@ -138,9 +133,7 @@ public class ResetCommandTest extends RepositoryTestCase { @Test public void testHardReset() throws JGitInternalException, - AmbiguousObjectException, IOException, NoFilepatternException, - NoHeadException, NoMessageException, ConcurrentRefUpdateException, - WrongRepositoryStateException { + AmbiguousObjectException, IOException, GitAPIException { setupRepository(); ObjectId prevHead = db.resolve(Constants.HEAD); git.reset().setMode(ResetType.HARD).setRef(initialCommit.getName()) @@ -156,11 +149,12 @@ public class ResetCommandTest extends RepositoryTestCase { assertFalse(inHead(fileInIndexPath)); assertFalse(inIndex(indexFile.getName())); assertReflog(prevHead, head); + assertEquals(prevHead, db.readOrigHead()); } @Test public void testResetToNonexistingHEAD() throws JGitInternalException, - AmbiguousObjectException, IOException { + AmbiguousObjectException, IOException, GitAPIException { // create a file in the working tree of a fresh repo git = new Git(db); @@ -176,9 +170,7 @@ public class ResetCommandTest extends RepositoryTestCase { @Test public void testSoftReset() throws JGitInternalException, - AmbiguousObjectException, IOException, NoFilepatternException, - NoHeadException, NoMessageException, ConcurrentRefUpdateException, - WrongRepositoryStateException { + AmbiguousObjectException, IOException, GitAPIException { setupRepository(); ObjectId prevHead = db.resolve(Constants.HEAD); git.reset().setMode(ResetType.SOFT).setRef(initialCommit.getName()) @@ -194,13 +186,12 @@ public class ResetCommandTest extends RepositoryTestCase { assertFalse(inHead(fileInIndexPath)); assertTrue(inIndex(indexFile.getName())); assertReflog(prevHead, head); + assertEquals(prevHead, db.readOrigHead()); } @Test public void testMixedReset() throws JGitInternalException, - AmbiguousObjectException, IOException, NoFilepatternException, - NoHeadException, NoMessageException, ConcurrentRefUpdateException, - WrongRepositoryStateException { + AmbiguousObjectException, IOException, GitAPIException { setupRepository(); ObjectId prevHead = db.resolve(Constants.HEAD); git.reset().setMode(ResetType.MIXED).setRef(initialCommit.getName()) @@ -217,6 +208,49 @@ public class ResetCommandTest extends RepositoryTestCase { assertFalse(inIndex(indexFile.getName())); assertReflog(prevHead, head); + assertEquals(prevHead, db.readOrigHead()); + } + + @Test + public void testMixedResetRetainsSizeAndModifiedTime() throws Exception { + git = new Git(db); + + writeTrashFile("a.txt", "a").setLastModified( + System.currentTimeMillis() - 60 * 1000); + assertNotNull(git.add().addFilepattern("a.txt").call()); + assertNotNull(git.commit().setMessage("a commit").call()); + + writeTrashFile("b.txt", "b").setLastModified( + System.currentTimeMillis() - 60 * 1000); + assertNotNull(git.add().addFilepattern("b.txt").call()); + RevCommit commit2 = git.commit().setMessage("b commit").call(); + assertNotNull(commit2); + + DirCache cache = db.readDirCache(); + + DirCacheEntry aEntry = cache.getEntry("a.txt"); + assertNotNull(aEntry); + assertTrue(aEntry.getLength() > 0); + assertTrue(aEntry.getLastModified() > 0); + + DirCacheEntry bEntry = cache.getEntry("b.txt"); + assertNotNull(bEntry); + assertTrue(bEntry.getLength() > 0); + assertTrue(bEntry.getLastModified() > 0); + + git.reset().setMode(ResetType.MIXED).setRef(commit2.getName()).call(); + + cache = db.readDirCache(); + + DirCacheEntry mixedAEntry = cache.getEntry("a.txt"); + assertNotNull(mixedAEntry); + assertEquals(aEntry.getLastModified(), mixedAEntry.getLastModified()); + assertEquals(aEntry.getLastModified(), mixedAEntry.getLastModified()); + + DirCacheEntry mixedBEntry = cache.getEntry("b.txt"); + assertNotNull(mixedBEntry); + assertEquals(bEntry.getLastModified(), mixedBEntry.getLastModified()); + assertEquals(bEntry.getLastModified(), mixedBEntry.getLastModified()); } @Test diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RmCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RmCommandTest.java index d826b4c135..2eb4f22940 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RmCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/RmCommandTest.java @@ -46,8 +46,8 @@ import static org.junit.Assert.assertEquals; import java.io.IOException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; -import org.eclipse.jgit.api.errors.NoFilepatternException; import org.eclipse.jgit.lib.RepositoryTestCase; import org.junit.Before; import org.junit.Test; @@ -71,7 +71,7 @@ public class RmCommandTest extends RepositoryTestCase { @Test public void testRemove() throws JGitInternalException, - NoFilepatternException, IllegalStateException, IOException { + IllegalStateException, IOException, GitAPIException { assertEquals("[test.txt, mode:100644, content:Hello world]", indexState(CONTENT)); RmCommand command = git.rm(); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/StatusCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/StatusCommandTest.java index faca7ea3ab..c9a6048695 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/StatusCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/StatusCommandTest.java @@ -52,13 +52,15 @@ import java.util.Set; import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.NoFilepatternException; +import org.eclipse.jgit.errors.NoWorkTreeException; import org.eclipse.jgit.lib.RepositoryTestCase; import org.junit.Test; public class StatusCommandTest extends RepositoryTestCase { @Test - public void testEmptyStatus() throws IOException { + public void testEmptyStatus() throws NoWorkTreeException, + GitAPIException { Git git = new Git(db); Status stat = git.status().call(); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/TagCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/TagCommandTest.java index 7f381e3932..b417b44851 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/TagCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/api/TagCommandTest.java @@ -48,15 +48,9 @@ import static org.junit.Assert.fail; import java.io.IOException; import java.util.List; -import org.eclipse.jgit.api.errors.ConcurrentRefUpdateException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidTagNameException; import org.eclipse.jgit.api.errors.JGitInternalException; -import org.eclipse.jgit.api.errors.NoHeadException; -import org.eclipse.jgit.api.errors.NoMessageException; -import org.eclipse.jgit.api.errors.WrongRepositoryStateException; -import org.eclipse.jgit.errors.IncorrectObjectTypeException; -import org.eclipse.jgit.errors.MissingObjectException; -import org.eclipse.jgit.errors.UnmergedPathException; import org.eclipse.jgit.lib.Ref; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.RepositoryTestCase; @@ -67,10 +61,7 @@ import org.junit.Test; public class TagCommandTest extends RepositoryTestCase { @Test - public void testTaggingOnHead() throws NoHeadException, NoMessageException, - ConcurrentRefUpdateException, JGitInternalException, - WrongRepositoryStateException, InvalidTagNameException, - MissingObjectException, IncorrectObjectTypeException, IOException { + public void testTaggingOnHead() throws GitAPIException, IOException { Git git = new Git(db); RevCommit commit = git.commit().setMessage("initial commit").call(); Ref tagRef = git.tag().setName("tag").call(); @@ -80,10 +71,7 @@ public class TagCommandTest extends RepositoryTestCase { } @Test - public void testTagging() throws NoHeadException, NoMessageException, - UnmergedPathException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException, - InvalidTagNameException { + public void testTagging() throws GitAPIException, JGitInternalException { Git git = new Git(db); git.commit().setMessage("initial commit").call(); RevCommit commit = git.commit().setMessage("second commit").call(); @@ -93,9 +81,7 @@ public class TagCommandTest extends RepositoryTestCase { } @Test - public void testEmptyTagName() throws NoHeadException, NoMessageException, - UnmergedPathException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public void testEmptyTagName() throws GitAPIException { Git git = new Git(db); git.commit().setMessage("initial commit").call(); try { @@ -108,10 +94,7 @@ public class TagCommandTest extends RepositoryTestCase { } @Test - public void testInvalidTagName() throws NoHeadException, - NoMessageException, UnmergedPathException, - ConcurrentRefUpdateException, JGitInternalException, - WrongRepositoryStateException { + public void testInvalidTagName() throws GitAPIException { Git git = new Git(db); git.commit().setMessage("initial commit").call(); try { @@ -123,10 +106,7 @@ public class TagCommandTest extends RepositoryTestCase { } @Test - public void testFailureOnSignedTags() throws NoHeadException, - NoMessageException, UnmergedPathException, - ConcurrentRefUpdateException, JGitInternalException, - WrongRepositoryStateException, InvalidTagNameException { + public void testFailureOnSignedTags() throws GitAPIException { Git git = new Git(db); git.commit().setMessage("initial commit").call(); try { diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/DirCacheCheckoutMaliciousPathTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/DirCacheCheckoutMaliciousPathTest.java index 65d0418b33..fb9cc2cbfc 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/DirCacheCheckoutMaliciousPathTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/DirCacheCheckoutMaliciousPathTest.java @@ -46,14 +46,8 @@ import java.io.IOException; import java.util.Arrays; import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.CheckoutConflictException; -import org.eclipse.jgit.api.errors.InvalidRefNameException; -import org.eclipse.jgit.api.errors.JGitInternalException; -import org.eclipse.jgit.api.errors.RefAlreadyExistsException; -import org.eclipse.jgit.api.errors.RefNotFoundException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.dircache.InvalidPathException; -import org.eclipse.jgit.errors.IncorrectObjectTypeException; -import org.eclipse.jgit.errors.MissingObjectException; import org.eclipse.jgit.junit.MockSystemReader; import org.eclipse.jgit.revwalk.RevWalk; import org.eclipse.jgit.util.SystemReader; @@ -338,20 +332,11 @@ public class DirCacheCheckoutMaliciousPathTest extends RepositoryTestCase { * perform the actual test on the second checkout * @param path * to the blob, one or more levels + * @throws GitAPIException * @throws IOException - * @throws RefAlreadyExistsException - * @throws RefNotFoundException - * @throws InvalidRefNameException - * @throws MissingObjectException - * @throws IncorrectObjectTypeException - * @throws CheckoutConflictException - * @throws JGitInternalException */ - private void testMaliciousPath(boolean good, boolean secondCheckout, String... path) - throws IOException, RefAlreadyExistsException, - RefNotFoundException, InvalidRefNameException, - MissingObjectException, IncorrectObjectTypeException, - JGitInternalException, CheckoutConflictException { + private void testMaliciousPath(boolean good, boolean secondCheckout, + String... path) throws GitAPIException, IOException { Git git = new Git(db); ObjectInserter newObjectInserter; newObjectInserter = git.getRepository().newObjectInserter(); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/IndexDiffTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/IndexDiffTest.java index b7caecc2c2..dde32d7e9f 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/IndexDiffTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/IndexDiffTest.java @@ -59,7 +59,7 @@ import java.util.TreeSet; import org.eclipse.jgit.api.Git; import org.eclipse.jgit.api.MergeResult; import org.eclipse.jgit.api.MergeResult.MergeStatus; -import org.eclipse.jgit.api.errors.NoFilepatternException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEditor; import org.eclipse.jgit.dircache.DirCacheEditor.PathEdit; @@ -139,7 +139,7 @@ public class IndexDiffTest extends RepositoryTestCase { } @Test - public void testModified() throws IOException, NoFilepatternException { + public void testModified() throws IOException, GitAPIException { writeTrashFile("file2", "file2"); writeTrashFile("dir/file3", "dir/file3"); @@ -291,8 +291,7 @@ public class IndexDiffTest extends RepositoryTestCase { } @Test - public void testUnchangedSimple() throws IOException, - NoFilepatternException { + public void testUnchangedSimple() throws IOException, GitAPIException { writeTrashFile("a.b", "a.b"); writeTrashFile("a.c", "a.c"); writeTrashFile("a=c", "a=c"); @@ -328,11 +327,10 @@ public class IndexDiffTest extends RepositoryTestCase { * used by Git. * * @throws IOException - * @throws NoFilepatternException + * @throws GitAPIException */ @Test - public void testUnchangedComplex() throws IOException, - NoFilepatternException { + public void testUnchangedComplex() throws IOException, GitAPIException { Git git = new Git(db); writeTrashFile("a.b", "a.b"); writeTrashFile("a.c", "a.c"); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/PackWriterTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/PackWriterTest.java index b609b4766b..965a21ce05 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/PackWriterTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/PackWriterTest.java @@ -63,10 +63,14 @@ import java.util.Set; import org.eclipse.jgit.errors.MissingObjectException; import org.eclipse.jgit.junit.JGitTestUtil; +import org.eclipse.jgit.junit.TestRepository; +import org.eclipse.jgit.junit.TestRepository.BranchBuilder; import org.eclipse.jgit.lib.NullProgressMonitor; import org.eclipse.jgit.lib.ObjectId; import org.eclipse.jgit.lib.ObjectInserter; import org.eclipse.jgit.lib.SampleDataRepositoryTestCase; +import org.eclipse.jgit.revwalk.RevBlob; +import org.eclipse.jgit.revwalk.RevCommit; import org.eclipse.jgit.revwalk.RevObject; import org.eclipse.jgit.revwalk.RevWalk; import org.eclipse.jgit.storage.file.PackIndex.MutableEntry; @@ -447,6 +451,68 @@ public class PackWriterTest extends SampleDataRepositoryTestCase { } } + @Test + public void testExclude() throws Exception { + FileRepository repo = createBareRepository(); + + TestRepository<FileRepository> testRepo = new TestRepository<FileRepository>( + repo); + BranchBuilder bb = testRepo.branch("refs/heads/master"); + RevBlob contentA = testRepo.blob("A"); + RevCommit c1 = bb.commit().add("f", contentA).create(); + testRepo.getRevWalk().parseHeaders(c1); + PackIndex pf1 = writePack(repo, Collections.singleton(c1), + Collections.<PackIndex> emptySet()); + assertContent( + pf1, + Arrays.asList(c1.getId(), c1.getTree().getId(), + contentA.getId())); + RevBlob contentB = testRepo.blob("B"); + RevCommit c2 = bb.commit().add("f", contentB).create(); + testRepo.getRevWalk().parseHeaders(c2); + PackIndex pf2 = writePack(repo, Collections.singleton(c2), + Collections.singleton(pf1)); + assertContent( + pf2, + Arrays.asList(c2.getId(), c2.getTree().getId(), + contentB.getId())); + } + + private void assertContent(PackIndex pi, List<ObjectId> expected) { + assertEquals("Pack index has wrong size.", expected.size(), + pi.getObjectCount()); + for (int i = 0; i < pi.getObjectCount(); i++) + assertTrue( + "Pack index didn't contain the expected id " + + pi.getObjectId(i), + expected.contains(pi.getObjectId(i))); + } + + private PackIndex writePack(FileRepository repo, + Set<? extends ObjectId> want, Set<PackIndex> excludeObjects) + throws IOException { + PackWriter pw = new PackWriter(repo); + pw.setDeltaBaseAsOffset(true); + pw.setReuseDeltaCommits(false); + for (PackIndex idx : excludeObjects) + pw.excludeObjects(idx); + pw.preparePack(NullProgressMonitor.INSTANCE, want, + Collections.<ObjectId> emptySet()); + String id = pw.computeName().getName(); + File packdir = new File(repo.getObjectsDirectory(), "pack"); + File packFile = new File(packdir, "pack-" + id + ".pack"); + FileOutputStream packOS = new FileOutputStream(packFile); + pw.writePack(NullProgressMonitor.INSTANCE, + NullProgressMonitor.INSTANCE, packOS); + packOS.close(); + File idxFile = new File(packdir, "pack-" + id + ".idx"); + FileOutputStream idxOS = new FileOutputStream(idxFile); + pw.writeIndex(idxOS); + idxOS.close(); + pw.release(); + return PackIndex.open(idxFile); + } + // TODO: testWritePackDeltasCycle() // TODO: testWritePackDeltasDepth() diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/RefDirectoryTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/RefDirectoryTest.java index 3ca4f589db..508b690509 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/RefDirectoryTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/storage/file/RefDirectoryTest.java @@ -60,6 +60,8 @@ import static org.junit.Assert.fail; import java.io.File; import java.io.IOException; import java.util.Map; +import java.util.concurrent.atomic.AtomicInteger; +import java.util.concurrent.atomic.AtomicReference; import org.eclipse.jgit.events.ListenerHandle; import org.eclipse.jgit.events.RefsChangedEvent; @@ -1077,6 +1079,36 @@ public class RefDirectoryTest extends LocalDiskRepositoryTestCase { assertSame(master_p2, refdir.peel(master_p2)); } + @Test + public void testRefsChangedStackOverflow() throws Exception { + final FileRepository newRepo = createBareRepository(); + final RefDatabase refDb = newRepo.getRefDatabase(); + File packedRefs = new File(newRepo.getDirectory(), "packed-refs"); + assertTrue(packedRefs.createNewFile()); + final AtomicReference<StackOverflowError> error = new AtomicReference<StackOverflowError>(); + final AtomicReference<IOException> exception = new AtomicReference<IOException>(); + final AtomicInteger changeCount = new AtomicInteger(); + newRepo.getListenerList().addRefsChangedListener( + new RefsChangedListener() { + + public void onRefsChanged(RefsChangedEvent event) { + try { + refDb.getRefs("ref"); + changeCount.incrementAndGet(); + } catch (StackOverflowError soe) { + error.set(soe); + } catch (IOException ioe) { + exception.set(ioe); + } + } + }); + refDb.getRefs("ref"); + refDb.getRefs("ref"); + assertNull(error.get()); + assertNull(exception.get()); + assertEquals(1, changeCount.get()); + } + private void writeLooseRef(String name, AnyObjectId id) throws IOException { writeLooseRef(name, id.name() + "\n"); } diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleAddTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleAddTest.java index 568cd9e2bc..940a78ac4f 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleAddTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleAddTest.java @@ -53,6 +53,7 @@ import java.text.MessageFormat; import org.eclipse.jgit.api.Git; import org.eclipse.jgit.api.Status; import org.eclipse.jgit.api.SubmoduleAddCommand; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEditor; @@ -75,7 +76,7 @@ import org.junit.Test; public class SubmoduleAddTest extends RepositoryTestCase { @Test - public void commandWithNullPath() { + public void commandWithNullPath() throws GitAPIException { try { new SubmoduleAddCommand(db).setURI("uri").call(); fail("Exception not thrown"); @@ -85,7 +86,7 @@ public class SubmoduleAddTest extends RepositoryTestCase { } @Test - public void commandWithEmptyPath() { + public void commandWithEmptyPath() throws GitAPIException { try { new SubmoduleAddCommand(db).setPath("").setURI("uri").call(); fail("Exception not thrown"); @@ -95,7 +96,7 @@ public class SubmoduleAddTest extends RepositoryTestCase { } @Test - public void commandWithNullUri() { + public void commandWithNullUri() throws GitAPIException { try { new SubmoduleAddCommand(db).setPath("sub").call(); fail("Exception not thrown"); @@ -105,7 +106,7 @@ public class SubmoduleAddTest extends RepositoryTestCase { } @Test - public void commandWithEmptyUri() { + public void commandWithEmptyUri() throws GitAPIException { try { new SubmoduleAddCommand(db).setPath("sub").setURI("").call(); fail("Exception not thrown"); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleInitTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleInitTest.java index f0a0750c5c..424ad01fcb 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleInitTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleInitTest.java @@ -53,6 +53,7 @@ import java.io.IOException; import java.util.Collection; import org.eclipse.jgit.api.SubmoduleInitCommand; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEditor; @@ -73,7 +74,7 @@ import org.junit.Test; public class SubmoduleInitTest extends RepositoryTestCase { @Test - public void repositoryWithNoSubmodules() { + public void repositoryWithNoSubmodules() throws GitAPIException { SubmoduleInitCommand command = new SubmoduleInitCommand(db); Collection<String> modules = command.call(); assertNotNull(modules); @@ -82,7 +83,7 @@ public class SubmoduleInitTest extends RepositoryTestCase { @Test public void repositoryWithUninitializedModule() throws IOException, - ConfigInvalidException { + ConfigInvalidException, GitAPIException { final String path = addSubmoduleToIndex(); SubmoduleWalk generator = SubmoduleWalk.forIndex(db); @@ -156,7 +157,7 @@ public class SubmoduleInitTest extends RepositoryTestCase { @Test public void resolveOneLevelHigherRelativeUrl() throws IOException, - ConfigInvalidException { + ConfigInvalidException, GitAPIException { final String path = addSubmoduleToIndex(); String base = "git://server/repo.git"; @@ -197,7 +198,7 @@ public class SubmoduleInitTest extends RepositoryTestCase { @Test public void resolveTwoLevelHigherRelativeUrl() throws IOException, - ConfigInvalidException { + ConfigInvalidException, GitAPIException { final String path = addSubmoduleToIndex(); String base = "git://server/repo.git"; @@ -238,7 +239,7 @@ public class SubmoduleInitTest extends RepositoryTestCase { @Test public void resolveWorkingDirectoryRelativeUrl() throws IOException, - ConfigInvalidException { + GitAPIException, ConfigInvalidException { final String path = addSubmoduleToIndex(); String base = db.getWorkTree().getAbsolutePath(); @@ -281,7 +282,7 @@ public class SubmoduleInitTest extends RepositoryTestCase { @Test public void resolveInvalidParentUrl() throws IOException, - ConfigInvalidException { + ConfigInvalidException, GitAPIException { final String path = addSubmoduleToIndex(); String base = "no_slash"; diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleStatusTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleStatusTest.java index dc79d84259..6feefdb2d1 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleStatusTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleStatusTest.java @@ -53,6 +53,7 @@ import java.util.Map.Entry; import org.eclipse.jgit.api.Git; import org.eclipse.jgit.api.SubmoduleStatusCommand; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEditor; import org.eclipse.jgit.dircache.DirCacheEditor.PathEdit; @@ -74,7 +75,7 @@ import org.junit.Test; public class SubmoduleStatusTest extends RepositoryTestCase { @Test - public void repositoryWithNoSubmodules() { + public void repositoryWithNoSubmodules() throws GitAPIException { SubmoduleStatusCommand command = new SubmoduleStatusCommand(db); Map<String, SubmoduleStatus> statuses = command.call(); assertNotNull(statuses); @@ -82,7 +83,8 @@ public class SubmoduleStatusTest extends RepositoryTestCase { } @Test - public void repositoryWithMissingSubmodule() throws IOException { + public void repositoryWithMissingSubmodule() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; @@ -113,7 +115,8 @@ public class SubmoduleStatusTest extends RepositoryTestCase { } @Test - public void repositoryWithUninitializedSubmodule() throws IOException { + public void repositoryWithUninitializedSubmodule() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; @@ -152,7 +155,8 @@ public class SubmoduleStatusTest extends RepositoryTestCase { } @Test - public void repositoryWithNoHeadInSubmodule() throws IOException { + public void repositoryWithNoHeadInSubmodule() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; @@ -202,7 +206,8 @@ public class SubmoduleStatusTest extends RepositoryTestCase { } @Test - public void repositoryWithNoSubmoduleRepository() throws IOException { + public void repositoryWithNoSubmoduleRepository() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; @@ -247,7 +252,8 @@ public class SubmoduleStatusTest extends RepositoryTestCase { } @Test - public void repositoryWithInitializedSubmodule() throws IOException { + public void repositoryWithInitializedSubmodule() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; @@ -302,7 +308,7 @@ public class SubmoduleStatusTest extends RepositoryTestCase { @Test public void repositoryWithDifferentRevCheckedOutSubmodule() - throws IOException { + throws IOException, GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleSyncTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleSyncTest.java index 4df9077ba0..3f9ad11f1d 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleSyncTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleSyncTest.java @@ -53,6 +53,7 @@ import java.util.Map.Entry; import org.eclipse.jgit.api.Git; import org.eclipse.jgit.api.SubmoduleSyncCommand; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEditor; import org.eclipse.jgit.dircache.DirCacheEditor.PathEdit; @@ -73,7 +74,7 @@ import org.junit.Test; public class SubmoduleSyncTest extends RepositoryTestCase { @Test - public void repositoryWithNoSubmodules() { + public void repositoryWithNoSubmodules() throws GitAPIException { SubmoduleSyncCommand command = new SubmoduleSyncCommand(db); Map<String, String> modules = command.call(); assertNotNull(modules); diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleUpdateTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleUpdateTest.java index 9bb4a63aab..eb0cf2b0b6 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleUpdateTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/submodule/SubmoduleUpdateTest.java @@ -52,6 +52,7 @@ import java.util.Collection; import org.eclipse.jgit.api.Git; import org.eclipse.jgit.api.SubmoduleUpdateCommand; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheEditor; import org.eclipse.jgit.dircache.DirCacheEditor.PathEdit; @@ -73,7 +74,7 @@ import org.junit.Test; public class SubmoduleUpdateTest extends RepositoryTestCase { @Test - public void repositoryWithNoSubmodules() { + public void repositoryWithNoSubmodules() throws GitAPIException { SubmoduleUpdateCommand command = new SubmoduleUpdateCommand(db); Collection<String> modules = command.call(); assertNotNull(modules); @@ -125,7 +126,8 @@ public class SubmoduleUpdateTest extends RepositoryTestCase { } @Test - public void repositoryWithUnconfiguredSubmodule() throws IOException { + public void repositoryWithUnconfiguredSubmodule() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; @@ -159,7 +161,8 @@ public class SubmoduleUpdateTest extends RepositoryTestCase { } @Test - public void repositoryWithInitializedSubmodule() throws IOException { + public void repositoryWithInitializedSubmodule() throws IOException, + GitAPIException { final ObjectId id = ObjectId .fromString("abcd1234abcd1234abcd1234abcd1234abcd1234"); final String path = "sub"; diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java index 3da9640b49..f89f3e480c 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java @@ -48,6 +48,7 @@ import java.io.InputStream; import java.util.Collection; import java.util.LinkedList; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoFilepatternException; import org.eclipse.jgit.dircache.DirCache; @@ -122,7 +123,7 @@ public class AddCommand extends GitCommand<DirCache> { * * @return the DirCache after Add */ - public DirCache call() throws NoFilepatternException { + public DirCache call() throws GitAPIException, NoFilepatternException { if (filepatterns.isEmpty()) throw new NoFilepatternException(JGitText.get().atLeastOnePatternIsRequired); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/AddNoteCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/AddNoteCommand.java index d1c75e2ca1..3af86959da 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/AddNoteCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/AddNoteCommand.java @@ -44,6 +44,7 @@ package org.eclipse.jgit.api; import java.io.IOException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.CommitBuilder; import org.eclipse.jgit.lib.Constants; @@ -80,11 +81,7 @@ public class AddNoteCommand extends GitCommand<Note> { super(repo); } - /** - * @throws JGitInternalException - * upon internal failure - */ - public Note call() throws JGitInternalException { + public Note call() throws GitAPIException { checkCallable(); RevWalk walk = new RevWalk(repo); ObjectInserter inserter = repo.newObjectInserter(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/BlameCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/BlameCommand.java index 400d94bc88..12be64bb02 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/BlameCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/BlameCommand.java @@ -48,6 +48,7 @@ import java.util.ArrayList; import java.util.Collection; import java.util.Collections; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.blame.BlameGenerator; import org.eclipse.jgit.blame.BlameResult; @@ -189,7 +190,7 @@ public class BlameCommand extends GitCommand<BlameResult> { * * @return list of lines */ - public BlameResult call() throws JGitInternalException { + public BlameResult call() throws GitAPIException { checkCallable(); BlameGenerator gen = new BlameGenerator(repo, path); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/CheckoutCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/CheckoutCommand.java index e6d56c8e6f..03df65d8a7 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/CheckoutCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/CheckoutCommand.java @@ -51,6 +51,7 @@ import java.util.List; import org.eclipse.jgit.api.CheckoutResult.Status; import org.eclipse.jgit.api.errors.CheckoutConflictException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRefNameException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.RefAlreadyExistsException; @@ -121,9 +122,11 @@ public class CheckoutCommand extends GitCommand<Ref> { * @throws InvalidRefNameException * if the provided name is <code>null</code> or otherwise * invalid + * @throws CheckoutConflictException + * if the checkout results in a conflict * @return the newly created branch */ - public Ref call() throws JGitInternalException, RefAlreadyExistsException, + public Ref call() throws GitAPIException, RefAlreadyExistsException, RefNotFoundException, InvalidRefNameException, CheckoutConflictException { checkCallable(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/CleanCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/CleanCommand.java index e31f119cb2..341be91da6 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/CleanCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/CleanCommand.java @@ -49,6 +49,7 @@ import java.util.Collections; import java.util.Set; import java.util.TreeSet; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.util.FileUtils; @@ -81,7 +82,7 @@ public class CleanCommand extends GitCommand<Set<String>> { * * @return a set of strings representing each file cleaned. */ - public Set<String> call() { + public Set<String> call() throws GitAPIException { Set<String> files = new TreeSet<String>(); try { StatusCommand command = new StatusCommand(repo); @@ -113,7 +114,7 @@ public class CleanCommand extends GitCommand<Set<String>> { /** * If dryRun is set, the paths in question will not actually be deleted. - * + * * @param dryRun * whether to do a dry run or not * @return {@code this} diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/CloneCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/CloneCommand.java index f354de1657..23bbc2aa9c 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/CloneCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/CloneCommand.java @@ -50,6 +50,7 @@ import java.util.ArrayList; import java.util.Collection; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRemoteException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.dircache.DirCache; @@ -111,11 +112,9 @@ public class CloneCommand extends TransportCommand<CloneCommand, Git> { /** * Executes the {@code Clone} command. * - * @throws JGitInternalException - * if the repository can't be created * @return the newly created {@code Git} object with associated repository */ - public Git call() throws JGitInternalException { + public Git call() throws GitAPIException { try { URIish u = new URIish(uri); Repository repository = init(u); @@ -132,7 +131,7 @@ public class CloneCommand extends TransportCommand<CloneCommand, Git> { } } - private Repository init(URIish u) { + private Repository init(URIish u) throws GitAPIException { InitCommand command = Git.init(); command.setBare(bare); if (directory == null) @@ -145,9 +144,7 @@ public class CloneCommand extends TransportCommand<CloneCommand, Git> { } private FetchResult fetch(Repository clonedRepo, URIish u) - throws URISyntaxException, - JGitInternalException, - InvalidRemoteException, IOException { + throws URISyntaxException, IOException, GitAPIException { // create the remote config and save it RemoteConfig config = new RemoteConfig(clonedRepo.getConfig(), remote); config.addURI(u); @@ -193,8 +190,8 @@ public class CloneCommand extends TransportCommand<CloneCommand, Git> { } private void checkout(Repository clonedRepo, FetchResult result) - throws JGitInternalException, - MissingObjectException, IncorrectObjectTypeException, IOException { + throws MissingObjectException, IncorrectObjectTypeException, + IOException, GitAPIException { Ref head = result.getAdvertisedRef(branch); if (branch.equals(Constants.HEAD)) { @@ -230,7 +227,8 @@ public class CloneCommand extends TransportCommand<CloneCommand, Git> { } } - private void cloneSubmodules(Repository clonedRepo) throws IOException { + private void cloneSubmodules(Repository clonedRepo) throws IOException, + GitAPIException { SubmoduleInitCommand init = new SubmoduleInitCommand(clonedRepo); if (init.call().isEmpty()) return; diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/CommitCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/CommitCommand.java index 242d11efaa..eac6fe6a40 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/CommitCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/CommitCommand.java @@ -50,10 +50,12 @@ import java.util.LinkedList; import java.util.List; import org.eclipse.jgit.api.errors.ConcurrentRefUpdateException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoFilepatternException; import org.eclipse.jgit.api.errors.NoHeadException; import org.eclipse.jgit.api.errors.NoMessageException; +import org.eclipse.jgit.api.errors.UnmergedPathsException; import org.eclipse.jgit.api.errors.WrongRepositoryStateException; import org.eclipse.jgit.dircache.DirCache; import org.eclipse.jgit.dircache.DirCacheBuilder; @@ -134,21 +136,18 @@ public class CommitCommand extends GitCommand<RevCommit> { * when called on a git repo without a HEAD reference * @throws NoMessageException * when called without specifying a commit message - * @throws UnmergedPathException + * @throws UnmergedPathsException * when the current index contained unmerged paths (conflicts) + * @throws ConcurrentRefUpdateException + * when HEAD or branch ref is updated concurrently by someone + * else * @throws WrongRepositoryStateException * when repository is not in the right state for committing - * @throws JGitInternalException - * a low-level exception of JGit has occurred. The original - * exception can be retrieved by calling - * {@link Exception#getCause()}. Expect only - * {@code IOException's} to be wrapped. Subclasses of - * {@link IOException} (e.g. {@link UnmergedPathException}) are - * typically not wrapped here but thrown as original exception */ - public RevCommit call() throws NoHeadException, NoMessageException, - UnmergedPathException, ConcurrentRefUpdateException, - JGitInternalException, WrongRepositoryStateException { + public RevCommit call() throws GitAPIException, NoHeadException, + NoMessageException, UnmergedPathsException, + ConcurrentRefUpdateException, + WrongRepositoryStateException { checkCallable(); RepositoryState state = repo.getRepositoryState(); @@ -269,10 +268,7 @@ public class CommitCommand extends GitCommand<RevCommit> { index.unlock(); } } catch (UnmergedPathException e) { - // since UnmergedPathException is a subclass of IOException - // which should not be wrapped by a JGitInternalException we - // have to catch and re-throw it here - throw e; + throw new UnmergedPathsException(e); } catch (IOException e) { throw new JGitInternalException( JGitText.get().exceptionCaughtDuringExecutionOfCommitCommand, e); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/CreateBranchCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/CreateBranchCommand.java index 7ef1f2e134..4fb3c174cd 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/CreateBranchCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/CreateBranchCommand.java @@ -46,6 +46,7 @@ package org.eclipse.jgit.api; import java.io.IOException; import java.text.MessageFormat; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRefNameException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.RefAlreadyExistsException; @@ -57,9 +58,9 @@ import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.ObjectId; import org.eclipse.jgit.lib.Ref; import org.eclipse.jgit.lib.RefUpdate; +import org.eclipse.jgit.lib.RefUpdate.Result; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.StoredConfig; -import org.eclipse.jgit.lib.RefUpdate.Result; import org.eclipse.jgit.revwalk.RevCommit; import org.eclipse.jgit.revwalk.RevWalk; @@ -119,7 +120,7 @@ public class CreateBranchCommand extends GitCommand<Ref> { * invalid * @return the newly created branch */ - public Ref call() throws JGitInternalException, RefAlreadyExistsException, + public Ref call() throws GitAPIException, RefAlreadyExistsException, RefNotFoundException, InvalidRefNameException { checkCallable(); processOptions(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteBranchCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteBranchCommand.java index fe629f30a2..0d03162543 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteBranchCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteBranchCommand.java @@ -51,6 +51,7 @@ import java.util.List; import java.util.Set; import org.eclipse.jgit.api.errors.CannotDeleteCurrentBranchException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NotMergedException; import org.eclipse.jgit.internal.JGitText; @@ -58,9 +59,9 @@ import org.eclipse.jgit.lib.ConfigConstants; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Ref; import org.eclipse.jgit.lib.RefUpdate; +import org.eclipse.jgit.lib.RefUpdate.Result; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.StoredConfig; -import org.eclipse.jgit.lib.RefUpdate.Result; import org.eclipse.jgit.revwalk.RevCommit; import org.eclipse.jgit.revwalk.RevWalk; @@ -93,9 +94,10 @@ public class DeleteBranchCommand extends GitCommand<List<String>> { * @throws NotMergedException * when trying to delete a branch which has not been merged into * the currently checked out branch without force + * @throws CannotDeleteCurrentBranchException * @return the list with the (full) names of the deleted branches */ - public List<String> call() throws JGitInternalException, + public List<String> call() throws GitAPIException, NotMergedException, CannotDeleteCurrentBranchException { checkCallable(); List<String> result = new ArrayList<String>(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteTagCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteTagCommand.java index bd4c8eca38..ae511c6df0 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteTagCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/DeleteTagCommand.java @@ -49,6 +49,7 @@ import java.util.HashSet; import java.util.List; import java.util.Set; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.internal.JGitText; import org.eclipse.jgit.lib.Ref; @@ -77,12 +78,9 @@ public class DeleteTagCommand extends GitCommand<List<String>> { } /** - * @throws JGitInternalException - * when trying to delete a tag that doesn't exist - * * @return the list with the full names of the deleted tags */ - public List<String> call() throws JGitInternalException { + public List<String> call() throws GitAPIException { checkCallable(); List<String> result = new ArrayList<String>(); if (tags.isEmpty()) diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/DiffCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/DiffCommand.java index e82b0486a6..9b4476d628 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/DiffCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/DiffCommand.java @@ -50,6 +50,7 @@ import java.io.OutputStream; import java.util.List; import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoHeadException; import org.eclipse.jgit.diff.DiffEntry; import org.eclipse.jgit.diff.DiffFormatter; @@ -108,7 +109,7 @@ public class DiffCommand extends GitCommand<List<DiffEntry>> { * * @return a DiffEntry for each path which is different */ - public List<DiffEntry> call() throws GitAPIException, IOException { + public List<DiffEntry> call() throws GitAPIException { final DiffFormatter diffFmt; if (out != null && !showNameAndStatusOnly) diffFmt = new DiffFormatter(new BufferedOutputStream(out)); @@ -155,6 +156,8 @@ public class DiffCommand extends GitCommand<List<DiffEntry>> { diffFmt.flush(); return result; } + } catch (IOException e) { + throw new JGitInternalException(e.getMessage(), e); } finally { diffFmt.release(); } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/FetchCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/FetchCommand.java index 181c4c458c..6df244bcc3 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/FetchCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/FetchCommand.java @@ -47,6 +47,7 @@ import java.text.MessageFormat; import java.util.ArrayList; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRemoteException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.NoRemoteRepositoryException; @@ -106,13 +107,11 @@ public class FetchCommand extends TransportCommand<FetchCommand, FetchResult> { * result * @throws InvalidRemoteException * when called with an invalid remote uri - * @throws JGitInternalException - * a low-level exception of JGit has occurred. The original - * exception can be retrieved by calling - * {@link Exception#getCause()}. + * @throws org.eclipse.jgit.api.errors.TransportException + * when an error occurs during transport */ - public FetchResult call() throws JGitInternalException, - InvalidRemoteException { + public FetchResult call() throws GitAPIException, InvalidRemoteException, + org.eclipse.jgit.api.errors.TransportException { checkCallable(); try { @@ -135,7 +134,7 @@ public class FetchCommand extends TransportCommand<FetchCommand, FetchResult> { throw new InvalidRemoteException(MessageFormat.format( JGitText.get().invalidRemote, remote), e); } catch (TransportException e) { - throw new JGitInternalException( + throw new org.eclipse.jgit.api.errors.TransportException( JGitText.get().exceptionCaughtDuringExecutionOfFetchCommand, e); } catch (URISyntaxException e) { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/GitCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/GitCommand.java index 83e7cfd989..329b1b5aea 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/GitCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/GitCommand.java @@ -40,6 +40,7 @@ package org.eclipse.jgit.api; import java.text.MessageFormat; import java.util.concurrent.Callable; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.internal.JGitText; import org.eclipse.jgit.lib.Repository; @@ -116,4 +117,13 @@ public abstract class GitCommand<T> implements Callable<T> { JGitText.get().commandWasCalledInTheWrongState , this.getClass().getName())); } + + /** + * Executes the command + * + * @return T a result. Each command has its own return type + * @throws GitAPIException + * or subclass thereof when an error occurs + */ + public abstract T call() throws GitAPIException; } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/InitCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/InitCommand.java index 77fc3042c5..8777be5546 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/InitCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/InitCommand.java @@ -46,6 +46,7 @@ import java.io.File; import java.io.IOException; import java.util.concurrent.Callable; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Repository; @@ -65,11 +66,9 @@ public class InitCommand implements Callable<Git> { /** * Executes the {@code Init} command. * - * @throws JGitInternalException - * if the repository can't be created * @return the newly created {@code Git} object with associated repository */ - public Git call() throws JGitInternalException { + public Git call() throws GitAPIException { try { RepositoryBuilder builder = new RepositoryBuilder(); if (bare) diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/ListBranchCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/ListBranchCommand.java index 846c5385c5..ea6f34b414 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/ListBranchCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/ListBranchCommand.java @@ -47,10 +47,11 @@ import java.io.IOException; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; +import java.util.HashMap; import java.util.List; import java.util.Map; -import java.util.HashMap; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Ref; @@ -88,11 +89,7 @@ public class ListBranchCommand extends GitCommand<List<Ref>> { super(repo); } - /** - * @throws JGitInternalException - * upon internal failure - */ - public List<Ref> call() throws JGitInternalException { + public List<Ref> call() throws GitAPIException { checkCallable(); Map<String, Ref> refList; try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/ListNotesCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/ListNotesCommand.java index 92f883a02e..84fa355af5 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/ListNotesCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/ListNotesCommand.java @@ -47,6 +47,7 @@ import java.util.ArrayList; import java.util.Iterator; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Ref; @@ -74,10 +75,9 @@ public class ListNotesCommand extends GitCommand<List<Note>> { } /** - * @throws JGitInternalException - * upon internal failure + * @return the requested notes */ - public List<Note> call() throws JGitInternalException { + public List<Note> call() throws GitAPIException { checkCallable(); List<Note> notes = new ArrayList<Note>(); RevWalk walk = new RevWalk(repo); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/ListTagCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/ListTagCommand.java index c1ae88731f..a0a5d950ca 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/ListTagCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/ListTagCommand.java @@ -49,6 +49,7 @@ import java.util.Comparator; import java.util.List; import java.util.Map; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Ref; @@ -71,11 +72,9 @@ public class ListTagCommand extends GitCommand<List<Ref>> { } /** - * @throws JGitInternalException - * upon internal failure * @return the tags available */ - public List<Ref> call() throws JGitInternalException { + public List<Ref> call() throws GitAPIException { checkCallable(); Map<String, Ref> refList; List<Ref> tags = new ArrayList<Ref>(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/LogCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/LogCommand.java index 04a87b092a..6d4b3474ef 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/LogCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/LogCommand.java @@ -47,6 +47,7 @@ import java.text.MessageFormat; import java.util.ArrayList; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoHeadException; import org.eclipse.jgit.errors.IncorrectObjectTypeException; @@ -108,9 +109,10 @@ public class LogCommand extends GitCommand<Iterable<RevCommit>> { * method twice on an instance. * * @return an iteration over RevCommits + * @throws NoHeadException + * of the references ref cannot be resolved */ - public Iterable<RevCommit> call() throws NoHeadException, - JGitInternalException { + public Iterable<RevCommit> call() throws GitAPIException, NoHeadException { checkCallable(); if (pathFilters.size() > 0) walk.setTreeFilter(AndTreeFilter.create( @@ -166,7 +168,7 @@ public class LogCommand extends GitCommand<Iterable<RevCommit>> { * typically not wrapped here but thrown as original exception */ public LogCommand add(AnyObjectId start) throws MissingObjectException, - IncorrectObjectTypeException, JGitInternalException { + IncorrectObjectTypeException { return add(true, start); } @@ -194,7 +196,7 @@ public class LogCommand extends GitCommand<Iterable<RevCommit>> { * typically not wrapped here but thrown as original exception */ public LogCommand not(AnyObjectId start) throws MissingObjectException, - IncorrectObjectTypeException, JGitInternalException { + IncorrectObjectTypeException { return add(false, start); } @@ -223,8 +225,7 @@ public class LogCommand extends GitCommand<Iterable<RevCommit>> { * typically not wrapped here but thrown as original exception */ public LogCommand addRange(AnyObjectId since, AnyObjectId until) - throws MissingObjectException, IncorrectObjectTypeException, - JGitInternalException { + throws MissingObjectException, IncorrectObjectTypeException { return not(since).add(until); } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/LsRemoteCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/LsRemoteCommand.java index 947b3f5929..b041f33c4c 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/LsRemoteCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/LsRemoteCommand.java @@ -144,13 +144,11 @@ public class LsRemoteCommand extends * @return a collection of references in the remote repository * @throws InvalidRemoteException * when called with an invalid remote uri - * @throws JGitInternalException - * a low-level exception of JGit has occurred. The original - * exception can be retrieved by calling - * {@link Exception#getCause()}. + * @throws org.eclipse.jgit.api.errors.TransportException + * for errors that occurs during transport */ public Collection<Ref> call() throws GitAPIException, - JGitInternalException { + org.eclipse.jgit.api.errors.TransportException { checkCallable(); Transport transport = null; diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/MergeCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/MergeCommand.java index 05743e6c21..c5a9552112 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/MergeCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/MergeCommand.java @@ -54,6 +54,7 @@ import java.util.Map; import org.eclipse.jgit.api.MergeResult.MergeStatus; import org.eclipse.jgit.api.errors.CheckoutConflictException; import org.eclipse.jgit.api.errors.ConcurrentRefUpdateException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidMergeHeadsException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoHeadException; @@ -109,7 +110,7 @@ public class MergeCommand extends GitCommand<MergeResult> { * * @return the result of the merge */ - public MergeResult call() throws NoHeadException, + public MergeResult call() throws GitAPIException, NoHeadException, ConcurrentRefUpdateException, CheckoutConflictException, InvalidMergeHeadsException, WrongRepositoryStateException, NoMessageException { checkCallable(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/PullCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/PullCommand.java index 3a85f1093e..86d38fb36c 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/PullCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/PullCommand.java @@ -110,7 +110,7 @@ public class PullCommand extends TransportCommand<PullCommand, PullResult> { * * @return the result of the pull */ - public PullResult call() throws WrongRepositoryStateException, + public PullResult call() throws GitAPIException, WrongRepositoryStateException, InvalidConfigurationException, DetachedHeadException, InvalidRemoteException, CanceledException, RefNotFoundException, NoHeadException { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/PushCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/PushCommand.java index e7f0b06a96..edfb2f7b75 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/PushCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/PushCommand.java @@ -50,6 +50,7 @@ import java.util.Collection; import java.util.Collections; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRemoteException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.NotSupportedException; @@ -108,12 +109,8 @@ public class PushCommand extends * @return an iteration over {@link PushResult} objects * @throws InvalidRemoteException * when called with an invalid remote uri - * @throws JGitInternalException - * a low-level exception of JGit has occurred. The original - * exception can be retrieved by calling - * {@link Exception#getCause()}. */ - public Iterable<PushResult> call() throws JGitInternalException, + public Iterable<PushResult> call() throws GitAPIException, InvalidRemoteException { checkCallable(); @@ -325,7 +322,7 @@ public class PushCommand extends * @throws JGitInternalException * the reference name cannot be resolved. */ - public PushCommand add(String nameOrSpec) throws JGitInternalException { + public PushCommand add(String nameOrSpec) { if (0 <= nameOrSpec.indexOf(':')) { refSpecs.add(new RefSpec(nameOrSpec)); } else { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/RebaseCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/RebaseCommand.java index aa6572600c..ecf85932e9 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/RebaseCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/RebaseCommand.java @@ -190,8 +190,8 @@ public class RebaseCommand extends GitCommand<RebaseResult> { * * @return an object describing the result of this command */ - public RebaseResult call() throws NoHeadException, RefNotFoundException, - JGitInternalException, GitAPIException { + public RebaseResult call() throws GitAPIException, NoHeadException, + RefNotFoundException { RevCommit newHead = null; boolean lastStepWasForward = false; checkCallable(); @@ -325,8 +325,7 @@ public class RebaseCommand extends GitCommand<RebaseResult> { } } - private RevCommit checkoutCurrentHead() throws IOException, - NoHeadException, JGitInternalException { + private RevCommit checkoutCurrentHead() throws IOException, NoHeadException { ObjectId headTree = repo.resolve(Constants.HEAD + "^{tree}"); if (headTree == null) throw new NoHeadException( @@ -517,8 +516,8 @@ public class RebaseCommand extends GitCommand<RebaseResult> { } } - private RebaseResult initFilesAndRewind() throws RefNotFoundException, - IOException, NoHeadException, JGitInternalException { + private RebaseResult initFilesAndRewind() throws IOException, + GitAPIException { // we need to store everything into files so that we can implement // --skip, --continue, and --abort @@ -576,7 +575,7 @@ public class RebaseCommand extends GitCommand<RebaseResult> { // create the folder for the meta information FileUtils.mkdir(rebaseDir); - createFile(repo.getDirectory(), Constants.ORIG_HEAD, headId.name()); + repo.writeOrigHead(headId); createFile(rebaseDir, REBASE_HEAD, headId.name()); createFile(rebaseDir, HEAD_NAME, headName); createFile(rebaseDir, ONTO, upstreamCommit.name()); @@ -626,11 +625,11 @@ public class RebaseCommand extends GitCommand<RebaseResult> { * * @param newCommit * @return the new head, or null - * @throws RefNotFoundException * @throws IOException + * @throws GitAPIException */ - public RevCommit tryFastForward(RevCommit newCommit) - throws RefNotFoundException, IOException { + public RevCommit tryFastForward(RevCommit newCommit) throws IOException, + GitAPIException { Ref head = repo.getRef(Constants.HEAD); if (head == null || head.getObjectId() == null) throw new RefNotFoundException(MessageFormat.format( @@ -653,7 +652,7 @@ public class RebaseCommand extends GitCommand<RebaseResult> { } private RevCommit tryFastForward(String headName, RevCommit oldCommit, - RevCommit newCommit) throws IOException, JGitInternalException { + RevCommit newCommit) throws IOException, GitAPIException { boolean tryRebase = false; for (RevCommit parentCommit : newCommit.getParents()) if (parentCommit.equals(oldCommit)) @@ -733,7 +732,8 @@ public class RebaseCommand extends GitCommand<RebaseResult> { private RebaseResult abort(RebaseResult result) throws IOException { try { - String commitId = readFile(repo.getDirectory(), Constants.ORIG_HEAD); + ObjectId origHead = repo.readOrigHead(); + String commitId = origHead != null ? origHead.name() : null; monitor.beginTask(MessageFormat.format( JGitText.get().abortingRebase, commitId), ProgressMonitor.UNKNOWN); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/ReflogCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/ReflogCommand.java index 10757a845c..c4d112a319 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/ReflogCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/ReflogCommand.java @@ -46,6 +46,7 @@ import java.io.IOException; import java.text.MessageFormat; import java.util.Collection; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRefNameException; import org.eclipse.jgit.internal.JGitText; import org.eclipse.jgit.lib.Constants; @@ -84,7 +85,7 @@ public class ReflogCommand extends GitCommand<Collection<ReflogEntry>> { return this; } - public Collection<ReflogEntry> call() throws Exception { + public Collection<ReflogEntry> call() throws GitAPIException { checkCallable(); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/RemoveNoteCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/RemoveNoteCommand.java index 5b9075e436..d1e2770931 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/RemoveNoteCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/RemoveNoteCommand.java @@ -44,6 +44,7 @@ package org.eclipse.jgit.api; import java.io.IOException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.CommitBuilder; import org.eclipse.jgit.lib.Constants; @@ -78,11 +79,7 @@ public class RemoveNoteCommand extends GitCommand<Note> { super(repo); } - /** - * @throws JGitInternalException - * upon internal failure - */ - public Note call() throws JGitInternalException { + public Note call() throws GitAPIException { checkCallable(); RevWalk walk = new RevWalk(repo); ObjectInserter inserter = repo.newObjectInserter(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/RenameBranchCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/RenameBranchCommand.java index f5dfa2b111..f9cb828d8e 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/RenameBranchCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/RenameBranchCommand.java @@ -48,6 +48,7 @@ import java.text.MessageFormat; import java.util.Arrays; import org.eclipse.jgit.api.errors.DetachedHeadException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRefNameException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.RefAlreadyExistsException; @@ -58,9 +59,9 @@ import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.ObjectId; import org.eclipse.jgit.lib.Ref; import org.eclipse.jgit.lib.RefRename; +import org.eclipse.jgit.lib.RefUpdate.Result; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.StoredConfig; -import org.eclipse.jgit.lib.RefUpdate.Result; /** * Used to rename branches. @@ -94,7 +95,7 @@ public class RenameBranchCommand extends GitCommand<Ref> { * if rename is tried without specifying the old name and HEAD * is detached */ - public Ref call() throws RefNotFoundException, InvalidRefNameException, + public Ref call() throws GitAPIException, RefNotFoundException, InvalidRefNameException, RefAlreadyExistsException, DetachedHeadException { checkCallable(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/ResetCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/ResetCommand.java index 422056bd6d..a6d425ea31 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/ResetCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/ResetCommand.java @@ -47,11 +47,13 @@ import java.text.MessageFormat; import java.util.Collection; import java.util.LinkedList; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.dircache.DirCache; -import org.eclipse.jgit.dircache.DirCacheBuilder; import org.eclipse.jgit.dircache.DirCacheCheckout; import org.eclipse.jgit.dircache.DirCacheEditor; +import org.eclipse.jgit.dircache.DirCacheEditor.DeletePath; +import org.eclipse.jgit.dircache.DirCacheEditor.PathEdit; import org.eclipse.jgit.dircache.DirCacheEntry; import org.eclipse.jgit.dircache.DirCacheIterator; import org.eclipse.jgit.internal.JGitText; @@ -64,6 +66,7 @@ import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.lib.RepositoryState; import org.eclipse.jgit.revwalk.RevCommit; import org.eclipse.jgit.revwalk.RevWalk; +import org.eclipse.jgit.treewalk.AbstractTreeIterator; import org.eclipse.jgit.treewalk.CanonicalTreeParser; import org.eclipse.jgit.treewalk.TreeWalk; import org.eclipse.jgit.treewalk.filter.PathFilterGroup; @@ -133,7 +136,7 @@ public class ResetCommand extends GitCommand<Ref> { * * @return the Ref after reset */ - public Ref call() throws IOException { + public Ref call() throws GitAPIException { checkCallable(); Ref r; @@ -192,6 +195,10 @@ public class ResetCommand extends GitCommand<Ref> { throw new JGitInternalException(MessageFormat.format( JGitText.get().cannotLock, ru.getName())); + ObjectId origHead = ru.getOldObjectId(); + if (origHead != null) + repo.writeOrigHead(origHead); + switch (mode) { case HARD: checkoutIndex(commit); @@ -313,14 +320,49 @@ public class ResetCommand extends GitCommand<Ref> { private void resetIndex(RevCommit commit) throws IOException { DirCache dc = repo.lockDirCache(); + TreeWalk walk = null; try { - dc.clear(); - DirCacheBuilder dcb = dc.builder(); - dcb.addTree(new byte[0], 0, repo.newObjectReader(), - commit.getTree()); - dcb.commit(); + DirCacheEditor editor = dc.editor(); + + walk = new TreeWalk(repo); + walk.addTree(commit.getTree()); + walk.addTree(new DirCacheIterator(dc)); + walk.setRecursive(true); + + while (walk.next()) { + AbstractTreeIterator cIter = walk.getTree(0, + AbstractTreeIterator.class); + if (cIter == null) { + editor.add(new DeletePath(walk.getPathString())); + continue; + } + + final DirCacheEntry entry = new DirCacheEntry(walk.getRawPath()); + entry.setFileMode(cIter.getEntryFileMode()); + entry.setObjectIdFromRaw(cIter.idBuffer(), cIter.idOffset()); + + DirCacheIterator dcIter = walk.getTree(1, + DirCacheIterator.class); + if (dcIter != null && dcIter.idEqual(cIter)) { + DirCacheEntry indexEntry = dcIter.getDirCacheEntry(); + entry.setLastModified(indexEntry.getLastModified()); + entry.setLength(indexEntry.getLength()); + } + + editor.add(new PathEdit(entry) { + + @Override + public void apply(DirCacheEntry ent) { + ent.copyMetaData(entry); + } + }); + } + + editor.commit(); } finally { dc.unlock(); + if (walk != null) + walk.release(); } } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/RevertCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/RevertCommand.java index b6757d8070..416677c406 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/RevertCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/RevertCommand.java @@ -50,8 +50,8 @@ import java.util.Map; import org.eclipse.jgit.api.MergeResult.MergeStatus; import org.eclipse.jgit.api.errors.GitAPIException; -import org.eclipse.jgit.api.errors.MultipleParentsNotAllowedException; import org.eclipse.jgit.api.errors.JGitInternalException; +import org.eclipse.jgit.api.errors.MultipleParentsNotAllowedException; import org.eclipse.jgit.api.errors.NoHeadException; import org.eclipse.jgit.dircache.DirCacheCheckout; import org.eclipse.jgit.internal.JGitText; diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/RmCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/RmCommand.java index 2b8cafccee..d29d547bd1 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/RmCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/RmCommand.java @@ -47,6 +47,7 @@ import java.io.IOException; import java.util.Collection; import java.util.LinkedList; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoFilepatternException; import org.eclipse.jgit.dircache.DirCache; @@ -99,7 +100,8 @@ public class RmCommand extends GitCommand<DirCache> { * * @return the DirCache after Rm */ - public DirCache call() throws NoFilepatternException { + public DirCache call() throws GitAPIException, + NoFilepatternException { if (filepatterns.isEmpty()) throw new NoFilepatternException(JGitText.get().atLeastOnePatternIsRequired); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/ShowNoteCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/ShowNoteCommand.java index 45f53e7fae..7d411c3ecf 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/ShowNoteCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/ShowNoteCommand.java @@ -44,6 +44,7 @@ package org.eclipse.jgit.api; import java.io.IOException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.Ref; @@ -73,11 +74,7 @@ public class ShowNoteCommand extends GitCommand<Note> { super(repo); } - /** - * @throws JGitInternalException - * upon internal failure - */ - public Note call() throws JGitInternalException { + public Note call() throws GitAPIException { checkCallable(); RevWalk walk = new RevWalk(repo); NoteMap map = NoteMap.newEmptyMap(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashApplyCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashApplyCommand.java index 3876e48cd0..4992d3ccd3 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashApplyCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashApplyCommand.java @@ -189,8 +189,7 @@ public class StashApplyCommand extends GitCommand<ObjectId> { return false; } - private ObjectId getHeadTree() throws JGitInternalException, - GitAPIException { + private ObjectId getHeadTree() throws GitAPIException { final ObjectId headTree; try { headTree = repo.resolve(Constants.HEAD + "^{tree}"); @@ -202,7 +201,7 @@ public class StashApplyCommand extends GitCommand<ObjectId> { return headTree; } - private ObjectId getStashId() throws JGitInternalException, GitAPIException { + private ObjectId getStashId() throws GitAPIException { final String revision = stashRef != null ? stashRef : DEFAULT_REF; final ObjectId stashId; try { @@ -298,7 +297,7 @@ public class StashApplyCommand extends GitCommand<ObjectId> { * * @return id of stashed commit that was applied */ - public ObjectId call() throws GitAPIException, JGitInternalException { + public ObjectId call() throws GitAPIException { checkCallable(); if (repo.getRepositoryState() != RepositoryState.SAFE) diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashCreateCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashCreateCommand.java index 5ba61622ea..4056894c9d 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashCreateCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashCreateCommand.java @@ -212,7 +212,7 @@ public class StashCreateCommand extends GitCommand<RevCommit> { * * @return stashed commit or null if no changes to stash */ - public RevCommit call() throws GitAPIException, JGitInternalException { + public RevCommit call() throws GitAPIException { checkCallable(); Ref head = getHead(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashDropCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashDropCommand.java index e718417d1e..eb61298e2c 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashDropCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashDropCommand.java @@ -168,7 +168,7 @@ public class StashDropCommand extends GitCommand<ObjectId> { * * @return commit id of stash reference or null if no more stashed changes */ - public ObjectId call() throws GitAPIException, JGitInternalException { + public ObjectId call() throws GitAPIException { checkCallable(); Ref stashRef = getRef(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashListCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashListCommand.java index 8f7bf2e0f5..407b5ab1ee 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/StashListCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/StashListCommand.java @@ -49,6 +49,7 @@ import java.util.Collection; import java.util.Collections; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidRefNameException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.internal.JGitText; @@ -75,7 +76,7 @@ public class StashListCommand extends GitCommand<Collection<RevCommit>> { super(repo); } - public Collection<RevCommit> call() throws Exception { + public Collection<RevCommit> call() throws GitAPIException { checkCallable(); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/StatusCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/StatusCommand.java index 7d7eb1871f..b3e112fc6a 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/StatusCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/StatusCommand.java @@ -44,6 +44,8 @@ package org.eclipse.jgit.api; import java.io.IOException; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.NoWorkTreeException; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.IndexDiff; @@ -80,14 +82,17 @@ public class StatusCommand extends GitCommand<Status> { * @return a {@link Status} object telling about each path where working * tree, index or HEAD differ from each other. */ - public Status call() throws IOException, NoWorkTreeException { + public Status call() throws GitAPIException, NoWorkTreeException { if (workingTreeIt == null) workingTreeIt = new FileTreeIterator(repo); - IndexDiff diff = new IndexDiff(repo, Constants.HEAD, workingTreeIt); - diff.diff(); - - return new Status(diff); + try { + IndexDiff diff = new IndexDiff(repo, Constants.HEAD, workingTreeIt); + diff.diff(); + return new Status(diff); + } catch (IOException e) { + throw new JGitInternalException(e.getMessage(), e); + } } /** diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleAddCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleAddCommand.java index 454fc23853..bfef053d85 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleAddCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleAddCommand.java @@ -46,6 +46,7 @@ import java.io.File; import java.io.IOException; import java.text.MessageFormat; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoFilepatternException; import org.eclipse.jgit.errors.ConfigInvalidException; @@ -134,7 +135,7 @@ public class SubmoduleAddCommand extends return SubmoduleWalk.forIndex(repo).setFilter(filter).next(); } - public Repository call() throws JGitInternalException { + public Repository call() throws GitAPIException { checkCallable(); if (path == null || path.length() == 0) throw new IllegalArgumentException(JGitText.get().pathNotConfigured); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleInitCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleInitCommand.java index fef13704ef..e799bfb8bd 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleInitCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleInitCommand.java @@ -47,6 +47,7 @@ import java.util.ArrayList; import java.util.Collection; import java.util.List; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.ConfigInvalidException; import org.eclipse.jgit.lib.ConfigConstants; @@ -89,7 +90,7 @@ public class SubmoduleInitCommand extends GitCommand<Collection<String>> { return this; } - public Collection<String> call() throws JGitInternalException { + public Collection<String> call() throws GitAPIException { checkCallable(); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleStatusCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleStatusCommand.java index 0542583785..d27f90c129 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleStatusCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleStatusCommand.java @@ -48,6 +48,7 @@ import java.util.Collection; import java.util.HashMap; import java.util.Map; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.ConfigInvalidException; import org.eclipse.jgit.lib.Constants; @@ -89,7 +90,7 @@ public class SubmoduleStatusCommand extends return this; } - public Map<String, SubmoduleStatus> call() throws JGitInternalException { + public Map<String, SubmoduleStatus> call() throws GitAPIException { checkCallable(); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleSyncCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleSyncCommand.java index fd8ddc941d..edc54ff4cc 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleSyncCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleSyncCommand.java @@ -48,6 +48,7 @@ import java.util.Collection; import java.util.HashMap; import java.util.Map; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.errors.ConfigInvalidException; import org.eclipse.jgit.lib.ConfigConstants; @@ -106,7 +107,7 @@ public class SubmoduleSyncCommand extends GitCommand<Map<String, String>> { return null; } - public Map<String, String> call() throws JGitInternalException { + public Map<String, String> call() throws GitAPIException { checkCallable(); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleUpdateCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleUpdateCommand.java index f94b2099a0..be705ee6dd 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleUpdateCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/SubmoduleUpdateCommand.java @@ -109,7 +109,7 @@ public class SubmoduleUpdateCommand extends return this; } - public Collection<String> call() throws JGitInternalException { + public Collection<String> call() throws GitAPIException { checkCallable(); try { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/TagCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/TagCommand.java index c867b53e8d..cef9e18349 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/TagCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/TagCommand.java @@ -46,6 +46,7 @@ import java.io.IOException; import java.text.MessageFormat; import org.eclipse.jgit.api.errors.ConcurrentRefUpdateException; +import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.api.errors.InvalidTagNameException; import org.eclipse.jgit.api.errors.JGitInternalException; import org.eclipse.jgit.api.errors.NoHeadException; @@ -100,15 +101,10 @@ public class TagCommand extends GitCommand<Ref> { * @return a {@link Ref} a ref pointing to a tag * @throws NoHeadException * when called on a git repo without a HEAD reference - * @throws JGitInternalException - * a low-level exception of JGit has occurred. The original - * exception can be retrieved by calling - * {@link Exception#getCause()}. Expect only - * {@code IOException's} to be wrapped. * @since 2.0 */ - public Ref call() throws JGitInternalException, - ConcurrentRefUpdateException, InvalidTagNameException, NoHeadException { + public Ref call() throws GitAPIException, ConcurrentRefUpdateException, + InvalidTagNameException, NoHeadException { checkCallable(); RepositoryState state = repo.getRepositoryState(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/errors/UnmergedPathsException.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/errors/UnmergedPathsException.java index 19101dbb05..0990040150 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/api/errors/UnmergedPathsException.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/errors/UnmergedPathsException.java @@ -49,6 +49,16 @@ public class UnmergedPathsException extends GitAPIException { * The default constructor with a default message */ public UnmergedPathsException() { - super(JGitText.get().unmergedPaths); + this(null); + } + + /** + * The default constructor with a default message + * + * @param cause + * original exception + */ + public UnmergedPathsException(Throwable cause) { + super(JGitText.get().unmergedPaths, cause); } } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/dircache/DirCache.java b/org.eclipse.jgit/src/org/eclipse/jgit/dircache/DirCache.java index 0d5952df24..9108d9235d 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/dircache/DirCache.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/dircache/DirCache.java @@ -69,8 +69,11 @@ import org.eclipse.jgit.internal.JGitText; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.ObjectId; import org.eclipse.jgit.lib.ObjectInserter; +import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.storage.file.FileSnapshot; import org.eclipse.jgit.storage.file.LockFile; +import org.eclipse.jgit.treewalk.FileTreeIterator; +import org.eclipse.jgit.treewalk.TreeWalk; import org.eclipse.jgit.util.FS; import org.eclipse.jgit.util.IO; import org.eclipse.jgit.util.MutableInteger; @@ -145,6 +148,30 @@ public class DirCache { * failures are reported as exceptions and therefore prevent the method from * returning a partially populated index. * + * @param repository + * repository containing the index to read + * @return a cache representing the contents of the specified index file (if + * it exists) or an empty cache if the file does not exist. + * @throws IOException + * the index file is present but could not be read. + * @throws CorruptObjectException + * the index file is using a format or extension that this + * library does not support. + */ + public static DirCache read(final Repository repository) + throws CorruptObjectException, IOException { + final DirCache c = read(repository.getIndexFile(), repository.getFS()); + c.repository = repository; + return c; + } + + /** + * Create a new in-core index representation and read an index from disk. + * <p> + * The new index will be read before it is returned to the caller. Read + * failures are reported as exceptions and therefore prevent the method from + * returning a partially populated index. + * * @param indexLocation * location of the index file on disk. * @param fs @@ -217,6 +244,37 @@ public class DirCache { * the method from returning a partially populated index. On read failure, * the lock is released. * + * @param repository + * repository containing the index to lock and read + * @param indexChangedListener + * listener to be informed when DirCache is committed + * @return a cache representing the contents of the specified index file (if + * it exists) or an empty cache if the file does not exist. + * @throws IOException + * the index file is present but could not be read, or the lock + * could not be obtained. + * @throws CorruptObjectException + * the index file is using a format or extension that this + * library does not support. + * @since 2.0 + */ + public static DirCache lock(final Repository repository, + final IndexChangedListener indexChangedListener) + throws CorruptObjectException, IOException { + DirCache c = lock(repository.getIndexFile(), repository.getFS(), + indexChangedListener); + c.repository = repository; + return c; + } + + /** + * Create a new in-core index representation, lock it, and read from disk. + * <p> + * The new index will be locked and then read before it is returned to the + * caller. Read failures are reported as exceptions and therefore prevent + * the method from returning a partially populated index. On read failure, + * the lock is released. + * * @param indexLocation * location of the index file on disk. * @param fs @@ -272,6 +330,9 @@ public class DirCache { /** listener to be informed on commit */ private IndexChangedListener indexChangedListener; + /** Repository containing this index */ + private Repository repository; + /** * Create a new in-core index representation. * <p> @@ -591,6 +652,13 @@ public class DirCache { smudge_s = 0; } + // Check if tree is non-null here since calling updateSmudgedEntries + // will automatically build it via creating a DirCacheIterator + final boolean writeTree = tree != null; + + if (repository != null && entryCnt > 0) + updateSmudgedEntries(); + for (int i = 0; i < entryCnt; i++) { final DirCacheEntry e = sortedEntries[i]; if (e.mightBeRacilyClean(smudge_s, smudge_ns)) @@ -598,7 +666,7 @@ public class DirCache { e.write(dos); } - if (tree != null) { + if (writeTree) { final TemporaryBuffer bb = new TemporaryBuffer.LocalFile(); tree.write(tmp, bb); bb.close(); @@ -865,4 +933,35 @@ public class DirCache { private void registerIndexChangedListener(IndexChangedListener listener) { this.indexChangedListener = listener; } + + /** + * Update any smudged entries with information from the working tree. + * + * @throws IOException + */ + private void updateSmudgedEntries() throws IOException { + TreeWalk walk = new TreeWalk(repository); + try { + DirCacheIterator iIter = new DirCacheIterator(this); + FileTreeIterator fIter = new FileTreeIterator(repository); + walk.addTree(iIter); + walk.addTree(fIter); + walk.setRecursive(true); + while (walk.next()) { + iIter = walk.getTree(0, DirCacheIterator.class); + if (iIter == null) + continue; + fIter = walk.getTree(1, FileTreeIterator.class); + if (fIter == null) + continue; + DirCacheEntry entry = iIter.getDirCacheEntry(); + if (entry.isSmudged() && iIter.idEqual(fIter)) { + entry.setLength(fIter.getEntryLength()); + entry.setLastModified(fIter.getEntryLastModified()); + } + } + } finally { + walk.release(); + } + } } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/errors/GitlinksNotSupportedException.java b/org.eclipse.jgit/src/org/eclipse/jgit/errors/GitlinksNotSupportedException.java deleted file mode 100644 index d501bda38b..0000000000 --- a/org.eclipse.jgit/src/org/eclipse/jgit/errors/GitlinksNotSupportedException.java +++ /dev/null @@ -1,65 +0,0 @@ -/* - * Copyright (C) 2009, Jonas Fonseca <fonseca@diku.dk> - * Copyright (C) 2007, Robin Rosenberg <robin.rosenberg@dewire.com> - * Copyright (C) 2007, Shawn O. Pearce <spearce@spearce.org> - * and other copyright owners as documented in the project's IP log. - * - * This program and the accompanying materials are made available - * under the terms of the Eclipse Distribution License v1.0 which - * accompanies this distribution, is reproduced below, and is - * available at http://www.eclipse.org/org/documents/edl-v10.php - * - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or - * without modification, are permitted provided that the following - * conditions are met: - * - * - Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * - * - Redistributions in binary form must reproduce the above - * copyright notice, this list of conditions and the following - * disclaimer in the documentation and/or other materials provided - * with the distribution. - * - * - Neither the name of the Eclipse Foundation, Inc. nor the - * names of its contributors may be used to endorse or promote - * products derived from this software without specific prior - * written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND - * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, - * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES - * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, - * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT - * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER - * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -package org.eclipse.jgit.errors; - -import java.io.IOException; - -/** - * An exception thrown when a gitlink entry is found and cannot be - * handled. - */ -public class GitlinksNotSupportedException extends IOException { - private static final long serialVersionUID = 1L; - - /** - * Construct a GitlinksNotSupportedException for the specified link - * - * @param s name of link in tree or workdir - */ - public GitlinksNotSupportedException(final String s) { - super(s); - } -} diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/lib/Repository.java b/org.eclipse.jgit/src/org/eclipse/jgit/lib/Repository.java index c70c9b0f85..7b9d453aa2 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/lib/Repository.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/lib/Repository.java @@ -871,7 +871,7 @@ public abstract class Repository { */ public DirCache readDirCache() throws NoWorkTreeException, CorruptObjectException, IOException { - return DirCache.read(getIndexFile(), getFS()); + return DirCache.read(this); } /** @@ -903,7 +903,7 @@ public abstract class Repository { notifyIndexChanged(); } }; - return DirCache.lock(getIndexFile(), getFS(), l); + return DirCache.lock(this, l); } static byte[] gitInternalSlash(byte[] bytes) { @@ -1248,6 +1248,39 @@ public abstract class Repository { } /** + * Write original HEAD commit into $GIT_DIR/ORIG_HEAD. + * + * @param head + * an object id of the original HEAD commit or <code>null</code> + * to delete the file + * @throws IOException + */ + public void writeOrigHead(ObjectId head) throws IOException { + List<ObjectId> heads = head != null ? Collections.singletonList(head) + : null; + writeHeadsFile(heads, Constants.ORIG_HEAD); + } + + /** + * Return the information stored in the file $GIT_DIR/ORIG_HEAD. + * + * @return object id from ORIG_HEAD file or {@code null} if this file + * doesn't exist. Also if the file exists but is empty {@code null} + * will be returned + * @throws IOException + * @throws NoWorkTreeException + * if this is bare, which implies it has no working directory. + * See {@link #isBare()}. + */ + public ObjectId readOrigHead() throws IOException, NoWorkTreeException { + if (isBare() || getDirectory() == null) + throw new NoWorkTreeException(); + + byte[] raw = readGitDirectoryFile(Constants.ORIG_HEAD); + return raw != null ? ObjectId.fromString(raw, 0) : null; + } + + /** * Read a file from the git directory. * * @param filename diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/revplot/PlotWalk.java b/org.eclipse.jgit/src/org/eclipse/jgit/revplot/PlotWalk.java index 8323d2fe25..55cf235cf9 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/revplot/PlotWalk.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/revplot/PlotWalk.java @@ -172,6 +172,11 @@ public class PlotWalk extends RevWalk { return ((RevCommit) o).getCommitTime(); if (o instanceof RevTag) { RevTag tag = (RevTag) o; + try { + parseBody(tag); + } catch (IOException e) { + return 0; + } PersonIdent who = tag.getTaggerIdent(); return who != null ? who.getWhen().getTime() : 0; } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/storage/file/RefDirectory.java b/org.eclipse.jgit/src/org/eclipse/jgit/storage/file/RefDirectory.java index a152e86fb6..fe13f2c3c7 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/storage/file/RefDirectory.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/storage/file/RefDirectory.java @@ -63,6 +63,8 @@ import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.io.InputStreamReader; +import java.security.DigestInputStream; +import java.security.MessageDigest; import java.text.MessageFormat; import java.util.Arrays; import java.util.LinkedList; @@ -626,24 +628,27 @@ public class RefDirectory extends RefDatabase { return curList; final PackedRefList newList = readPackedRefs(); - if (packedRefs.compareAndSet(curList, newList)) + if (packedRefs.compareAndSet(curList, newList) + && !curList.id.equals(newList.id)) modCnt.incrementAndGet(); return newList; } - private PackedRefList readPackedRefs() - throws IOException { + private PackedRefList readPackedRefs() throws IOException { final FileSnapshot snapshot = FileSnapshot.save(packedRefsFile); final BufferedReader br; + final MessageDigest digest = Constants.newMessageDigest(); try { - br = new BufferedReader(new InputStreamReader(new FileInputStream( - packedRefsFile), CHARSET)); + br = new BufferedReader(new InputStreamReader( + new DigestInputStream(new FileInputStream(packedRefsFile), + digest), CHARSET)); } catch (FileNotFoundException noPackedRefs) { // Ignore it and leave the new list empty. return PackedRefList.NO_PACKED_REFS; } try { - return new PackedRefList(parsePackedRefs(br), snapshot); + return new PackedRefList(parsePackedRefs(br), snapshot, + ObjectId.fromRaw(digest.digest())); } finally { br.close(); } @@ -724,8 +729,9 @@ public class RefDirectory extends RefDatabase { if (!lck.commit()) throw new ObjectWritingException(MessageFormat.format(JGitText.get().unableToWrite, name)); - packedRefs.compareAndSet(oldPackedList, new PackedRefList( - refs, lck.getCommitSnapshot())); + byte[] digest = Constants.newMessageDigest().digest(content); + packedRefs.compareAndSet(oldPackedList, new PackedRefList(refs, + lck.getCommitSnapshot(), ObjectId.fromRaw(digest))); } }.writePackedRefs(); } @@ -899,13 +905,17 @@ public class RefDirectory extends RefDatabase { private static class PackedRefList extends RefList<Ref> { static final PackedRefList NO_PACKED_REFS = new PackedRefList( - RefList.emptyList(), FileSnapshot.MISSING_FILE); + RefList.emptyList(), FileSnapshot.MISSING_FILE, + ObjectId.zeroId()); final FileSnapshot snapshot; - PackedRefList(RefList<Ref> src, FileSnapshot s) { + final ObjectId id; + + PackedRefList(RefList<Ref> src, FileSnapshot s, ObjectId i) { super(src); snapshot = s; + id = i; } } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/storage/pack/PackWriter.java b/org.eclipse.jgit/src/org/eclipse/jgit/storage/pack/PackWriter.java index 03cf649a29..d93e2d6805 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/storage/pack/PackWriter.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/storage/pack/PackWriter.java @@ -1660,7 +1660,8 @@ public class PackWriter { for (int i = 0; i < cmit.getParentCount(); i++) { RevCommit p = cmit.getParent(i); - if (!p.has(added) && !p.has(RevFlag.UNINTERESTING)) { + if (!p.has(added) && !p.has(RevFlag.UNINTERESTING) + && !exclude(p)) { p.add(added); addObject(p, 0); commitCnt++; @@ -173,7 +173,7 @@ <junit-version>4.5</junit-version> <args4j-version>2.0.12</args4j-version> <servlet-api-version>2.5</servlet-api-version> - <jetty-version>7.1.6.v20100715</jetty-version> + <jetty-version>7.6.0.v20120127</jetty-version> <protobuf-version>2.4.0a</protobuf-version> <clirr-version>2.3</clirr-version> </properties> @@ -183,6 +183,11 @@ <id>jgit-repository</id> <url>http://download.eclipse.org/jgit/maven</url> </repository> + <repository> + <id>jetty</id> + <layout>p2</layout> + <url>http://download.eclipse.org/jetty/updates/jetty-bundles-7.x/${jetty-version}/</url> + </repository> </repositories> <build> |