diff_match_patch_native 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,278 @@
1
+ require "test/unit"
2
+ require File.join(File.dirname(File.expand_path(__FILE__)), '../', 'lib', 'diff_match_patch')
3
+
4
+ class TestDiffMatchPatch < Test::Unit::TestCase
5
+
6
+ def setup
7
+ @dmp = DiffMatchPatch.new
8
+ end
9
+
10
+ def test_should_get_and_set_diff_timeout
11
+ dmp = DiffMatchPatch.new # Use a new one so there's no interference
12
+ assert dmp.diff_timeout.instance_of?(Float)
13
+ assert_equal 1.0, dmp.diff_timeout
14
+
15
+ dmp.diff_timeout = 0
16
+
17
+ assert dmp.diff_timeout.instance_of?(Float)
18
+ assert_equal 0, dmp.diff_timeout
19
+ end
20
+
21
+ def test_should_get_and_set_diff_edit_cost
22
+ dmp = DiffMatchPatch.new # Use a new one so there's no interference
23
+ assert dmp.diff_edit_cost.instance_of?(Float)
24
+ assert_equal 4.0, dmp.diff_edit_cost
25
+
26
+ dmp.diff_edit_cost = 1.0
27
+
28
+ assert dmp.diff_edit_cost.instance_of?(Float)
29
+ assert_equal 1, dmp.diff_edit_cost
30
+ end
31
+
32
+ def test_simple_diff_main_scenarios
33
+ assert @dmp.diff_main("", "", false).empty?
34
+
35
+ equality_result = [[0, "abc"]]
36
+ assert_equal equality_result, @dmp.diff_main("abc", "abc", false)
37
+
38
+ simple_insertion_result = [[0, "ab"], [1, "123"], [0, "c"]]
39
+ assert_equal simple_insertion_result, @dmp.diff_main("abc", "ab123c", false)
40
+
41
+ simple_deletion_result = [[0, "a"], [-1,"123"], [0,"bc"]]
42
+ assert_equal simple_deletion_result, @dmp.diff_main("a123bc", "abc", false)
43
+
44
+ two_insertion_result = [[0, "a"], [1, "123"], [0, "b"], [1, "456"], [0, "c"]]
45
+ assert_equal two_insertion_result, @dmp.diff_main("abc", "a123b456c", false)
46
+
47
+ two_deletion_result = [[0, "a"], [-1, "123"], [0, "b"], [-1, "456"], [0, "c"]]
48
+ assert_equal two_deletion_result, @dmp.diff_main("a123b456c", "abc", false)
49
+ end
50
+
51
+ def test_real_diff_main_scenarios
52
+ # Turn off the timeout
53
+ @dmp.diff_timeout = 0
54
+
55
+ simple_case_1_result = [[-1, "a"], [1, "b"]]
56
+ assert_equal simple_case_1_result, @dmp.diff_main("a", "b", false)
57
+
58
+ simple_case_2_result = [[-1, "Apple"], [1, "Banana"], [0, "s are a"], [1, "lso"], [0, " fruit."]]
59
+ assert_equal simple_case_2_result, @dmp.diff_main("Apples are a fruit.", "Bananas are also fruit.", false)
60
+
61
+ # TODO: Case 3 from diff_match_patch.cpp
62
+
63
+ overlap_1_result = [[-1, "1"], [0, "a"], [-1, "y"], [0, "b"], [-1, "2"], [1, "xab"]]
64
+ assert_equal overlap_1_result, @dmp.diff_main("1ayb2", "abxab", false)
65
+
66
+ overlap_2_result = [[1, "xaxcx"], [0, "abc"], [-1, "y"]]
67
+ assert_equal overlap_2_result, @dmp.diff_main("abcy", "xaxcxabc", false)
68
+
69
+ overlap_3_result = [[-1, "ABCD"], [0, "a"], [-1, "="], [1, "-"], [0, "bcd"], [-1, "="], [1, "-"], [0, "efghijklmnopqrs"], [-1, "EFGHIJKLMNOefg"]]
70
+ assert_equal overlap_3_result, @dmp.diff_main("ABCDa=bcd=efghijklmnopqrsEFGHIJKLMNOefg", "a-bcd-efghijklmnopqrs", false)
71
+
72
+ large_equality_result = [[1, " "], [0, "a"], [1, "nd"], [0, " [[Pennsylvania]]"], [-1, " and [[New"]]
73
+ assert_equal large_equality_result, @dmp.diff_main("a [[Pennsylvania]] and [[New", " and [[Pennsylvania]]", false)
74
+
75
+ # TODO: Timeout test
76
+
77
+ # Test the linemode speedup.
78
+ # Must be long to pass the 100 char cutoff.
79
+ a = "1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n1234567890\n"
80
+ b = "abcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\nabcdefghij\n"
81
+ assert_equal(@dmp.diff_main(a, b, true), @dmp.diff_main(a, b, false))
82
+
83
+ a = "1234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890"
84
+ b = "abcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghijabcdefghij"
85
+ assert_equal(@dmp.diff_main(a, b, true), @dmp.diff_main(a, b, false))
86
+ end
87
+
88
+ def test_diff_cleanup_semantic
89
+ diffs = []
90
+ @dmp.diff_cleanup_semantic!(diffs)
91
+ assert_equal [], diffs
92
+
93
+ diffs = [[-1, "ab"], [1, "cd"], [0, "12"], [-1, "e"]]
94
+ @dmp.diff_cleanup_semantic!(diffs)
95
+ assert_equal [[-1, "ab"], [1, "cd"], [0, "12"], [-1, "e"]], diffs
96
+
97
+ diffs = [[-1, "abc"], [1, "ABC"], [0, "1234"], [-1, "wxyz"]]
98
+ @dmp.diff_cleanup_semantic!(diffs)
99
+ assert_equal [[-1, "abc"], [1, "ABC"], [0, "1234"], [-1, "wxyz"]], diffs
100
+
101
+ diffs = [[-1, "a"], [0, "b"], [-1, "c"]]
102
+ @dmp.diff_cleanup_semantic!(diffs)
103
+ assert_equal [[-1, "abc"], [1, "b"]], diffs
104
+
105
+ diffs = [[-1, "ab"], [0, "cd"], [-1, "e"], [0, "f"], [1, "g"]]
106
+ @dmp.diff_cleanup_semantic!(diffs)
107
+ assert_equal [[-1, "abcdef"], [1, "cdfg"]], diffs
108
+
109
+ diffs = [[1, "1"], [0, "A"], [-1, "B"], [1, "2"], [0, "_"], [1, "1"], [0, "A"], [-1, "B"], [1, "2"]]
110
+ @dmp.diff_cleanup_semantic!(diffs)
111
+ assert_equal [[-1, "AB_AB"], [1, "1A2_1A2"]], diffs
112
+
113
+ diffs = [[0, "The c"], [-1, "ow and the c"], [0, "at."]]
114
+ @dmp.diff_cleanup_semantic!(diffs)
115
+ assert_equal [[0, "The "], [-1, "cow and the "], [0, "cat."]], diffs
116
+
117
+ diffs = [[-1, "abcxx"], [1, "xxdef"]]
118
+ @dmp.diff_cleanup_semantic!(diffs)
119
+ assert_equal [[-1, "abc"], [0, "xx"], [1, "def"]], diffs
120
+
121
+ diffs = [[-1, "abcxx"], [1, "xxdef"], [-1, "ABCXX"], [1, "XXDEF"]]
122
+ @dmp.diff_cleanup_semantic!(diffs)
123
+ assert_equal [[-1, "abc"], [0, "xx"], [1, "def"], [-1, "ABC"], [0, "XX"], [1, "DEF"]], diffs
124
+ end
125
+
126
+ def test_diff_cleanup_efficiency
127
+ @dmp.diff_edit_cost = 4
128
+ diffs = []
129
+ @dmp.diff_cleanup_efficiency!(diffs)
130
+ assert_equal [], diffs
131
+
132
+ diffs = [[-1, "ab"], [1, "12"], [0, "wxyz"], [-1, "cd"], [1, "34"]]
133
+ @dmp.diff_cleanup_efficiency!(diffs)
134
+ assert_equal [[-1, "ab"], [1, "12"], [0, "wxyz"], [-1, "cd"], [1, "34"]], diffs
135
+
136
+ diffs = [[-1, "ab"], [1, "12"], [0, "xyz"], [-1, "cd"], [1, "34"]]
137
+ @dmp.diff_cleanup_efficiency!(diffs)
138
+ assert_equal [[-1, "abxyzcd"], [1, "12xyz34"]], diffs
139
+
140
+ diffs = [[1, "12"], [0, "x"], [-1, "cd"], [1, "34"]]
141
+ @dmp.diff_cleanup_efficiency!(diffs)
142
+ assert_equal [[-1, "xcd"], [1, "12x34"]], diffs
143
+
144
+ diffs = [[-1, "ab"], [1, "12"], [0, "xy"], [1, "34"], [0, "z"], [-1, "cd"], [1, "56"]]
145
+ @dmp.diff_cleanup_efficiency!(diffs)
146
+ assert_equal [[-1, "abxyzcd"], [1, "12xy34z56"]], diffs
147
+
148
+ @dmp.diff_edit_cost = 5
149
+ diffs = [[-1, "ab"], [1, "12"], [0, "wxyz"], [-1, "cd"], [1, "34"]]
150
+ @dmp.diff_cleanup_efficiency!(diffs)
151
+ assert_equal [[-1, "abwxyzcd"], [1, "12wxyz34"]], diffs
152
+ @dmp.diff_edit_cost = 4
153
+ end
154
+
155
+ def test_diff_levenshtein
156
+ diffs = [[-1, "abc"], [1, "1234"], [0, "xyz"]]
157
+ assert_equal 4, @dmp.diff_levenshtein(diffs)
158
+
159
+ diffs = [[0, "xyz"], [-1, "abc"], [1, "1234"]]
160
+ assert_equal 4, @dmp.diff_levenshtein(diffs)
161
+
162
+ diffs = [[-1, "abc"], [0, "xyz"], [1, "1234"]]
163
+ assert_equal 7, @dmp.diff_levenshtein(diffs)
164
+ end
165
+
166
+ def test_diff_pretty_html
167
+ diffs = [[0, "a\n"], [-1, "<B>b</B>"], [1, "c&d"]];
168
+ assert_equal "<span>a&para;<br></span><del style=\"background:#ffe6e6;\">&lt;B&gt;b&lt;/B&gt;</del><ins style=\"background:#e6ffe6;\">c&amp;d</ins>", @dmp.diff_pretty_html(diffs)
169
+ end
170
+
171
+ def test_match_main
172
+ assert_equal(0, @dmp.match_main("abcdef", "abcdef", 1000))
173
+
174
+ assert_equal(-1, @dmp.match_main("", "abcdef", 1))
175
+
176
+ assert_equal 3, @dmp.match_main("abcdef", "", 3)
177
+
178
+ assert_equal 3, @dmp.match_main("abcdef", "de", 3)
179
+
180
+ @dmp.match_threshold = 0.7
181
+ assert_equal 4, @dmp.match_main("I am the very model of a modern major general.", " that berry ", 5)
182
+ @dmp.match_threshold = 0.5
183
+ end
184
+
185
+ def test_patch_from_text
186
+ assert @dmp.patch_from_text("").empty?
187
+
188
+ [
189
+ "@@ -21,18 +22,17 @@\n jump\n-s\n+ed\n over \n-the\n+a\n laz\n",
190
+ "@@ -1 +1 @@\n-a\n+b\n",
191
+ "@@ -1,3 +0,0 @@\n-abc\n",
192
+ "@@ -0,0 +1,3 @@\n+abc\n"
193
+ ].each do |str|
194
+ assert_equal str, @dmp.patch_from_text(str).first.to_string
195
+ end
196
+ end
197
+
198
+ def test_patch_to_text
199
+ str = "@@ -21,18 +22,17 @@\n jump\n-s\n+ed\n over \n-the\n+a\n laz\n"
200
+ patches = @dmp.patch_from_text(str)
201
+ assert_equal str, @dmp.patch_to_text(patches)
202
+
203
+ multiples = "@@ -1,9 +1,9 @@\n-f\n+F\n oo+fooba\n@@ -7,9 +7,9 @@\n obar\n-,\n+.\n tes\n"
204
+ patches = @dmp.patch_from_text(multiples)
205
+ assert_equal multiples, @dmp.patch_to_text(patches)
206
+ end
207
+
208
+ def test_patch_make
209
+ patches = @dmp.patch_make("", "")
210
+ assert_equal "", @dmp.patch_to_text(patches)
211
+
212
+ text_1 = "The quick brown fox jumps over the lazy dog."
213
+ text_2 = "That quick brown fox jumped over a lazy dog."
214
+
215
+ expected_patch = "@@ -1,8 +1,7 @@\n Th\n-at\n+e\n qui\n@@ -21,17 +21,18 @@\n jump\n-ed\n+s\n over \n-a\n+the\n laz\n"
216
+ patches = @dmp.patch_make(text_2, text_1)
217
+ assert_equal(expected_patch, @dmp.patch_to_text(patches))
218
+
219
+ expected_patch = "@@ -1,11 +1,12 @@\n Th\n-e\n+at\n quick b\n@@ -22,18 +22,17 @@\n jump\n-s\n+ed\n over \n-the\n+a\n laz\n"
220
+ patches = @dmp.patch_make(text_1, text_2)
221
+ assert_equal(expected_patch, @dmp.patch_to_text(patches))
222
+
223
+ diffs = @dmp.diff_main(text_1, text_2, false)
224
+ patches = @dmp.patch_make(diffs)
225
+ assert_equal(expected_patch, @dmp.patch_to_text(patches))
226
+
227
+ patches = @dmp.patch_make(text_1, diffs)
228
+ assert_equal(expected_patch, @dmp.patch_to_text(patches))
229
+ end
230
+
231
+ def test_patch_apply
232
+ @dmp.match_distance = 1000
233
+ @dmp.match_threshold = 0.5
234
+ @dmp.patch_delete_threshold = 0.5
235
+
236
+ patches = @dmp.patch_make("", "")
237
+ results = @dmp.patch_apply(patches, "Hello World")
238
+ assert_equal ["Hello World", []], results
239
+
240
+ patches = @dmp.patch_make("The quick brown fox jumps over the lazy dog.", "That quick brown fox jumped over a lazy dog.")
241
+ results = @dmp.patch_apply(patches, "The quick brown fox jumps over the lazy dog.")
242
+ assert_equal ["That quick brown fox jumped over a lazy dog.", [true, true]], results
243
+
244
+ results = @dmp.patch_apply(patches, "The quick red rabbit jumps over the tired tiger.")
245
+ assert_equal ["That quick red rabbit jumped over a tired tiger.", [true, true]], results
246
+
247
+ results = @dmp.patch_apply(patches, "I am the very model of a modern major general.")
248
+ assert_equal ["I am the very model of a modern major general.", [false, false]], results
249
+
250
+ patches = @dmp.patch_make("x1234567890123456789012345678901234567890123456789012345678901234567890y", "xabcy")
251
+ results = @dmp.patch_apply(patches, "x123456789012345678901234567890-----++++++++++-----123456789012345678901234567890y")
252
+ assert_equal ["xabcy", [true, true]], results
253
+
254
+ patches = @dmp.patch_make("x1234567890123456789012345678901234567890123456789012345678901234567890y", "xabcy")
255
+ results = @dmp.patch_apply(patches, "x12345678901234567890---------------++++++++++---------------12345678901234567890y")
256
+ assert_equal ["xabc12345678901234567890---------------++++++++++---------------12345678901234567890y", [false, true]], results
257
+
258
+ @dmp.patch_delete_threshold = 0.6
259
+ patches = @dmp.patch_make("x1234567890123456789012345678901234567890123456789012345678901234567890y", "xabcy")
260
+ results = @dmp.patch_apply(patches, "x12345678901234567890---------------++++++++++---------------12345678901234567890y")
261
+ assert_equal ["xabcy", [true, true]], results
262
+
263
+ @dmp.patch_delete_threshold = 0.5
264
+ @dmp.match_distance = 0
265
+ @dmp.match_threshold = 0
266
+ patches = @dmp.patch_make("abcdefghijklmnopqrstuvwxyz--------------------1234567890", "abcXXXXXXXXXXdefghijklmnopqrstuvwxyz--------------------1234567YYYYYYYYYY890")
267
+ results = @dmp.patch_apply(patches, "ABCDEFGHIJKLMNOPQRSTUVWXYZ--------------------1234567890")
268
+ assert_equal ["ABCDEFGHIJKLMNOPQRSTUVWXYZ--------------------1234567YYYYYYYYYY890", [false, true]], results
269
+
270
+ @dmp.match_distance = 1000
271
+ @dmp.match_threshold = 0.5
272
+ patches = @dmp.patch_make("", "test")
273
+ str = @dmp.patch_to_text(patches)
274
+ @dmp.patch_apply(patches, "")
275
+ assert_equal str, @dmp.patch_to_text(patches)
276
+ end
277
+
278
+ end
metadata ADDED
@@ -0,0 +1,99 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: diff_match_patch_native
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Elliot Laster
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-02-15 00:00:00.000000000Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rice
16
+ requirement: &2165194700 !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: 1.4.2
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: *2165194700
25
+ - !ruby/object:Gem::Dependency
26
+ name: rake-compiler
27
+ requirement: &2165191640 !ruby/object:Gem::Requirement
28
+ none: false
29
+ requirements:
30
+ - - ! '>='
31
+ - !ruby/object:Gem::Version
32
+ version: '0'
33
+ type: :development
34
+ prerelease: false
35
+ version_requirements: *2165191640
36
+ - !ruby/object:Gem::Dependency
37
+ name: hoe
38
+ requirement: &2165190820 !ruby/object:Gem::Requirement
39
+ none: false
40
+ requirements:
41
+ - - ~>
42
+ - !ruby/object:Gem::Version
43
+ version: '2.12'
44
+ type: :development
45
+ prerelease: false
46
+ version_requirements: *2165190820
47
+ description: The Diff Match and Patch libraries offer robust algorithms to perform
48
+ the operations required for synchronizing plain text.
49
+ email:
50
+ - elliotlaster@gmail.com
51
+ executables: []
52
+ extensions:
53
+ - ext/diff_match_patch/extconf.rb
54
+ extra_rdoc_files:
55
+ - History.txt
56
+ - Manifest.txt
57
+ files:
58
+ - History.txt
59
+ - Manifest.txt
60
+ - README.rdoc
61
+ - Rakefile
62
+ - ext/diff_match_patch/_dmp.cpp
63
+ - ext/diff_match_patch/_dmp.h
64
+ - ext/diff_match_patch/diff_match_patch.cpp
65
+ - ext/diff_match_patch/extconf.rb
66
+ - lib/diff_match_patch.rb
67
+ - lib/diff_match_patch/diff_match_patch.bundle
68
+ - src/include/diff_match_patch-stl/diff_match_patch.h
69
+ - test/test_diff_patch_match.rb
70
+ - .gemtest
71
+ homepage: https://github.com/elliotlaster/Ruby-Diff-Match-Patch
72
+ licenses: []
73
+ post_install_message:
74
+ rdoc_options:
75
+ - --main
76
+ - README.rdoc
77
+ require_paths:
78
+ - lib
79
+ required_ruby_version: !ruby/object:Gem::Requirement
80
+ none: false
81
+ requirements:
82
+ - - ! '>='
83
+ - !ruby/object:Gem::Version
84
+ version: '0'
85
+ required_rubygems_version: !ruby/object:Gem::Requirement
86
+ none: false
87
+ requirements:
88
+ - - ! '>='
89
+ - !ruby/object:Gem::Version
90
+ version: '0'
91
+ requirements: []
92
+ rubyforge_project: diff_match_patch_native
93
+ rubygems_version: 1.8.10
94
+ signing_key:
95
+ specification_version: 3
96
+ summary: The Diff Match and Patch libraries offer robust algorithms to perform the
97
+ operations required for synchronizing plain text.
98
+ test_files:
99
+ - test/test_diff_patch_match.rb