changeset 561:d3c71498919c

Do not process child revisions before all possible parent paths were visited
author Artem Tikhomirov <tikhomirov.artem@gmail.com>
date Wed, 27 Feb 2013 19:37:58 +0100
parents 52263817b998
children 6fbca6506bb5
files src/org/tmatesoft/hg/internal/IntVector.java src/org/tmatesoft/hg/internal/RangeSeq.java src/org/tmatesoft/hg/repo/HgBlameFacility.java test/org/tmatesoft/hg/test/TestBlame.java
diffstat 4 files changed, 38 insertions(+), 13 deletions(-) [+]
line wrap: on
line diff
--- a/src/org/tmatesoft/hg/internal/IntVector.java	Tue Feb 26 21:06:43 2013 +0100
+++ b/src/org/tmatesoft/hg/internal/IntVector.java	Wed Feb 27 19:37:58 2013 +0100
@@ -16,6 +16,8 @@
  */
 package org.tmatesoft.hg.internal;
 
+import java.util.Arrays;
+
 /**
  * Vector of primitive values
  * 
@@ -101,6 +103,18 @@
 		}
 	}
 
+	/**
+	 * 
+	 * @param ascending <code>true</code> to sort in ascending order, <code>false</code> for descending
+	 */
+	public void sort(boolean ascending) {
+		Arrays.sort(data, 0, count);
+		if (!ascending) {
+			reverse();
+		}
+	}
+
+
 	@Override
 	public String toString() {
 		return String.format("%s[%d]", IntVector.class.getSimpleName(), size());
--- a/src/org/tmatesoft/hg/internal/RangeSeq.java	Tue Feb 26 21:06:43 2013 +0100
+++ b/src/org/tmatesoft/hg/internal/RangeSeq.java	Wed Feb 27 19:37:58 2013 +0100
@@ -170,6 +170,6 @@
 	
 	@Override
 	public String toString() {
-		return String.format("RangeSeq[%d]", count);
+		return String.format("RangeSeq[%d]:%s", count, dump());
 	}
 }
\ No newline at end of file
--- a/src/org/tmatesoft/hg/repo/HgBlameFacility.java	Tue Feb 26 21:06:43 2013 +0100
+++ b/src/org/tmatesoft/hg/repo/HgBlameFacility.java	Wed Feb 27 19:37:58 2013 +0100
@@ -80,7 +80,9 @@
 			df.parents(i, fileRevParents, null, null);
 			fileParentRevs.add(fileRevParents[0], fileRevParents[1]);
 		}
-		// collect file revisions to visit, from newest to oldest
+		// collect file revisions to visit, from newest to oldest:
+		// traverse parents, starting from the given file revision
+		// this ignores all file revision made in parallel to the one of interest
 		IntVector fileRevsToVisit = new IntVector(fileRevIndex + 1, 0);
 		LinkedList<Integer> queue = new LinkedList<Integer>();
 		BitSet seen = new BitSet(fileRevIndex + 1);
@@ -102,6 +104,8 @@
 			}
 		} while (!queue.isEmpty());
 		FileLinesCache fileInfoCache = new FileLinesCache(df, 10);
