aboutsummaryrefslogtreecommitdiffstats
path: root/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk
diff options
context:
space:
mode:
Diffstat (limited to 'org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk')
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/AlwaysEmptyRevQueueTest.java69
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/DateRevQueueTest.java124
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FIFORevQueueTest.java87
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FooterLineTest.java323
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/LIFORevQueueTest.java75
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/ObjectWalkTest.java196
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevCommitParseTest.java321
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevFlagSetTest.java137
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevObjectTest.java177
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevQueueTestCase.java91
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevTagParseTest.java356
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkCullTest.java100
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkFilterTest.java297
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkMergeBaseTest.java139
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter1Test.java182
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter6012Test.java168
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkSortTest.java168
-rw-r--r--org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkTestCase.java183
18 files changed, 3193 insertions, 0 deletions
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/AlwaysEmptyRevQueueTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/AlwaysEmptyRevQueueTest.java
new file mode 100644
index 0000000000..d752501c12
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/AlwaysEmptyRevQueueTest.java
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+public class AlwaysEmptyRevQueueTest extends RevWalkTestCase {
+ private final AbstractRevQueue q = AbstractRevQueue.EMPTY_QUEUE;
+
+ public void testEmpty() throws Exception {
+ assertNull(q.next());
+ assertTrue(q.everbodyHasFlag(RevWalk.UNINTERESTING));
+ assertFalse(q.anybodyHasFlag(RevWalk.UNINTERESTING));
+ assertEquals(0, q.outputType());
+ }
+
+ public void testClear() throws Exception {
+ q.clear();
+ testEmpty();
+ }
+
+ public void testAddFails() throws Exception {
+ try {
+ q.add(commit());
+ fail("Did not throw UnsupportedOperationException");
+ } catch (UnsupportedOperationException e) {
+ // expected result
+ }
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/DateRevQueueTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/DateRevQueueTest.java
new file mode 100644
index 0000000000..b3a92951b6
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/DateRevQueueTest.java
@@ -0,0 +1,124 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+public class DateRevQueueTest extends RevQueueTestCase<DateRevQueue> {
+ protected DateRevQueue create() {
+ return new DateRevQueue();
+ }
+
+ public void testEmpty() throws Exception {
+ super.testEmpty();
+ assertNull(q.peek());
+ assertEquals(Generator.SORT_COMMIT_TIME_DESC, q.outputType());
+ }
+
+ public void testCloneEmpty() throws Exception {
+ q = new DateRevQueue(AbstractRevQueue.EMPTY_QUEUE);
+ assertNull(q.next());
+ }
+
+ public void testInsertOutOfOrder() throws Exception {
+ final RevCommit a = parse(commit());
+ final RevCommit b = parse(commit(10, a));
+ final RevCommit c1 = parse(commit(5, b));
+ final RevCommit c2 = parse(commit(-50, b));
+
+ q.add(c2);
+ q.add(a);
+ q.add(b);
+ q.add(c1);
+
+ assertCommit(c1, q.next());
+ assertCommit(b, q.next());
+ assertCommit(a, q.next());
+ assertCommit(c2, q.next());
+ assertNull(q.next());
+ }
+
+ public void testInsertTie() throws Exception {
+ final RevCommit a = parse(commit());
+ final RevCommit b = parse(commit(0, a));
+ {
+ q = create();
+ q.add(a);
+ q.add(b);
+
+ assertCommit(a, q.next());
+ assertCommit(b, q.next());
+ assertNull(q.next());
+ }
+ {
+ q = create();
+ q.add(b);
+ q.add(a);
+
+ assertCommit(b, q.next());
+ assertCommit(a, q.next());
+ assertNull(q.next());
+ }
+ }
+
+ public void testCloneFIFO() throws Exception {
+ final RevCommit a = parse(commit());
+ final RevCommit b = parse(commit(200, a));
+ final RevCommit c = parse(commit(200, b));
+
+ final FIFORevQueue src = new FIFORevQueue();
+ src.add(a);
+ src.add(b);
+ src.add(c);
+
+ q = new DateRevQueue(src);
+ assertFalse(q.everbodyHasFlag(RevWalk.UNINTERESTING));
+ assertFalse(q.anybodyHasFlag(RevWalk.UNINTERESTING));
+ assertCommit(c, q.peek());
+ assertCommit(c, q.peek());
+
+ assertCommit(c, q.next());
+ assertCommit(b, q.next());
+ assertCommit(a, q.next());
+ assertNull(q.next());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FIFORevQueueTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FIFORevQueueTest.java
new file mode 100644
index 0000000000..3f4daab9f6
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FIFORevQueueTest.java
@@ -0,0 +1,87 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.util.ArrayList;
+
+public class FIFORevQueueTest extends RevQueueTestCase<FIFORevQueue> {
+ protected FIFORevQueue create() {
+ return new FIFORevQueue();
+ }
+
+ public void testEmpty() throws Exception {
+ super.testEmpty();
+ assertEquals(0, q.outputType());
+ }
+
+ public void testCloneEmpty() throws Exception {
+ q = new FIFORevQueue(AbstractRevQueue.EMPTY_QUEUE);
+ assertNull(q.next());
+ }
+
+ public void testAddLargeBlocks() throws Exception {
+ final ArrayList<RevCommit> lst = new ArrayList<RevCommit>();
+ for (int i = 0; i < 3 * BlockRevQueue.Block.BLOCK_SIZE; i++) {
+ final RevCommit c = commit();
+ lst.add(c);
+ q.add(c);
+ }
+ for (int i = 0; i < lst.size(); i++)
+ assertSame(lst.get(i), q.next());
+ }
+
+ public void testUnpopAtFront() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit();
+ final RevCommit c = commit();
+
+ q.add(a);
+ q.unpop(b);
+ q.unpop(c);
+
+ assertSame(c, q.next());
+ assertSame(b, q.next());
+ assertSame(a, q.next());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FooterLineTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FooterLineTest.java
new file mode 100644
index 0000000000..d199f04ccb
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/FooterLineTest.java
@@ -0,0 +1,323 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.util.List;
+
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.RepositoryTestCase;
+
+public class FooterLineTest extends RepositoryTestCase {
+ public void testNoFooters_EmptyBody() {
+ final RevCommit commit = parse("");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testNoFooters_NewlineOnlyBody1() {
+ final RevCommit commit = parse("\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testNoFooters_NewlineOnlyBody5() {
+ final RevCommit commit = parse("\n\n\n\n\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testNoFooters_OneLineBodyNoLF() {
+ final RevCommit commit = parse("this is a commit");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testNoFooters_OneLineBodyWithLF() {
+ final RevCommit commit = parse("this is a commit\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testNoFooters_ShortBodyNoLF() {
+ final RevCommit commit = parse("subject\n\nbody of commit");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testNoFooters_ShortBodyWithLF() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ assertNotNull(footers);
+ assertEquals(0, footers.size());
+ }
+
+ public void testSignedOffBy_OneUserNoLF() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Signed-off-by: A. U. Thor <a@example.com>");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("A. U. Thor <a@example.com>", f.getValue());
+ assertEquals("a@example.com", f.getEmailAddress());
+ }
+
+ public void testSignedOffBy_OneUserWithLF() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Signed-off-by: A. U. Thor <a@example.com>\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("A. U. Thor <a@example.com>", f.getValue());
+ assertEquals("a@example.com", f.getEmailAddress());
+ }
+
+ public void testSignedOffBy_IgnoreWhitespace() {
+ // We only ignore leading whitespace on the value, trailing
+ // is assumed part of the value.
+ //
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Signed-off-by: A. U. Thor <a@example.com> \n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("A. U. Thor <a@example.com> ", f.getValue());
+ assertEquals("a@example.com", f.getEmailAddress());
+ }
+
+ public void testEmptyValueNoLF() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Signed-off-by:");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("", f.getValue());
+ assertNull(f.getEmailAddress());
+ }
+
+ public void testEmptyValueWithLF() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Signed-off-by:\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("", f.getValue());
+ assertNull(f.getEmailAddress());
+ }
+
+ public void testShortKey() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "K:V\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("K", f.getKey());
+ assertEquals("V", f.getValue());
+ assertNull(f.getEmailAddress());
+ }
+
+ public void testNonDelimtedEmail() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Acked-by: re@example.com\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Acked-by", f.getKey());
+ assertEquals("re@example.com", f.getValue());
+ assertEquals("re@example.com", f.getEmailAddress());
+ }
+
+ public void testNotEmail() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n" + "\n"
+ + "Acked-by: Main Tain Er\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(1, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Acked-by", f.getKey());
+ assertEquals("Main Tain Er", f.getValue());
+ assertNull(f.getEmailAddress());
+ }
+
+ public void testSignedOffBy_ManyUsers() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n"
+ + "Not-A-Footer-Line: this line must not be read as a footer\n"
+ + "\n" // paragraph break, now footers appear in final block
+ + "Signed-off-by: A. U. Thor <a@example.com>\n"
+ + "CC: <some.mailing.list@example.com>\n"
+ + "Acked-by: Some Reviewer <sr@example.com>\n"
+ + "Signed-off-by: Main Tain Er <mte@example.com>\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(4, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("A. U. Thor <a@example.com>", f.getValue());
+ assertEquals("a@example.com", f.getEmailAddress());
+
+ f = footers.get(1);
+ assertEquals("CC", f.getKey());
+ assertEquals("<some.mailing.list@example.com>", f.getValue());
+ assertEquals("some.mailing.list@example.com", f.getEmailAddress());
+
+ f = footers.get(2);
+ assertEquals("Acked-by", f.getKey());
+ assertEquals("Some Reviewer <sr@example.com>", f.getValue());
+ assertEquals("sr@example.com", f.getEmailAddress());
+
+ f = footers.get(3);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("Main Tain Er <mte@example.com>", f.getValue());
+ assertEquals("mte@example.com", f.getEmailAddress());
+ }
+
+ public void testSignedOffBy_SkipNonFooter() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n"
+ + "Not-A-Footer-Line: this line must not be read as a footer\n"
+ + "\n" // paragraph break, now footers appear in final block
+ + "Signed-off-by: A. U. Thor <a@example.com>\n"
+ + "CC: <some.mailing.list@example.com>\n"
+ + "not really a footer line but we'll skip it anyway\n"
+ + "Acked-by: Some Reviewer <sr@example.com>\n"
+ + "Signed-off-by: Main Tain Er <mte@example.com>\n");
+ final List<FooterLine> footers = commit.getFooterLines();
+ FooterLine f;
+
+ assertNotNull(footers);
+ assertEquals(4, footers.size());
+
+ f = footers.get(0);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("A. U. Thor <a@example.com>", f.getValue());
+
+ f = footers.get(1);
+ assertEquals("CC", f.getKey());
+ assertEquals("<some.mailing.list@example.com>", f.getValue());
+
+ f = footers.get(2);
+ assertEquals("Acked-by", f.getKey());
+ assertEquals("Some Reviewer <sr@example.com>", f.getValue());
+
+ f = footers.get(3);
+ assertEquals("Signed-off-by", f.getKey());
+ assertEquals("Main Tain Er <mte@example.com>", f.getValue());
+ }
+
+ public void testFilterFootersIgnoreCase() {
+ final RevCommit commit = parse("subject\n\nbody of commit\n"
+ + "Not-A-Footer-Line: this line must not be read as a footer\n"
+ + "\n" // paragraph break, now footers appear in final block
+ + "Signed-Off-By: A. U. Thor <a@example.com>\n"
+ + "CC: <some.mailing.list@example.com>\n"
+ + "Acked-by: Some Reviewer <sr@example.com>\n"
+ + "signed-off-by: Main Tain Er <mte@example.com>\n");
+ final List<String> footers = commit.getFooterLines("signed-off-by");
+
+ assertNotNull(footers);
+ assertEquals(2, footers.size());
+
+ assertEquals("A. U. Thor <a@example.com>", footers.get(0));
+ assertEquals("Main Tain Er <mte@example.com>", footers.get(1));
+ }
+
+ private RevCommit parse(final String msg) {
+ final StringBuilder buf = new StringBuilder();
+ buf.append("tree " + ObjectId.zeroId().name() + "\n");
+ buf.append("author A. U. Thor <a@example.com> 1 +0000\n");
+ buf.append("committer A. U. Thor <a@example.com> 1 +0000\n");
+ buf.append("\n");
+ buf.append(msg);
+
+ final RevWalk walk = new RevWalk(db);
+ walk.setRetainBody(true);
+ final RevCommit c = new RevCommit(ObjectId.zeroId());
+ c.parseCanonical(walk, Constants.encode(buf.toString()));
+ return c;
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/LIFORevQueueTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/LIFORevQueueTest.java
new file mode 100644
index 0000000000..7676a71503
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/LIFORevQueueTest.java
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.util.ArrayList;
+import java.util.Collections;
+
+public class LIFORevQueueTest extends RevQueueTestCase<LIFORevQueue> {
+ protected LIFORevQueue create() {
+ return new LIFORevQueue();
+ }
+
+ public void testEmpty() throws Exception {
+ super.testEmpty();
+ assertEquals(0, q.outputType());
+ }
+
+ public void testCloneEmpty() throws Exception {
+ q = new LIFORevQueue(AbstractRevQueue.EMPTY_QUEUE);
+ assertNull(q.next());
+ }
+
+ public void testAddLargeBlocks() throws Exception {
+ final ArrayList<RevCommit> lst = new ArrayList<RevCommit>();
+ for (int i = 0; i < 3 * BlockRevQueue.Block.BLOCK_SIZE; i++) {
+ final RevCommit c = commit();
+ lst.add(c);
+ q.add(c);
+ }
+ Collections.reverse(lst);
+ for (int i = 0; i < lst.size(); i++)
+ assertSame(lst.get(i), q.next());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/ObjectWalkTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/ObjectWalkTest.java
new file mode 100644
index 0000000000..7dddeee205
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/ObjectWalkTest.java
@@ -0,0 +1,196 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+public class ObjectWalkTest extends RevWalkTestCase {
+ protected ObjectWalk objw;
+
+ protected RevWalk createRevWalk() {
+ return objw = new ObjectWalk(db);
+ }
+
+ public void testNoCommits() throws Exception {
+ assertNull(objw.next());
+ assertNull(objw.nextObject());
+ }
+
+ public void testTwoCommitsEmptyTree() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ markStart(b);
+
+ assertCommit(b, objw.next());
+ assertCommit(a, objw.next());
+ assertNull(objw.next());
+
+ assertSame(emptyTree, objw.nextObject());
+ assertNull(objw.nextObject());
+ }
+
+ public void testOneCommitOneTreeTwoBlob() throws Exception {
+ final RevBlob f0 = blob("0");
+ final RevBlob f1 = blob("1");
+ final RevTree t = tree(file("0", f0), file("1", f1), file("2", f1));
+ final RevCommit a = commit(t);
+ markStart(a);
+
+ assertCommit(a, objw.next());
+ assertNull(objw.next());
+
+ assertSame(t, objw.nextObject());
+ assertSame(f0, objw.nextObject());
+ assertSame(f1, objw.nextObject());
+ assertNull(objw.nextObject());
+ }
+
+ public void testTwoCommitTwoTreeTwoBlob() throws Exception {
+ final RevBlob f0 = blob("0");
+ final RevBlob f1 = blob("1");
+ final RevBlob f2 = blob("0v2");
+ final RevTree ta = tree(file("0", f0), file("1", f1), file("2", f1));
+ final RevTree tb = tree(file("0", f2), file("1", f1), file("2", f1));
+ final RevCommit a = commit(ta);
+ final RevCommit b = commit(tb, a);
+ markStart(b);
+
+ assertCommit(b, objw.next());
+ assertCommit(a, objw.next());
+ assertNull(objw.next());
+
+ assertSame(tb, objw.nextObject());
+ assertSame(f2, objw.nextObject());
+ assertSame(f1, objw.nextObject());
+
+ assertSame(ta, objw.nextObject());
+ assertSame(f0, objw.nextObject());
+
+ assertNull(objw.nextObject());
+ }
+
+ public void testTwoCommitDeepTree1() throws Exception {
+ final RevBlob f0 = blob("0");
+ final RevBlob f1 = blob("0v2");
+ final RevTree ta = tree(file("a/b/0", f0));
+ final RevTree tb = tree(file("a/b/1", f1));
+ final RevCommit a = commit(ta);
+ final RevCommit b = commit(tb, a);
+ markStart(b);
+
+ assertCommit(b, objw.next());
+ assertCommit(a, objw.next());
+ assertNull(objw.next());
+
+ assertSame(tb, objw.nextObject());
+ assertSame(get(tb, "a"), objw.nextObject());
+ assertSame(get(tb, "a/b"), objw.nextObject());
+ assertSame(f1, objw.nextObject());
+
+ assertSame(ta, objw.nextObject());
+ assertSame(get(ta, "a"), objw.nextObject());
+ assertSame(get(ta, "a/b"), objw.nextObject());
+ assertSame(f0, objw.nextObject());
+
+ assertNull(objw.nextObject());
+ }
+
+ public void testTwoCommitDeepTree2() throws Exception {
+ final RevBlob f1 = blob("1");
+ final RevTree ta = tree(file("a/b/0", f1), file("a/c/q", f1));
+ final RevTree tb = tree(file("a/b/1", f1), file("a/c/q", f1));
+ final RevCommit a = commit(ta);
+ final RevCommit b = commit(tb, a);
+ markStart(b);
+
+ assertCommit(b, objw.next());
+ assertCommit(a, objw.next());
+ assertNull(objw.next());
+
+ assertSame(tb, objw.nextObject());
+ assertSame(get(tb, "a"), objw.nextObject());
+ assertSame(get(tb, "a/b"), objw.nextObject());
+ assertSame(f1, objw.nextObject());
+ assertSame(get(tb, "a/c"), objw.nextObject());
+
+ assertSame(ta, objw.nextObject());
+ assertSame(get(ta, "a"), objw.nextObject());
+ assertSame(get(ta, "a/b"), objw.nextObject());
+
+ assertNull(objw.nextObject());
+ }
+
+ public void testCull() throws Exception {
+ final RevBlob f1 = blob("1");
+ final RevBlob f2 = blob("2");
+ final RevBlob f3 = blob("3");
+ final RevBlob f4 = blob("4");
+
+ final RevTree ta = tree(file("a/1", f1), file("c/3", f3));
+ final RevCommit a = commit(ta);
+
+ final RevTree tb = tree(file("a/1", f2), file("c/3", f3));
+ final RevCommit b1 = commit(tb, a);
+ final RevCommit b2 = commit(tb, b1);
+
+ final RevTree tc = tree(file("a/1", f4));
+ final RevCommit c1 = commit(tc, a);
+ final RevCommit c2 = commit(tc, c1);
+
+ markStart(b2);
+ markUninteresting(c2);
+
+ assertCommit(b2, objw.next());
+ assertCommit(b1, objw.next());
+ assertNull(objw.next());
+
+ assertTrue(a.has(RevFlag.UNINTERESTING));
+ assertTrue(ta.has(RevFlag.UNINTERESTING));
+ assertTrue(f1.has(RevFlag.UNINTERESTING));
+ assertTrue(f3.has(RevFlag.UNINTERESTING));
+
+ assertSame(tb, objw.nextObject());
+ assertSame(get(tb, "a"), objw.nextObject());
+ assertSame(f2, objw.nextObject());
+ assertNull(objw.nextObject());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevCommitParseTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevCommitParseTest.java
new file mode 100644
index 0000000000..b7e84419c9
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevCommitParseTest.java
@@ -0,0 +1,321 @@
+/*
+ * Copyright (C) 2008-2009, Google Inc.
+ * 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.revwalk;
+
+import java.io.ByteArrayOutputStream;
+
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.PersonIdent;
+import org.eclipse.jgit.lib.RepositoryTestCase;
+
+public class RevCommitParseTest extends RepositoryTestCase {
+ public void testParse_NoParents() throws Exception {
+ final ObjectId treeId = id("9788669ad918b6fcce64af8882fc9a81cb6aba67");
+ final String authorName = "A U. Thor";
+ final String authorEmail = "a_u_thor@example.com";
+ final int authorTime = 1218123387;
+
+ final String committerName = "C O. Miter";
+ final String committerEmail = "comiter@example.com";
+ final int committerTime = 1218123390;
+ final StringBuilder body = new StringBuilder();
+
+ body.append("tree ");
+ body.append(treeId.name());
+ body.append("\n");
+
+ body.append("author ");
+ body.append(authorName);
+ body.append(" <");
+ body.append(authorEmail);
+ body.append("> ");
+ body.append(authorTime);
+ body.append(" +0700\n");
+
+ body.append("committer ");
+ body.append(committerName);
+ body.append(" <");
+ body.append(committerEmail);
+ body.append("> ");
+ body.append(committerTime);
+ body.append(" -0500\n");
+
+ body.append("\n");
+
+ final RevWalk rw = new RevWalk(db);
+ final RevCommit c;
+
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ assertNull(c.getTree());
+ assertNull(c.parents);
+
+ c.parseCanonical(rw, body.toString().getBytes("UTF-8"));
+ assertNotNull(c.getTree());
+ assertEquals(treeId, c.getTree().getId());
+ assertSame(rw.lookupTree(treeId), c.getTree());
+
+ assertNotNull(c.parents);
+ assertEquals(0, c.parents.length);
+ assertEquals("", c.getFullMessage());
+
+ final PersonIdent cAuthor = c.getAuthorIdent();
+ assertNotNull(cAuthor);
+ assertEquals(authorName, cAuthor.getName());
+ assertEquals(authorEmail, cAuthor.getEmailAddress());
+
+ final PersonIdent cCommitter = c.getCommitterIdent();
+ assertNotNull(cCommitter);
+ assertEquals(committerName, cCommitter.getName());
+ assertEquals(committerEmail, cCommitter.getEmailAddress());
+ }
+
+ private RevCommit create(final String msg) throws Exception {
+ final StringBuilder b = new StringBuilder();
+ b.append("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n");
+ b.append("author A U. Thor <a_u_thor@example.com> 1218123387 +0700\n");
+ b.append("committer C O. Miter <c@example.com> 1218123390 -0500\n");
+ b.append("\n");
+ b.append(msg);
+
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toString().getBytes("UTF-8"));
+ return c;
+ }
+
+ public void testParse_WeirdHeaderOnlyCommit() throws Exception {
+ final StringBuilder b = new StringBuilder();
+ b.append("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n");
+ b.append("author A U. Thor <a_u_thor@example.com> 1218123387 +0700\n");
+ b.append("committer C O. Miter <c@example.com> 1218123390 -0500\n");
+
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toString().getBytes("UTF-8"));
+
+ assertEquals("", c.getFullMessage());
+ assertEquals("", c.getShortMessage());
+ }
+
+ public void testParse_implicit_UTF8_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n".getBytes("UTF-8"));
+ b.write("author F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n".getBytes("UTF-8"));
+ b.write("committer C O. Miter <c@example.com> 1218123390 -0500\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Sm\u00f6rg\u00e5sbord\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67")); // bogus id
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertSame(Constants.CHARSET, c.getEncoding());
+ assertEquals("F\u00f6r fattare", c.getAuthorIdent().getName());
+ assertEquals("Sm\u00f6rg\u00e5sbord", c.getShortMessage());
+ assertEquals("Sm\u00f6rg\u00e5sbord\n\n\u304d\u308c\u3044\n", c.getFullMessage());
+ }
+
+ public void testParse_implicit_mixed_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n".getBytes("UTF-8"));
+ b.write("author F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n".getBytes("ISO-8859-1"));
+ b.write("committer C O. Miter <c@example.com> 1218123390 -0500\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Sm\u00f6rg\u00e5sbord\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67")); // bogus id
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertSame(Constants.CHARSET, c.getEncoding());
+ assertEquals("F\u00f6r fattare", c.getAuthorIdent().getName());
+ assertEquals("Sm\u00f6rg\u00e5sbord", c.getShortMessage());
+ assertEquals("Sm\u00f6rg\u00e5sbord\n\n\u304d\u308c\u3044\n", c.getFullMessage());
+ }
+
+ /**
+ * Test parsing of a commit whose encoding is given and works.
+ *
+ * @throws Exception
+ */
+ public void testParse_explicit_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n".getBytes("EUC-JP"));
+ b.write("author F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n".getBytes("EUC-JP"));
+ b.write("committer C O. Miter <c@example.com> 1218123390 -0500\n".getBytes("EUC-JP"));
+ b.write("encoding euc_JP\n".getBytes("EUC-JP"));
+ b.write("\n".getBytes("EUC-JP"));
+ b.write("\u304d\u308c\u3044\n".getBytes("EUC-JP"));
+ b.write("\n".getBytes("EUC-JP"));
+ b.write("Hi\n".getBytes("EUC-JP"));
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67")); // bogus id
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("EUC-JP", c.getEncoding().name());
+ assertEquals("F\u00f6r fattare", c.getAuthorIdent().getName());
+ assertEquals("\u304d\u308c\u3044", c.getShortMessage());
+ assertEquals("\u304d\u308c\u3044\n\nHi\n", c.getFullMessage());
+ }
+
+ /**
+ * This is a twisted case, but show what we expect here. We can revise the
+ * expectations provided this case is updated.
+ *
+ * What happens here is that an encoding us given, but data is not encoded
+ * that way (and we can detect it), so we try other encodings.
+ *
+ * @throws Exception
+ */
+ public void testParse_explicit_bad_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n".getBytes("UTF-8"));
+ b.write("author F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n".getBytes("ISO-8859-1"));
+ b.write("committer C O. Miter <c@example.com> 1218123390 -0500\n".getBytes("UTF-8"));
+ b.write("encoding EUC-JP\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Hi\n".getBytes("UTF-8"));
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67")); // bogus id
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("EUC-JP", c.getEncoding().name());
+ assertEquals("F\u00f6r fattare", c.getAuthorIdent().getName());
+ assertEquals("\u304d\u308c\u3044", c.getShortMessage());
+ assertEquals("\u304d\u308c\u3044\n\nHi\n", c.getFullMessage());
+ }
+
+ /**
+ * This is a twisted case too, but show what we expect here. We can revise the
+ * expectations provided this case is updated.
+ *
+ * What happens here is that an encoding us given, but data is not encoded
+ * that way (and we can detect it), so we try other encodings. Here data could
+ * actually be decoded in the stated encoding, but we override using UTF-8.
+ *
+ * @throws Exception
+ */
+ public void testParse_explicit_bad_encoded2() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("tree 9788669ad918b6fcce64af8882fc9a81cb6aba67\n".getBytes("UTF-8"));
+ b.write("author F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n".getBytes("UTF-8"));
+ b.write("committer C O. Miter <c@example.com> 1218123390 -0500\n".getBytes("UTF-8"));
+ b.write("encoding ISO-8859-1\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Hi\n".getBytes("UTF-8"));
+ final RevCommit c;
+ c = new RevCommit(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67")); // bogus id
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("ISO-8859-1", c.getEncoding().name());
+ assertEquals("F\u00f6r fattare", c.getAuthorIdent().getName());
+ assertEquals("\u304d\u308c\u3044", c.getShortMessage());
+ assertEquals("\u304d\u308c\u3044\n\nHi\n", c.getFullMessage());
+ }
+
+ public void testParse_NoMessage() throws Exception {
+ final String msg = "";
+ final RevCommit c = create(msg);
+ assertEquals(msg, c.getFullMessage());
+ assertEquals(msg, c.getShortMessage());
+ }
+
+ public void testParse_OnlyLFMessage() throws Exception {
+ final RevCommit c = create("\n");
+ assertEquals("\n", c.getFullMessage());
+ assertEquals("", c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyNoLF() throws Exception {
+ final String shortMsg = "This is a short message.";
+ final RevCommit c = create(shortMsg);
+ assertEquals(shortMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyEndLF() throws Exception {
+ final String shortMsg = "This is a short message.";
+ final String fullMsg = shortMsg + "\n";
+ final RevCommit c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyEmbeddedLF() throws Exception {
+ final String fullMsg = "This is a\nshort message.";
+ final String shortMsg = fullMsg.replace('\n', ' ');
+ final RevCommit c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyEmbeddedAndEndingLF() throws Exception {
+ final String fullMsg = "This is a\nshort message.\n";
+ final String shortMsg = "This is a short message.";
+ final RevCommit c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_GitStyleMessage() throws Exception {
+ final String shortMsg = "This fixes a bug.";
+ final String body = "We do it with magic and pixie dust and stuff.\n"
+ + "\n" + "Signed-off-by: A U. Thor <author@example.com>\n";
+ final String fullMsg = shortMsg + "\n" + "\n" + body;
+ final RevCommit c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ private static ObjectId id(final String str) {
+ return ObjectId.fromString(str);
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevFlagSetTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevFlagSetTest.java
new file mode 100644
index 0000000000..13f1cfc4cc
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevFlagSetTest.java
@@ -0,0 +1,137 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.util.Arrays;
+import java.util.Iterator;
+
+public class RevFlagSetTest extends RevWalkTestCase {
+ public void testEmpty() {
+ final RevFlagSet set = new RevFlagSet();
+ assertEquals(0, set.mask);
+ assertEquals(0, set.size());
+ assertNotNull(set.iterator());
+ assertFalse(set.iterator().hasNext());
+ }
+
+ public void testAddOne() {
+ final String flagName = "flag";
+ final RevFlag flag = rw.newFlag(flagName);
+ assertTrue(0 != flag.mask);
+ assertSame(flagName, flag.name);
+
+ final RevFlagSet set = new RevFlagSet();
+ assertTrue(set.add(flag));
+ assertFalse(set.add(flag));
+ assertEquals(flag.mask, set.mask);
+ assertEquals(1, set.size());
+ final Iterator<RevFlag> i = set.iterator();
+ assertTrue(i.hasNext());
+ assertSame(flag, i.next());
+ assertFalse(i.hasNext());
+ }
+
+ public void testAddTwo() {
+ final RevFlag flag1 = rw.newFlag("flag_1");
+ final RevFlag flag2 = rw.newFlag("flag_2");
+ assertTrue((flag1.mask & flag2.mask) == 0);
+
+ final RevFlagSet set = new RevFlagSet();
+ assertTrue(set.add(flag1));
+ assertTrue(set.add(flag2));
+ assertEquals(flag1.mask | flag2.mask, set.mask);
+ assertEquals(2, set.size());
+ }
+
+ public void testContainsAll() {
+ final RevFlag flag1 = rw.newFlag("flag_1");
+ final RevFlag flag2 = rw.newFlag("flag_2");
+ final RevFlagSet set1 = new RevFlagSet();
+ assertTrue(set1.add(flag1));
+ assertTrue(set1.add(flag2));
+
+ assertTrue(set1.containsAll(set1));
+ assertTrue(set1.containsAll(Arrays
+ .asList(new RevFlag[] { flag1, flag2 })));
+
+ final RevFlagSet set2 = new RevFlagSet();
+ set2.add(rw.newFlag("flag_3"));
+ assertFalse(set1.containsAll(set2));
+ }
+
+ public void testEquals() {
+ final RevFlag flag1 = rw.newFlag("flag_1");
+ final RevFlag flag2 = rw.newFlag("flag_2");
+ final RevFlagSet set = new RevFlagSet();
+ assertTrue(set.add(flag1));
+ assertTrue(set.add(flag2));
+
+ assertTrue(new RevFlagSet(set).equals(set));
+ assertTrue(new RevFlagSet(Arrays.asList(new RevFlag[] { flag1, flag2 }))
+ .equals(set));
+ }
+
+ public void testRemove() {
+ final RevFlag flag1 = rw.newFlag("flag_1");
+ final RevFlag flag2 = rw.newFlag("flag_2");
+ final RevFlagSet set = new RevFlagSet();
+ assertTrue(set.add(flag1));
+ assertTrue(set.add(flag2));
+
+ assertTrue(set.remove(flag1));
+ assertFalse(set.remove(flag1));
+ assertEquals(flag2.mask, set.mask);
+ assertFalse(set.contains(flag1));
+ }
+
+ public void testContains() {
+ final RevFlag flag1 = rw.newFlag("flag_1");
+ final RevFlag flag2 = rw.newFlag("flag_2");
+ final RevFlagSet set = new RevFlagSet();
+ set.add(flag1);
+ assertTrue(set.contains(flag1));
+ assertFalse(set.contains(flag2));
+ assertFalse(set.contains("bob"));
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevObjectTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevObjectTest.java
new file mode 100644
index 0000000000..87ecaa8c53
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevObjectTest.java
@@ -0,0 +1,177 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import org.eclipse.jgit.lib.AnyObjectId;
+import org.eclipse.jgit.lib.Constants;
+
+public class RevObjectTest extends RevWalkTestCase {
+ public void testId() throws Exception {
+ final RevCommit a = commit();
+ assertSame(a, a.getId());
+ }
+
+ public void testEqualsIsIdentity() throws Exception {
+ final RevCommit a1 = commit();
+ final RevCommit b1 = commit();
+
+ assertTrue(a1.equals(a1));
+ assertTrue(a1.equals((Object) a1));
+ assertFalse(a1.equals(b1));
+
+ assertFalse(a1.equals(a1.copy()));
+ assertFalse(a1.equals((Object) a1.copy()));
+ assertFalse(a1.equals(""));
+
+ final RevWalk rw2 = new RevWalk(db);
+ final RevCommit a2 = rw2.parseCommit(a1);
+ final RevCommit b2 = rw2.parseCommit(b1);
+ assertNotSame(a1, a2);
+ assertNotSame(b1, b2);
+
+ assertFalse(a1.equals(a2));
+ assertFalse(b1.equals(b2));
+
+ assertEquals(a1.hashCode(), a2.hashCode());
+ assertEquals(b1.hashCode(), b2.hashCode());
+
+ assertTrue(AnyObjectId.equals(a1, a2));
+ assertTrue(AnyObjectId.equals(b1, b2));
+ }
+
+ public void testRevObjectTypes() throws Exception {
+ assertEquals(Constants.OBJ_TREE, emptyTree.getType());
+ assertEquals(Constants.OBJ_COMMIT, commit().getType());
+ assertEquals(Constants.OBJ_BLOB, blob("").getType());
+ assertEquals(Constants.OBJ_TAG, tag("emptyTree", emptyTree).getType());
+ }
+
+ public void testHasRevFlag() throws Exception {
+ final RevCommit a = commit();
+ assertFalse(a.has(RevFlag.UNINTERESTING));
+ a.flags |= RevWalk.UNINTERESTING;
+ assertTrue(a.has(RevFlag.UNINTERESTING));
+ }
+
+ public void testHasAnyFlag() throws Exception {
+ final RevCommit a = commit();
+ final RevFlag flag1 = rw.newFlag("flag1");
+ final RevFlag flag2 = rw.newFlag("flag2");
+ final RevFlagSet s = new RevFlagSet();
+ s.add(flag1);
+ s.add(flag2);
+
+ assertFalse(a.hasAny(s));
+ a.flags |= flag1.mask;
+ assertTrue(a.hasAny(s));
+ }
+
+ public void testHasAllFlag() throws Exception {
+ final RevCommit a = commit();
+ final RevFlag flag1 = rw.newFlag("flag1");
+ final RevFlag flag2 = rw.newFlag("flag2");
+ final RevFlagSet s = new RevFlagSet();
+ s.add(flag1);
+ s.add(flag2);
+
+ assertFalse(a.hasAll(s));
+ a.flags |= flag1.mask;
+ assertFalse(a.hasAll(s));
+ a.flags |= flag2.mask;
+ assertTrue(a.hasAll(s));
+ }
+
+ public void testAddRevFlag() throws Exception {
+ final RevCommit a = commit();
+ final RevFlag flag1 = rw.newFlag("flag1");
+ final RevFlag flag2 = rw.newFlag("flag2");
+ assertEquals(0, a.flags);
+
+ a.add(flag1);
+ assertEquals(flag1.mask, a.flags);
+
+ a.add(flag2);
+ assertEquals(flag1.mask | flag2.mask, a.flags);
+ }
+
+ public void testAddRevFlagSet() throws Exception {
+ final RevCommit a = commit();
+ final RevFlag flag1 = rw.newFlag("flag1");
+ final RevFlag flag2 = rw.newFlag("flag2");
+ final RevFlagSet s = new RevFlagSet();
+ s.add(flag1);
+ s.add(flag2);
+
+ assertEquals(0, a.flags);
+
+ a.add(s);
+ assertEquals(flag1.mask | flag2.mask, a.flags);
+ }
+
+ public void testRemoveRevFlag() throws Exception {
+ final RevCommit a = commit();
+ final RevFlag flag1 = rw.newFlag("flag1");
+ final RevFlag flag2 = rw.newFlag("flag2");
+ a.add(flag1);
+ a.add(flag2);
+ assertEquals(flag1.mask | flag2.mask, a.flags);
+ a.remove(flag2);
+ assertEquals(flag1.mask, a.flags);
+ }
+
+ public void testRemoveRevFlagSet() throws Exception {
+ final RevCommit a = commit();
+ final RevFlag flag1 = rw.newFlag("flag1");
+ final RevFlag flag2 = rw.newFlag("flag2");
+ final RevFlag flag3 = rw.newFlag("flag3");
+ final RevFlagSet s = new RevFlagSet();
+ s.add(flag1);
+ s.add(flag2);
+ a.add(flag3);
+ a.add(s);
+ assertEquals(flag1.mask | flag2.mask | flag3.mask, a.flags);
+ a.remove(s);
+ assertEquals(flag3.mask, a.flags);
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevQueueTestCase.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevQueueTestCase.java
new file mode 100644
index 0000000000..24e84b041d
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevQueueTestCase.java
@@ -0,0 +1,91 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+public abstract class RevQueueTestCase<T extends AbstractRevQueue> extends
+ RevWalkTestCase {
+ protected T q;
+
+ public void setUp() throws Exception {
+ super.setUp();
+ q = create();
+ }
+
+ protected abstract T create();
+
+ public void testEmpty() throws Exception {
+ assertNull(q.next());
+ assertTrue(q.everbodyHasFlag(RevWalk.UNINTERESTING));
+ assertFalse(q.anybodyHasFlag(RevWalk.UNINTERESTING));
+ }
+
+ public void testClear() throws Exception {
+ final RevCommit a = parse(commit());
+ final RevCommit b = parse(commit(a));
+
+ q.add(a);
+ q.add(b);
+ q.clear();
+ assertNull(q.next());
+ }
+
+ public void testHasFlags() throws Exception {
+ final RevCommit a = parse(commit());
+ final RevCommit b = parse(commit(a));
+
+ q.add(a);
+ q.add(b);
+
+ assertFalse(q.everbodyHasFlag(RevWalk.UNINTERESTING));
+ assertFalse(q.anybodyHasFlag(RevWalk.UNINTERESTING));
+
+ a.flags |= RevWalk.UNINTERESTING;
+ assertFalse(q.everbodyHasFlag(RevWalk.UNINTERESTING));
+ assertTrue(q.anybodyHasFlag(RevWalk.UNINTERESTING));
+
+ b.flags |= RevWalk.UNINTERESTING;
+ assertTrue(q.everbodyHasFlag(RevWalk.UNINTERESTING));
+ assertTrue(q.anybodyHasFlag(RevWalk.UNINTERESTING));
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevTagParseTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevTagParseTest.java
new file mode 100644
index 0000000000..8800536d27
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevTagParseTest.java
@@ -0,0 +1,356 @@
+/*
+ * Copyright (C) 2008-2009, Google Inc.
+ * 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.revwalk;
+
+import java.io.ByteArrayOutputStream;
+
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.PersonIdent;
+import org.eclipse.jgit.lib.RepositoryTestCase;
+
+public class RevTagParseTest extends RepositoryTestCase {
+ public void testTagBlob() throws Exception {
+ testOneType(Constants.OBJ_BLOB);
+ }
+
+ public void testTagTree() throws Exception {
+ testOneType(Constants.OBJ_TREE);
+ }
+
+ public void testTagCommit() throws Exception {
+ testOneType(Constants.OBJ_COMMIT);
+ }
+
+ public void testTagTag() throws Exception {
+ testOneType(Constants.OBJ_TAG);
+ }
+
+ private void testOneType(final int typeCode) throws Exception {
+ final ObjectId id = id("9788669ad918b6fcce64af8882fc9a81cb6aba67");
+ final StringBuilder b = new StringBuilder();
+ b.append("object " + id.name() + "\n");
+ b.append("type " + Constants.typeString(typeCode) + "\n");
+ b.append("tag v1.2.3.4.5\n");
+ b.append("tagger A U. Thor <a_u_thor@example.com> 1218123387 +0700\n");
+ b.append("\n");
+
+ final RevWalk rw = new RevWalk(db);
+ final RevTag c;
+
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ assertNull(c.getObject());
+ assertNull(c.getTagName());
+
+ c.parseCanonical(rw, b.toString().getBytes("UTF-8"));
+ assertNotNull(c.getObject());
+ assertEquals(id, c.getObject().getId());
+ assertSame(rw.lookupAny(id, typeCode), c.getObject());
+ }
+
+ public void testParseAllFields() throws Exception {
+ final ObjectId treeId = id("9788669ad918b6fcce64af8882fc9a81cb6aba67");
+ final String name = "v1.2.3.4.5";
+ final String taggerName = "A U. Thor";
+ final String taggerEmail = "a_u_thor@example.com";
+ final int taggerTime = 1218123387;
+
+ final StringBuilder body = new StringBuilder();
+
+ body.append("object ");
+ body.append(treeId.name());
+ body.append("\n");
+
+ body.append("type tree\n");
+
+ body.append("tag ");
+ body.append(name);
+ body.append("\n");
+
+ body.append("tagger ");
+ body.append(taggerName);
+ body.append(" <");
+ body.append(taggerEmail);
+ body.append("> ");
+ body.append(taggerTime);
+ body.append(" +0700\n");
+
+ body.append("\n");
+
+ final RevWalk rw = new RevWalk(db);
+ final RevTag c;
+
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ assertNull(c.getObject());
+ assertNull(c.getTagName());
+
+ c.parseCanonical(rw, body.toString().getBytes("UTF-8"));
+ assertNotNull(c.getObject());
+ assertEquals(treeId, c.getObject().getId());
+ assertSame(rw.lookupTree(treeId), c.getObject());
+
+ assertNotNull(c.getTagName());
+ assertEquals(name, c.getTagName());
+ assertEquals("", c.getFullMessage());
+
+ final PersonIdent cTagger = c.getTaggerIdent();
+ assertNotNull(cTagger);
+ assertEquals(taggerName, cTagger.getName());
+ assertEquals(taggerEmail, cTagger.getEmailAddress());
+ }
+
+ private RevTag create(final String msg) throws Exception {
+ final StringBuilder b = new StringBuilder();
+ b.append("object 9788669ad918b6fcce64af8882fc9a81cb6aba67\n");
+ b.append("type tree\n");
+ b.append("tag v1.2.3.4.5\n");
+ b.append("tagger A U. Thor <a_u_thor@example.com> 1218123387 +0700\n");
+ b.append("\n");
+ b.append(msg);
+
+ final RevTag c;
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toString().getBytes("UTF-8"));
+ return c;
+ }
+
+ public void testParse_implicit_UTF8_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("object 9788669ad918b6fcce64af8882fc9a81cb6aba67\n"
+ .getBytes("UTF-8"));
+ b.write("type tree\n".getBytes("UTF-8"));
+ b.write("tag v1.2.3.4.5\n".getBytes("UTF-8"));
+
+ b
+ .write("tagger F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n"
+ .getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Sm\u00f6rg\u00e5sbord\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ final RevTag c;
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("F\u00f6r fattare", c.getTaggerIdent().getName());
+ assertEquals("Sm\u00f6rg\u00e5sbord", c.getShortMessage());
+ assertEquals("Sm\u00f6rg\u00e5sbord\n\n\u304d\u308c\u3044\n", c
+ .getFullMessage());
+ }
+
+ public void testParse_implicit_mixed_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("object 9788669ad918b6fcce64af8882fc9a81cb6aba67\n"
+ .getBytes("UTF-8"));
+ b.write("type tree\n".getBytes("UTF-8"));
+ b.write("tag v1.2.3.4.5\n".getBytes("UTF-8"));
+ b
+ .write("tagger F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n"
+ .getBytes("ISO-8859-1"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Sm\u00f6rg\u00e5sbord\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ final RevTag c;
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("F\u00f6r fattare", c.getTaggerIdent().getName());
+ assertEquals("Sm\u00f6rg\u00e5sbord", c.getShortMessage());
+ assertEquals("Sm\u00f6rg\u00e5sbord\n\n\u304d\u308c\u3044\n", c
+ .getFullMessage());
+ }
+
+ /**
+ * Test parsing of a commit whose encoding is given and works.
+ *
+ * @throws Exception
+ */
+ public void testParse_explicit_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("object 9788669ad918b6fcce64af8882fc9a81cb6aba67\n"
+ .getBytes("EUC-JP"));
+ b.write("type tree\n".getBytes("EUC-JP"));
+ b.write("tag v1.2.3.4.5\n".getBytes("EUC-JP"));
+ b
+ .write("tagger F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n"
+ .getBytes("EUC-JP"));
+ b.write("encoding euc_JP\n".getBytes("EUC-JP"));
+ b.write("\n".getBytes("EUC-JP"));
+ b.write("\u304d\u308c\u3044\n".getBytes("EUC-JP"));
+ b.write("\n".getBytes("EUC-JP"));
+ b.write("Hi\n".getBytes("EUC-JP"));
+ final RevTag c;
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("F\u00f6r fattare", c.getTaggerIdent().getName());
+ assertEquals("\u304d\u308c\u3044", c.getShortMessage());
+ assertEquals("\u304d\u308c\u3044\n\nHi\n", c.getFullMessage());
+ }
+
+ /**
+ * This is a twisted case, but show what we expect here. We can revise the
+ * expectations provided this case is updated.
+ *
+ * What happens here is that an encoding us given, but data is not encoded
+ * that way (and we can detect it), so we try other encodings.
+ *
+ * @throws Exception
+ */
+ public void testParse_explicit_bad_encoded() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("object 9788669ad918b6fcce64af8882fc9a81cb6aba67\n"
+ .getBytes("UTF-8"));
+ b.write("type tree\n".getBytes("UTF-8"));
+ b.write("tag v1.2.3.4.5\n".getBytes("UTF-8"));
+ b
+ .write("tagger F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n"
+ .getBytes("ISO-8859-1"));
+ b.write("encoding EUC-JP\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Hi\n".getBytes("UTF-8"));
+ final RevTag c;
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("F\u00f6r fattare", c.getTaggerIdent().getName());
+ assertEquals("\u304d\u308c\u3044", c.getShortMessage());
+ assertEquals("\u304d\u308c\u3044\n\nHi\n", c.getFullMessage());
+ }
+
+ /**
+ * This is a twisted case too, but show what we expect here. We can revise
+ * the expectations provided this case is updated.
+ *
+ * What happens here is that an encoding us given, but data is not encoded
+ * that way (and we can detect it), so we try other encodings. Here data
+ * could actually be decoded in the stated encoding, but we override using
+ * UTF-8.
+ *
+ * @throws Exception
+ */
+ public void testParse_explicit_bad_encoded2() throws Exception {
+ final ByteArrayOutputStream b = new ByteArrayOutputStream();
+ b.write("object 9788669ad918b6fcce64af8882fc9a81cb6aba67\n"
+ .getBytes("UTF-8"));
+ b.write("type tree\n".getBytes("UTF-8"));
+ b.write("tag v1.2.3.4.5\n".getBytes("UTF-8"));
+ b
+ .write("tagger F\u00f6r fattare <a_u_thor@example.com> 1218123387 +0700\n"
+ .getBytes("UTF-8"));
+ b.write("encoding ISO-8859-1\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("\u304d\u308c\u3044\n".getBytes("UTF-8"));
+ b.write("\n".getBytes("UTF-8"));
+ b.write("Hi\n".getBytes("UTF-8"));
+ final RevTag c;
+ c = new RevTag(id("9473095c4cb2f12aefe1db8a355fe3fafba42f67"));
+ c.parseCanonical(new RevWalk(db), b.toByteArray());
+
+ assertEquals("F\u00f6r fattare", c.getTaggerIdent().getName());
+ assertEquals("\u304d\u308c\u3044", c.getShortMessage());
+ assertEquals("\u304d\u308c\u3044\n\nHi\n", c.getFullMessage());
+ }
+
+ public void testParse_NoMessage() throws Exception {
+ final String msg = "";
+ final RevTag c = create(msg);
+ assertEquals(msg, c.getFullMessage());
+ assertEquals(msg, c.getShortMessage());
+ }
+
+ public void testParse_OnlyLFMessage() throws Exception {
+ final RevTag c = create("\n");
+ assertEquals("\n", c.getFullMessage());
+ assertEquals("", c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyNoLF() throws Exception {
+ final String shortMsg = "This is a short message.";
+ final RevTag c = create(shortMsg);
+ assertEquals(shortMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyEndLF() throws Exception {
+ final String shortMsg = "This is a short message.";
+ final String fullMsg = shortMsg + "\n";
+ final RevTag c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyEmbeddedLF() throws Exception {
+ final String fullMsg = "This is a\nshort message.";
+ final String shortMsg = fullMsg.replace('\n', ' ');
+ final RevTag c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_ShortLineOnlyEmbeddedAndEndingLF() throws Exception {
+ final String fullMsg = "This is a\nshort message.\n";
+ final String shortMsg = "This is a short message.";
+ final RevTag c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ public void testParse_GitStyleMessage() throws Exception {
+ final String shortMsg = "This fixes a bug.";
+ final String body = "We do it with magic and pixie dust and stuff.\n"
+ + "\n" + "Signed-off-by: A U. Thor <author@example.com>\n";
+ final String fullMsg = shortMsg + "\n" + "\n" + body;
+ final RevTag c = create(fullMsg);
+ assertEquals(fullMsg, c.getFullMessage());
+ assertEquals(shortMsg, c.getShortMessage());
+ }
+
+ private static ObjectId id(final String str) {
+ return ObjectId.fromString(str);
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkCullTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkCullTest.java
new file mode 100644
index 0000000000..9e879c5f0d
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkCullTest.java
@@ -0,0 +1,100 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+public class RevWalkCullTest extends RevWalkTestCase {
+ public void testProperlyCullAllAncestors1() throws Exception {
+ // Credit goes to Junio C Hamano <gitster@pobox.com> for this
+ // test case in git-core (t/t6009-rev-list-parent.sh)
+ //
+ // We induce a clock skew so two is dated before one.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(-2400, a);
+ final RevCommit c = commit(b);
+ final RevCommit d = commit(c);
+
+ markStart(a);
+ markUninteresting(d);
+ assertNull(rw.next());
+ }
+
+ public void testProperlyCullAllAncestors2() throws Exception {
+ // Despite clock skew on c1 being very old it should not
+ // produce, neither should a or b, or any part of that chain.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(-5, b);
+ final RevCommit c2 = commit(10, b);
+ final RevCommit d = commit(c1, c2);
+
+ markStart(d);
+ markUninteresting(c1);
+ assertCommit(d, rw.next());
+ assertCommit(c2, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testProperlyCullAllAncestors_LongHistory() throws Exception {
+ final RevCommit a = commit();
+ RevCommit b = commit(a);
+ for (int i = 0; i < 24; i++) {
+ b = commit(b);
+ if ((i & 2) == 0)
+ markUninteresting(b);
+ }
+ final RevCommit c = commit(b);
+
+ markStart(c);
+ markUninteresting(b);
+ assertCommit(c, rw.next());
+ assertNull(rw.next());
+
+ // We should have aborted before we got back so far that "a"
+ // would be parsed. Thus, its parents shouldn't be allocated.
+ //
+ assertNull(a.parents);
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkFilterTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkFilterTest.java
new file mode 100644
index 0000000000..db4c38e72b
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkFilterTest.java
@@ -0,0 +1,297 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.io.IOException;
+import java.util.Date;
+
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.errors.StopWalkException;
+import org.eclipse.jgit.revwalk.filter.AndRevFilter;
+import org.eclipse.jgit.revwalk.filter.CommitTimeRevFilter;
+import org.eclipse.jgit.revwalk.filter.NotRevFilter;
+import org.eclipse.jgit.revwalk.filter.OrRevFilter;
+import org.eclipse.jgit.revwalk.filter.RevFilter;
+
+public class RevWalkFilterTest extends RevWalkTestCase {
+ private static final MyAll MY_ALL = new MyAll();
+
+ public void testFilter_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(RevFilter.ALL);
+ markStart(c);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testFilter_Negate_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(RevFilter.ALL.negate());
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NOT_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(NotRevFilter.create(RevFilter.ALL));
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NONE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(RevFilter.NONE);
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NOT_NONE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(NotRevFilter.create(RevFilter.NONE));
+ markStart(c);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testFilter_ALL_And_NONE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(AndRevFilter.create(RevFilter.ALL, RevFilter.NONE));
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NONE_And_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(AndRevFilter.create(RevFilter.NONE, RevFilter.ALL));
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_ALL_Or_NONE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(OrRevFilter.create(RevFilter.ALL, RevFilter.NONE));
+ markStart(c);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NONE_Or_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(OrRevFilter.create(RevFilter.NONE, RevFilter.ALL));
+ markStart(c);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testFilter_MY_ALL_And_NONE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(AndRevFilter.create(MY_ALL, RevFilter.NONE));
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NONE_And_MY_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(AndRevFilter.create(RevFilter.NONE, MY_ALL));
+ markStart(c);
+ assertNull(rw.next());
+ }
+
+ public void testFilter_MY_ALL_Or_NONE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(OrRevFilter.create(MY_ALL, RevFilter.NONE));
+ markStart(c);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NONE_Or_MY_ALL() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+
+ rw.setRevFilter(OrRevFilter.create(RevFilter.NONE, MY_ALL));
+ markStart(c);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testFilter_NO_MERGES() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(b);
+ final RevCommit c2 = commit(b);
+ final RevCommit d = commit(c1, c2);
+ final RevCommit e = commit(d);
+
+ rw.setRevFilter(RevFilter.NO_MERGES);
+ markStart(e);
+ assertCommit(e, rw.next());
+ assertCommit(c2, rw.next());
+ assertCommit(c1, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testCommitTimeRevFilter() throws Exception {
+ final RevCommit a = commit();
+ tick(100);
+
+ final RevCommit b = commit(a);
+ tick(100);
+
+ Date since = new Date(nowTick);
+ final RevCommit c1 = commit(b);
+ tick(100);
+
+ final RevCommit c2 = commit(b);
+ tick(100);
+
+ Date until = new Date(nowTick);
+ final RevCommit d = commit(c1, c2);
+ tick(100);
+
+ final RevCommit e = commit(d);
+
+ {
+ RevFilter after = CommitTimeRevFilter.after(since);
+ assertNotNull(after);
+ rw.setRevFilter(after);
+ markStart(e);
+ assertCommit(e, rw.next());
+ assertCommit(d, rw.next());
+ assertCommit(c2, rw.next());
+ assertCommit(c1, rw.next());
+ assertNull(rw.next());
+ }
+
+ {
+ RevFilter before = CommitTimeRevFilter.before(until);
+ assertNotNull(before);
+ rw.reset();
+ rw.setRevFilter(before);
+ markStart(e);
+ assertCommit(c2, rw.next());
+ assertCommit(c1, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ {
+ RevFilter between = CommitTimeRevFilter.between(since, until);
+ assertNotNull(between);
+ rw.reset();
+ rw.setRevFilter(between);
+ markStart(e);
+ assertCommit(c2, rw.next());
+ assertCommit(c1, rw.next());
+ assertNull(rw.next());
+ }
+ }
+
+ private static class MyAll extends RevFilter {
+ @Override
+ public RevFilter clone() {
+ return this;
+ }
+
+ @Override
+ public boolean include(RevWalk walker, RevCommit cmit)
+ throws StopWalkException, MissingObjectException,
+ IncorrectObjectTypeException, IOException {
+ return true;
+ }
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkMergeBaseTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkMergeBaseTest.java
new file mode 100644
index 0000000000..10c9f9b12e
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkMergeBaseTest.java
@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import org.eclipse.jgit.revwalk.filter.RevFilter;
+import org.eclipse.jgit.treewalk.filter.TreeFilter;
+
+public class RevWalkMergeBaseTest extends RevWalkTestCase {
+ public void testNone() throws Exception {
+ final RevCommit c1 = commit(commit(commit()));
+ final RevCommit c2 = commit(commit(commit()));
+
+ rw.setRevFilter(RevFilter.MERGE_BASE);
+ markStart(c1);
+ markStart(c2);
+ assertNull(rw.next());
+ }
+
+ public void testDisallowTreeFilter() throws Exception {
+ final RevCommit c1 = commit();
+ final RevCommit c2 = commit();
+
+ rw.setRevFilter(RevFilter.MERGE_BASE);
+ rw.setTreeFilter(TreeFilter.ANY_DIFF);
+ markStart(c1);
+ markStart(c2);
+ try {
+ assertNull(rw.next());
+ fail("did not throw IllegalStateException");
+ } catch (IllegalStateException ise) {
+ // expected result
+ }
+ }
+
+ public void testSimple() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(commit(commit(commit(commit(b)))));
+ final RevCommit c2 = commit(commit(commit(commit(commit(b)))));
+
+ rw.setRevFilter(RevFilter.MERGE_BASE);
+ markStart(c1);
+ markStart(c2);
+ assertCommit(b, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testMultipleHeads_SameBase1() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(commit(commit(commit(commit(b)))));
+ final RevCommit c2 = commit(commit(commit(commit(commit(b)))));
+ final RevCommit c3 = commit(commit(commit(b)));
+
+ rw.setRevFilter(RevFilter.MERGE_BASE);
+ markStart(c1);
+ markStart(c2);
+ markStart(c3);
+ assertCommit(b, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testMultipleHeads_SameBase2() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+ final RevCommit d1 = commit(commit(commit(commit(commit(b)))));
+ final RevCommit d2 = commit(commit(commit(commit(commit(c)))));
+ final RevCommit d3 = commit(commit(commit(c)));
+
+ rw.setRevFilter(RevFilter.MERGE_BASE);
+ markStart(d1);
+ markStart(d2);
+ markStart(d3);
+ assertCommit(b, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testCrissCross() throws Exception {
+ // See http://marc.info/?l=git&m=111463358500362&w=2 for a nice
+ // description of what this test is creating. We don't have a
+ // clean merge base for d,e as they each merged the parents b,c
+ // in different orders.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(a);
+ final RevCommit d = commit(b, c);
+ final RevCommit e = commit(c, b);
+
+ rw.setRevFilter(RevFilter.MERGE_BASE);
+ markStart(d);
+ markStart(e);
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertNull(rw.next());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter1Test.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter1Test.java
new file mode 100644
index 0000000000..986a886566
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter1Test.java
@@ -0,0 +1,182 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.util.Collections;
+
+import org.eclipse.jgit.treewalk.filter.AndTreeFilter;
+import org.eclipse.jgit.treewalk.filter.PathFilterGroup;
+import org.eclipse.jgit.treewalk.filter.TreeFilter;
+
+public class RevWalkPathFilter1Test extends RevWalkTestCase {
+ protected void filter(final String path) {
+ rw.setTreeFilter(AndTreeFilter.create(PathFilterGroup
+ .createFromStrings(Collections.singleton(path)),
+ TreeFilter.ANY_DIFF));
+ }
+
+ public void testEmpty_EmptyTree() throws Exception {
+ final RevCommit a = commit();
+ filter("a");
+ markStart(a);
+ assertNull(rw.next());
+ }
+
+ public void testEmpty_NoMatch() throws Exception {
+ final RevCommit a = commit(tree(file("0", blob("0"))));
+ filter("a");
+ markStart(a);
+ assertNull(rw.next());
+ }
+
+ public void testSimple1() throws Exception {
+ final RevCommit a = commit(tree(file("0", blob("0"))));
+ filter("0");
+ markStart(a);
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testEdits_MatchNone() throws Exception {
+ final RevCommit a = commit(tree(file("0", blob("a"))));
+ final RevCommit b = commit(tree(file("0", blob("b"))), a);
+ final RevCommit c = commit(tree(file("0", blob("c"))), b);
+ final RevCommit d = commit(tree(file("0", blob("d"))), c);
+ filter("a");
+ markStart(d);
+ assertNull(rw.next());
+ }
+
+ public void testEdits_MatchAll() throws Exception {
+ final RevCommit a = commit(tree(file("0", blob("a"))));
+ final RevCommit b = commit(tree(file("0", blob("b"))), a);
+ final RevCommit c = commit(tree(file("0", blob("c"))), b);
+ final RevCommit d = commit(tree(file("0", blob("d"))), c);
+ filter("0");
+ markStart(d);
+ assertCommit(d, rw.next());
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testStringOfPearls_FilePath1() throws Exception {
+ final RevCommit a = commit(tree(file("d/f", blob("a"))));
+ final RevCommit b = commit(tree(file("d/f", blob("a"))), a);
+ final RevCommit c = commit(tree(file("d/f", blob("b"))), b);
+ filter("d/f");
+ markStart(c);
+
+ assertCommit(c, rw.next());
+ assertEquals(1, c.getParentCount());
+ assertCommit(a, c.getParent(0)); // b was skipped
+
+ assertCommit(a, rw.next());
+ assertEquals(0, a.getParentCount());
+ assertNull(rw.next());
+ }
+
+ public void testStringOfPearls_FilePath2() throws Exception {
+ final RevCommit a = commit(tree(file("d/f", blob("a"))));
+ final RevCommit b = commit(tree(file("d/f", blob("a"))), a);
+ final RevCommit c = commit(tree(file("d/f", blob("b"))), b);
+ final RevCommit d = commit(tree(file("d/f", blob("b"))), c);
+ filter("d/f");
+ markStart(d);
+
+ // d was skipped
+ assertCommit(c, rw.next());
+ assertEquals(1, c.getParentCount());
+ assertCommit(a, c.getParent(0)); // b was skipped
+
+ assertCommit(a, rw.next());
+ assertEquals(0, a.getParentCount());
+ assertNull(rw.next());
+ }
+
+ public void testStringOfPearls_DirPath2() throws Exception {
+ final RevCommit a = commit(tree(file("d/f", blob("a"))));
+ final RevCommit b = commit(tree(file("d/f", blob("a"))), a);
+ final RevCommit c = commit(tree(file("d/f", blob("b"))), b);
+ final RevCommit d = commit(tree(file("d/f", blob("b"))), c);
+ filter("d");
+ markStart(d);
+
+ // d was skipped
+ assertCommit(c, rw.next());
+ assertEquals(1, c.getParentCount());
+ assertCommit(a, c.getParent(0)); // b was skipped
+
+ assertCommit(a, rw.next());
+ assertEquals(0, a.getParentCount());
+ assertNull(rw.next());
+ }
+
+ public void testStringOfPearls_FilePath3() throws Exception {
+ final RevCommit a = commit(tree(file("d/f", blob("a"))));
+ final RevCommit b = commit(tree(file("d/f", blob("a"))), a);
+ final RevCommit c = commit(tree(file("d/f", blob("b"))), b);
+ final RevCommit d = commit(tree(file("d/f", blob("b"))), c);
+ final RevCommit e = commit(tree(file("d/f", blob("b"))), d);
+ final RevCommit f = commit(tree(file("d/f", blob("b"))), e);
+ final RevCommit g = commit(tree(file("d/f", blob("b"))), f);
+ final RevCommit h = commit(tree(file("d/f", blob("b"))), g);
+ final RevCommit i = commit(tree(file("d/f", blob("c"))), h);
+ filter("d/f");
+ markStart(i);
+
+ assertCommit(i, rw.next());
+ assertEquals(1, i.getParentCount());
+ assertCommit(c, i.getParent(0)); // h..d was skipped
+
+ assertCommit(c, rw.next());
+ assertEquals(1, c.getParentCount());
+ assertCommit(a, c.getParent(0)); // b was skipped
+
+ assertCommit(a, rw.next());
+ assertEquals(0, a.getParentCount());
+ assertNull(rw.next());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter6012Test.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter6012Test.java
new file mode 100644
index 0000000000..73d41eae64
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkPathFilter6012Test.java
@@ -0,0 +1,168 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.lang.reflect.Field;
+import java.util.Collections;
+import java.util.HashMap;
+
+import org.eclipse.jgit.treewalk.filter.AndTreeFilter;
+import org.eclipse.jgit.treewalk.filter.PathFilterGroup;
+import org.eclipse.jgit.treewalk.filter.TreeFilter;
+
+// Note: Much of this test case is broken as it depends upon
+// the graph applying topological sorting *before* doing merge
+// simplification. It also depends upon a difference between
+// full history and non-full history for a path, something we
+// don't quite yet have a distiction for in JGit.
+//
+public class RevWalkPathFilter6012Test extends RevWalkTestCase {
+ private static final String pA = "pA", pF = "pF", pE = "pE";
+
+ private RevCommit a, b, c, d, e, f, g, h, i;
+
+ private HashMap<RevCommit, String> byName;
+
+ public void setUp() throws Exception {
+ super.setUp();
+
+ // Test graph was stolen from git-core t6012-rev-list-simplify
+ // (by Junio C Hamano in 65347030590bcc251a9ff2ed96487a0f1b9e9fa8)
+ //
+ final RevBlob zF = blob("zF");
+ final RevBlob zH = blob("zH");
+ final RevBlob zI = blob("zI");
+ final RevBlob zS = blob("zS");
+ final RevBlob zY = blob("zY");
+
+ a = commit(tree(file(pF, zH)));
+ b = commit(tree(file(pF, zI)), a);
+ c = commit(tree(file(pF, zI)), a);
+ d = commit(tree(file(pA, zS), file(pF, zI)), c);
+ parse(d);
+ e = commit(d.getTree(), d, b);
+ f = commit(tree(file(pA, zS), file(pE, zY), file(pF, zI)), e);
+ parse(f);
+ g = commit(tree(file(pE, zY), file(pF, zI)), b);
+ h = commit(f.getTree(), g, f);
+ i = commit(tree(file(pA, zS), file(pE, zY), file(pF, zF)), h);
+
+ byName = new HashMap<RevCommit, String>();
+ for (Field z : RevWalkPathFilter6012Test.class.getDeclaredFields()) {
+ if (z.getType() == RevCommit.class)
+ byName.put((RevCommit) z.get(this), z.getName());
+ }
+ }
+
+ protected void check(final RevCommit... order) throws Exception {
+ markStart(i);
+ final StringBuilder act = new StringBuilder();
+ for (final RevCommit z : rw) {
+ final String name = byName.get(z);
+ assertNotNull(name);
+ act.append(name);
+ act.append(' ');
+ }
+ final StringBuilder exp = new StringBuilder();
+ for (final RevCommit z : order) {
+ final String name = byName.get(z);
+ assertNotNull(name);
+ exp.append(name);
+ exp.append(' ');
+ }
+ assertEquals(exp.toString(), act.toString());
+ }
+
+ protected void filter(final String path) {
+ rw.setTreeFilter(AndTreeFilter.create(PathFilterGroup
+ .createFromStrings(Collections.singleton(path)),
+ TreeFilter.ANY_DIFF));
+ }
+
+ public void test1() throws Exception {
+ // TODO --full-history
+ check(i, h, g, f, e, d, c, b, a);
+ }
+
+ public void test2() throws Exception {
+ // TODO --full-history
+ filter(pF);
+ // TODO fix broken test
+ // check(i, h, e, c, b, a);
+ }
+
+ public void test3() throws Exception {
+ // TODO --full-history
+ rw.sort(RevSort.TOPO);
+ filter(pF);
+ // TODO fix broken test
+ // check(i, h, e, c, b, a);
+ }
+
+ public void test4() throws Exception {
+ // TODO --full-history
+ rw.sort(RevSort.COMMIT_TIME_DESC);
+ filter(pF);
+ // TODO fix broken test
+ // check(i, h, e, c, b, a);
+ }
+
+ public void test5() throws Exception {
+ // TODO --simplify-merges
+ filter(pF);
+ // TODO fix broken test
+ // check(i, e, c, b, a);
+ }
+
+ public void test6() throws Exception {
+ filter(pF);
+ check(i, b, a);
+ }
+
+ public void test7() throws Exception {
+ rw.sort(RevSort.TOPO);
+ filter(pF);
+ check(i, b, a);
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkSortTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkSortTest.java
new file mode 100644
index 0000000000..0d3e0cf5aa
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkSortTest.java
@@ -0,0 +1,168 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+public class RevWalkSortTest extends RevWalkTestCase {
+ public void testSort_Default() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(1, a);
+ final RevCommit c = commit(1, b);
+ final RevCommit d = commit(1, c);
+
+ markStart(d);
+ assertCommit(d, rw.next());
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testSort_COMMIT_TIME_DESC() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+ final RevCommit d = commit(c);
+
+ rw.sort(RevSort.COMMIT_TIME_DESC);
+ markStart(d);
+ assertCommit(d, rw.next());
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testSort_REVERSE() throws Exception {
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(b);
+ final RevCommit d = commit(c);
+
+ rw.sort(RevSort.REVERSE);
+ markStart(d);
+ assertCommit(a, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(c, rw.next());
+ assertCommit(d, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testSort_COMMIT_TIME_DESC_OutOfOrder1() throws Exception {
+ // Despite being out of order time-wise, a strand-of-pearls must
+ // still maintain topological order.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c = commit(-5, b);
+ final RevCommit d = commit(10, c);
+ assertTrue(parse(a).getCommitTime() < parse(d).getCommitTime());
+ assertTrue(parse(c).getCommitTime() < parse(b).getCommitTime());
+
+ rw.sort(RevSort.COMMIT_TIME_DESC);
+ markStart(d);
+ assertCommit(d, rw.next());
+ assertCommit(c, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testSort_COMMIT_TIME_DESC_OutOfOrder2() throws Exception {
+ // c1 is back dated before its parent.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(-5, b);
+ final RevCommit c2 = commit(10, b);
+ final RevCommit d = commit(c1, c2);
+
+ rw.sort(RevSort.COMMIT_TIME_DESC);
+ markStart(d);
+ assertCommit(d, rw.next());
+ assertCommit(c2, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertCommit(c1, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testSort_TOPO() throws Exception {
+ // c1 is back dated before its parent.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(-5, b);
+ final RevCommit c2 = commit(10, b);
+ final RevCommit d = commit(c1, c2);
+
+ rw.sort(RevSort.TOPO);
+ markStart(d);
+ assertCommit(d, rw.next());
+ assertCommit(c2, rw.next());
+ assertCommit(c1, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(a, rw.next());
+ assertNull(rw.next());
+ }
+
+ public void testSort_TOPO_REVERSE() throws Exception {
+ // c1 is back dated before its parent.
+ //
+ final RevCommit a = commit();
+ final RevCommit b = commit(a);
+ final RevCommit c1 = commit(-5, b);
+ final RevCommit c2 = commit(10, b);
+ final RevCommit d = commit(c1, c2);
+
+ rw.sort(RevSort.TOPO);
+ rw.sort(RevSort.REVERSE, true);
+ markStart(d);
+ assertCommit(a, rw.next());
+ assertCommit(b, rw.next());
+ assertCommit(c1, rw.next());
+ assertCommit(c2, rw.next());
+ assertCommit(d, rw.next());
+ assertNull(rw.next());
+ }
+}
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkTestCase.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkTestCase.java
new file mode 100644
index 0000000000..50fbce41aa
--- /dev/null
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/revwalk/RevWalkTestCase.java
@@ -0,0 +1,183 @@
+/*
+ * Copyright (C) 2009, Google Inc.
+ * 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.revwalk;
+
+import java.util.Collections;
+import java.util.Date;
+
+import org.eclipse.jgit.dircache.DirCache;
+import org.eclipse.jgit.dircache.DirCacheBuilder;
+import org.eclipse.jgit.dircache.DirCacheEntry;
+import org.eclipse.jgit.lib.Commit;
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.FileMode;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.ObjectWriter;
+import org.eclipse.jgit.lib.PersonIdent;
+import org.eclipse.jgit.lib.RepositoryTestCase;
+import org.eclipse.jgit.lib.Tag;
+import org.eclipse.jgit.lib.Tree;
+import org.eclipse.jgit.treewalk.TreeWalk;
+import org.eclipse.jgit.treewalk.filter.PathFilterGroup;
+
+/** Support for tests of the {@link RevWalk} class. */
+public abstract class RevWalkTestCase extends RepositoryTestCase {
+ protected ObjectWriter ow;
+
+ protected RevTree emptyTree;
+
+ protected long nowTick;
+
+ protected RevWalk rw;
+
+ public void setUp() throws Exception {
+ super.setUp();
+ ow = new ObjectWriter(db);
+ rw = createRevWalk();
+ emptyTree = rw.parseTree(ow.writeTree(new Tree(db)));
+ nowTick = 1236977987000L;
+ }
+
+ protected RevWalk createRevWalk() {
+ return new RevWalk(db);
+ }
+
+ protected void tick(final int secDelta) {
+ nowTick += secDelta * 1000L;
+ }
+
+ protected RevBlob blob(final String content) throws Exception {
+ return rw.lookupBlob(ow.writeBlob(Constants.encode(content)));
+ }
+
+ protected DirCacheEntry file(final String path, final RevBlob blob)
+ throws Exception {
+ final DirCacheEntry e = new DirCacheEntry(path);
+ e.setFileMode(FileMode.REGULAR_FILE);
+ e.setObjectId(blob);
+ return e;
+ }
+
+ protected RevTree tree(final DirCacheEntry... entries) throws Exception {
+ final DirCache dc = DirCache.newInCore();
+ final DirCacheBuilder b = dc.builder();
+ for (final DirCacheEntry e : entries)
+ b.add(e);
+ b.finish();
+ return rw.lookupTree(dc.writeTree(ow));
+ }
+
+ protected RevObject get(final RevTree tree, final String path)
+ throws Exception {
+ final TreeWalk tw = new TreeWalk(db);
+ tw.setFilter(PathFilterGroup.createFromStrings(Collections
+ .singleton(path)));
+ tw.reset(tree);
+ while (tw.next()) {
+ if (tw.isSubtree() && !path.equals(tw.getPathString())) {
+ tw.enterSubtree();
+ continue;
+ }
+ final ObjectId entid = tw.getObjectId(0);
+ final FileMode entmode = tw.getFileMode(0);
+ return rw.lookupAny(entid, entmode.getObjectType());
+ }
+ fail("Can't find " + path + " in tree " + tree.name());
+ return null; // never reached.
+ }
+
+ protected RevCommit commit(final RevCommit... parents) throws Exception {
+ return commit(1, emptyTree, parents);
+ }
+
+ protected RevCommit commit(final RevTree tree, final RevCommit... parents)
+ throws Exception {
+ return commit(1, tree, parents);
+ }
+
+ protected RevCommit commit(final int secDelta, final RevCommit... parents)
+ throws Exception {
+ return commit(secDelta, emptyTree, parents);
+ }
+
+ protected RevCommit commit(final int secDelta, final RevTree tree,
+ final RevCommit... parents) throws Exception {
+ tick(secDelta);
+ final Commit c = new Commit(db);
+ c.setTreeId(tree);
+ c.setParentIds(parents);
+ c.setAuthor(new PersonIdent(jauthor, new Date(nowTick)));
+ c.setCommitter(new PersonIdent(jcommitter, new Date(nowTick)));
+ c.setMessage("");
+ return rw.lookupCommit(ow.writeCommit(c));
+ }
+
+ protected RevTag tag(final String name, final RevObject dst)
+ throws Exception {
+ final Tag t = new Tag(db);
+ t.setType(Constants.typeString(dst.getType()));
+ t.setObjId(dst.toObjectId());
+ t.setTag(name);
+ t.setTagger(new PersonIdent(jcommitter, new Date(nowTick)));
+ t.setMessage("");
+ return (RevTag) rw.lookupAny(ow.writeTag(t), Constants.OBJ_TAG);
+ }
+
+ protected <T extends RevObject> T parse(final T t) throws Exception {
+ rw.parseBody(t);
+ return t;
+ }
+
+ protected void markStart(final RevCommit commit) throws Exception {
+ rw.markStart(commit);
+ }
+
+ protected void markUninteresting(final RevCommit commit) throws Exception {
+ rw.markUninteresting(commit);
+ }
+
+ protected void assertCommit(final RevCommit exp, final RevCommit act) {
+ assertSame(exp, act);
+ }
+}