diff --git a/src/difflib/DiffUtils.java b/src/difflib/DiffUtils.java index e8642af..1659f29 100644 --- a/src/difflib/DiffUtils.java +++ b/src/difflib/DiffUtils.java @@ -15,12 +15,15 @@ */ package difflib; -import java.util.*; +import difflib.myers.MyersDiff; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.Comparator; +import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; -import difflib.myers.*; - /** * Implements the difference and patching engine * @@ -140,6 +143,8 @@ public class DiffUtils { if (tag.equals(" ") || tag.equals("+") || tag.equals("-")) { rawChunk.add(new Object[] { tag, rest }); } + } else { + rawChunk.add(new Object[] {" ", ""}); } } } @@ -184,47 +189,48 @@ public class DiffUtils { List ret = new ArrayList(); ret.add("--- " + original); ret.add("+++ " + revised); - - // Hmm, I thought the Deltas were sorted already... turns out they're not. - List patchDeltas = new ArrayList( patch.getDeltas() ); - Collections.sort( patchDeltas, new Comparator() { - public int compare( Delta a, Delta b ) { - return new Integer(a.getOriginal().getPosition()).compareTo( b.getOriginal().getPosition() ); - } - }); - - // code outside the if block also works for single-delta issues. - List deltas = new ArrayList(); // current list of Delta's to process - Delta delta = patchDeltas.get(0); - deltas.add(delta); // add the first Delta to the current set - // if there's more than 1 Delta, we may need to output them together - if (patchDeltas.size() > 1) { - for (int i = 1; i < patchDeltas.size(); i++) { - int position = delta.getOriginal().getPosition(); // store the current position of - // the first Delta - - // Check if the next Delta is too close to the current position. - // And if it is, add it to the current set - Delta nextDelta = patchDeltas.get(i); - if ((position + delta.getOriginal().getSize() + contextSize) >= - (nextDelta.getOriginal().getPosition() - contextSize)) { - deltas.add(nextDelta); - } else { - // if it isn't, output the current set, - // then create a new set and add the current Delta to it. - List curBlock = processDeltas(originalLines, deltas, contextSize); - ret.addAll(curBlock); - deltas.clear(); - deltas.add(nextDelta); + + if (!patch.getDeltas().isEmpty()) { + // Hmm, I thought the Deltas were sorted already... turns out they're not. + List patchDeltas = new ArrayList( patch.getDeltas() ); + Collections.sort( patchDeltas, new Comparator() { + public int compare( Delta a, Delta b ) { + return new Integer(a.getOriginal().getPosition()).compareTo( b.getOriginal().getPosition() ); } - delta = nextDelta; + }); + + // code outside the if block also works for single-delta issues. + List deltas = new ArrayList(); // current list of Delta's to process + Delta delta = patchDeltas.get(0); + deltas.add(delta); // add the first Delta to the current set + // if there's more than 1 Delta, we may need to output them together + if (patchDeltas.size() > 1) { + for (int i = 1; i < patchDeltas.size(); i++) { + int position = delta.getOriginal().getPosition(); // store the current position of + // the first Delta + + // Check if the next Delta is too close to the current position. + // And if it is, add it to the current set + Delta nextDelta = patchDeltas.get(i); + if ((position + delta.getOriginal().getSize() + contextSize) >= + (nextDelta.getOriginal().getPosition() - contextSize)) { + deltas.add(nextDelta); + } else { + // if it isn't, output the current set, + // then create a new set and add the current Delta to it. + List curBlock = processDeltas(originalLines, deltas, contextSize); + ret.addAll(curBlock); + deltas.clear(); + deltas.add(nextDelta); + } + delta = nextDelta; + } + } - + // don't forget to process the last set of Deltas + List curBlock = processDeltas(originalLines, deltas, contextSize); + ret.addAll(curBlock); } - // don't forget to process the last set of Deltas - List curBlock = processDeltas(originalLines, deltas, contextSize); - ret.addAll(curBlock); - return ret; } diff --git a/test/mocks/issue10_base.txt b/test/mocks/issue10_base.txt new file mode 100644 index 0000000..c0a2b21 --- /dev/null +++ b/test/mocks/issue10_base.txt @@ -0,0 +1,46 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/test/mocks/issue10_patch.txt b/test/mocks/issue10_patch.txt new file mode 100644 index 0000000..736fddd --- /dev/null +++ b/test/mocks/issue10_patch.txt @@ -0,0 +1,10 @@ +--- /bonobo/bonobo.iml ++++ /bonobo/bonobo.iml +@@ -41,6 +40,7 @@ + + + ++ + + + diff --git a/test/mocks/issue11_1.txt b/test/mocks/issue11_1.txt new file mode 100644 index 0000000..29c06f7 --- /dev/null +++ b/test/mocks/issue11_1.txt @@ -0,0 +1 @@ +svn: '77954' path not found diff --git a/test/mocks/issue11_2.txt b/test/mocks/issue11_2.txt new file mode 100644 index 0000000..29c06f7 --- /dev/null +++ b/test/mocks/issue11_2.txt @@ -0,0 +1 @@ +svn: '77954' path not found diff --git a/test/testcase/diffutills/GenerateUnifiedDiffTest.java b/test/testcase/diffutills/GenerateUnifiedDiffTest.java index a9368ab..950ed80 100644 --- a/test/testcase/diffutills/GenerateUnifiedDiffTest.java +++ b/test/testcase/diffutills/GenerateUnifiedDiffTest.java @@ -1,5 +1,10 @@ package diffutills; +import difflib.DiffUtils; +import difflib.Patch; +import difflib.PatchFailedException; +import junit.framework.TestCase; + import java.io.BufferedReader; import java.io.File; import java.io.FileReader; @@ -8,19 +13,13 @@ import java.util.ArrayList; import java.util.LinkedList; import java.util.List; -import difflib.DiffUtils; -import difflib.Patch; -import difflib.PatchFailedException; - -import junit.framework.TestCase; - public class GenerateUnifiedDiffTest extends TestCase { static final String FS = File.separator; static final String originalFilename = "test" + FS + "mocks" + FS + "original.txt"; static final String revisedFilename = "test" + FS + "mocks" + FS + "revised.txt"; static final String originalFilenameOneDelta = "test" + FS + "mocks" + FS + "one_delta_test_original.txt"; static final String revisedFilenameOneDelta = "test" + FS + "mocks" + FS + "one_delta_test_revised.txt"; - + public List fileToLines(String filename) { List lines = new LinkedList(); String line = ""; @@ -34,37 +33,37 @@ public class GenerateUnifiedDiffTest extends TestCase { } return lines; } - + /** * Tests the Unified Diff generation by creating a Patch, then * creating the Unified Diff representation, then parsing that * Unified Diff, and applying the patch to the original unrevised * text, then comparing that to the original revised text. - * + * * @author Bill James (tankerbay@gmail.com) */ public void testGenerateUnified() { List origLines = fileToLines(originalFilename); List revLines = fileToLines(revisedFilename); - + testGenerateUnified(origLines, revLines); } - + /** * Tests the Unified Diff generation for diff with one delta. */ public void testGenerateUnifiedWithOneDelta() { List origLines = fileToLines(originalFilenameOneDelta); List revLines = fileToLines(revisedFilenameOneDelta); - + testGenerateUnified(origLines, revLines); } - + private void testGenerateUnified(List origLines, List revLines) { Patch p = DiffUtils.diff(origLines, revLines); List unifiedDiff = DiffUtils.generateUnifiedDiff( originalFilename, revisedFilename, origLines, p, 10); - + Patch fromUnifiedPatch = DiffUtils.parseUnifiedDiff(unifiedDiff); List patchedLines = new ArrayList(); try { @@ -73,7 +72,7 @@ public class GenerateUnifiedDiffTest extends TestCase { // TODO Auto-generated catch block fail(e.getMessage()); } - + assertTrue(revLines.size() == patchedLines.size()); for (int i = 0; i < revLines.size(); i++) { String l1 = revLines.get(i); @@ -84,5 +83,22 @@ public class GenerateUnifiedDiffTest extends TestCase { } } + public void testDiff_Issue10() throws Exception { + final List baseLines = fileToLines("test" + FS + "mocks" + FS + "issue10_base.txt"); + final List patchLines = fileToLines("test" + FS + "mocks" + FS + "issue10_patch.txt"); + final Patch p = DiffUtils.parseUnifiedDiff(patchLines); + DiffUtils.patch(baseLines, p); + } + public void testDiff_Issue11() throws Exception { + final List lines1 = fileToLines("test" + FS + "mocks" + FS + "issue11_1.txt"); + final List lines2 = fileToLines("test" + FS + "mocks" + FS + "issue11_2.txt"); + + + final Patch patch = DiffUtils.diff(lines1, lines2); + final String fileName = "xxx"; + final List stringList = DiffUtils.generateUnifiedDiff(fileName, fileName, lines1, patch, 3); + final Patch x = DiffUtils.parseUnifiedDiff(stringList); + DiffUtils.patch(lines1, x); + } }