+		// make sure no child is processed before we handled all (grand-)parents of the element
+		fileRevsToVisit.sort(false);
 		// fileRevsToVisit now { r10, r7, r6, r5, r0 }
 		// and we'll iterate it from behind, e.g. old to new unless reversed 
 		if (iterateOrder == HgIterateDirection.NewToOld) {
--- a/test/org/tmatesoft/hg/test/TestBlame.java	Tue Feb 26 21:06:43 2013 +0100
+++ b/test/org/tmatesoft/hg/test/TestBlame.java	Wed Feb 27 19:37:58 2013 +0100
@@ -97,15 +97,15 @@
 		FileAnnotation.annotate(df, cs, fa);
 
 		op.reset();
-		eh.run("hg", "annotate", "-r", cs == TIP ? "tip" : String.valueOf(cs), df.getPath().toString());
+		eh.run("hg", "annotate", "--no-follow", "-r", cs == TIP ? "tip" : String.valueOf(cs), df.getPath().toString());
 
 		String[] hgAnnotateLines = splitLines(op.result());
 		assertTrue("[sanity]", hgAnnotateLines.length > 0);
 		assertEquals("Number of lines reported by native annotate and our impl", hgAnnotateLines.length, fa.lineRevisions.length);
 
 		for (int i = 0; i < fa.lineRevisions.length; i++) {
-			int hgAnnotateRevIndex = Integer.parseInt(hgAnnotateLines[i].substring(0, hgAnnotateLines[i].indexOf(':')));
-			errorCollector.assertEquals(String.format("Revision mismatch for line %d", i+1), hgAnnotateRevIndex, fa.lineRevisions[i]);
+			int hgAnnotateRevIndex = Integer.parseInt(hgAnnotateLines[i].substring(0, hgAnnotateLines[i].indexOf(':')).trim());
+			errorCollector.assertEquals(String.format("Revision mismatch for line %d (annotating rev: %d)", i+1, cs), hgAnnotateRevIndex, fa.lineRevisions[i]);
 			String hgAnnotateLine = hgAnnotateLines[i].substring(hgAnnotateLines[i].indexOf(':') + 1);
 			String apiLine = fa.line(i).trim();
 			errorCollector.assertEquals(hgAnnotateLine.trim(), apiLine);
@@ -264,26 +264,33 @@
 		af.annotate(df, checkChangeset, dump, HgIterateDirection.OldToNew);
 	}
 	
-	private void ccc() throws Exception {
-		HgRepository repo = new HgLookup().detect("/home/artem/hg/junit-test-repos/test-annotate/");
-		HgDataFile df = repo.getFileNode("file1");
+	private void ccc() throws Throwable {
+		HgRepository repo = new HgLookup().detect("/home/artem/hg/hgtest-annotate1/");
+		HgDataFile df = repo.getFileNode("file1b.txt");
 		HgBlameFacility af = new HgBlameFacility();
-//		DiffOutInspector dump = new DiffOutInspector(System.out);
-//		dump.needRevisions(true);
-//		af.annotate(df, TIP, dump, HgIterateDirection.OldToNew);
+		DiffOutInspector dump = new DiffOutInspector(System.out);
+		dump.needRevisions(true);
+//		af.annotate(df, 62, dump, HgIterateDirection.NewToOld);
+//		af.annotateSingleRevision(df, 113, dump);
 //		System.out.println();
 //		af.annotate(df, TIP, new LineDumpInspector(true), HgIterateDirection.NewToOld);
 //		System.out.println();
 //		af.annotate(df, TIP, new LineDumpInspector(false), HgIterateDirection.NewToOld);
 //		System.out.println();
+		OutputParser.Stub op = new OutputParser.Stub();
+		eh = new ExecHelper(op, repo.getWorkingDir());
+		for (int cs : new int[] { 24, 46, 49, 52, 59, 62, 64, TIP}) {
+			doLineAnnotateTest(df, cs, op);
+		}
+		errorCollector.verify();
 		FileAnnotateInspector fa = new FileAnnotateInspector();
-		FileAnnotation.annotate(df, TIP, fa); //4,6,TIP
+		FileAnnotation.annotate(df, 62, fa);
 		for (int i = 0; i < fa.lineRevisions.length; i++) {
 			System.out.printf("%d: %s", fa.lineRevisions[i], fa.line(i) == null ? "null\n" : fa.line(i));
 		}
 	}
 
-	public static void main(String[] args) throws Exception {
+	public static void main(String[] args) throws Throwable {
 //		System.out.println(Arrays.equals(new String[0], splitLines("")));
 //		System.out.println(Arrays.equals(new String[] { "abc" }, splitLines("abc")));
 //		System.out.println(Arrays.equals(new String[] { "a", "bc" }, splitLines("a\nbc")));