1 require "my-assertions"
9 class SvnCoreTest < Test::Unit::TestCase
13 setup_default_variables
14 @config_file = File.join(@config_path, Svn::Core::CONFIG_CATEGORY_CONFIG)
15 @servers_file = File.join(@config_path, Svn::Core::CONFIG_CATEGORY_SERVERS)
16 setup_repository(@repos_path)
22 teardown_repository(@repos_path)
27 def test_binary_mime_type?
28 assert(Svn::Core.binary_mime_type?("image/png"))
29 assert(!Svn::Core.binary_mime_type?("text/plain"))
34 str = now.strftime("%Y-%m-%dT%H:%M:%S.") + "#{now.usec}Z"
36 assert_equal(now, Time.from_svn_format(str))
38 apr_time = now.to_i * 1000000 + now.usec
39 assert_equal(apr_time, now.to_apr_time)
42 def test_not_new_auth_provider_object
43 assert_raise(NoMethodError) do
44 Svn::Core::AuthProviderObject.new
53 ver = Svn::Core::Version.new(major, minor, patch, tag)
55 assert_equal("#{major}.#{minor}.#{patch}#{tag}", ver.to_s)
56 assert_equal([major, minor, patch, tag], ver.to_a)
59 def test_version_valid?
60 assert_true(Svn::Core::Version.new(1, 2, 3, "-devel").valid?)
61 assert_true(Svn::Core::Version.new(nil, nil, nil, "").valid?)
62 assert_true(Svn::Core::Version.new.valid?)
65 def test_version_equal
70 ver1 = Svn::Core::Version.new(major, minor, patch, tag)
71 ver2 = Svn::Core::Version.new(major, minor, patch, tag)
72 ver3 = Svn::Core::Version.new
73 assert_equal(ver1, ver2)
74 assert_not_equal(ver1, ver3)
77 def test_version_compatible?
84 ver1 = Svn::Core::Version.new(major, minor, patch, my_tag)
85 ver2 = Svn::Core::Version.new(major, minor, patch, lib_tag)
86 ver3 = Svn::Core::Version.new(major, minor, patch, lib_tag + "x")
87 assert_true(ver1.compatible?(ver2))
88 assert_false(ver1.compatible?(ver3))
92 ver1 = Svn::Core::Version.new(major, minor, patch, my_tag)
93 ver2 = Svn::Core::Version.new(major, minor, patch, lib_tag)
94 ver3 = Svn::Core::Version.new(major, minor, patch - 1, lib_tag)
95 assert_false(ver1.compatible?(ver2))
96 assert_true(ver1.compatible?(ver3))
99 ver1 = Svn::Core::Version.new(major, minor, patch, tag)
100 ver2 = Svn::Core::Version.new(major, minor, patch, tag)
101 ver3 = Svn::Core::Version.new(major, minor, patch - 1, tag)
102 ver4 = Svn::Core::Version.new(major, minor + 1, patch, tag)
103 ver5 = Svn::Core::Version.new(major, minor - 1, patch, tag)
104 assert_true(ver1.compatible?(ver2))
105 assert_true(ver1.compatible?(ver3))
106 assert_true(ver1.compatible?(ver4))
107 assert_false(ver1.compatible?(ver5))
111 vers = [Svn::Core::VER_MAJOR, Svn::Core::VER_MINOR, Svn::Core::VER_PATCH]
112 ver_num = vers.collect {|ver| ver.to_s}.join(".")
113 assert_equal(ver_num, Svn::Core::VER_NUM)
114 assert_equal("#{ver_num}#{Svn::Core::VER_NUMTAG}", Svn::Core::VER_NUMBER)
115 assert_equal("#{ver_num}#{Svn::Core::VER_TAG}", Svn::Core::VERSION)
118 def test_auth_parameter
121 auth = Svn::Core::AuthBaton.new
122 assert_nil(auth[key])
124 assert_equal(value, auth[key])
126 assert_raise(TypeError) do
133 made_number_of_pool = 100
137 before_number_of_pools = Svn::Core::Pool.number_of_pools
138 made_number_of_pool.times do
142 current_number_of_pools = Svn::Core::Pool.number_of_pools
143 created_number_of_pools = current_number_of_pools - before_number_of_pools
144 assert_operator(made_number_of_pool, :<=, current_number_of_pools)
148 before_number_of_pools = Svn::Core::Pool.number_of_pools
150 current_number_of_pools = Svn::Core::Pool.number_of_pools
151 recycled_number_of_pools =
152 before_number_of_pools - current_number_of_pools
153 assert_operator(made_number_of_pool * 0.8, :<=, recycled_number_of_pools)
159 Svn::Core::CONFIG_CATEGORY_CONFIG,
160 Svn::Core::CONFIG_CATEGORY_SERVERS,
162 Svn::Core::Config.config(@config_path).keys.sort)
164 config = Svn::Core::Config.read(@config_file)
165 section = Svn::Core::CONFIG_SECTION_HELPERS
166 option = Svn::Core::CONFIG_OPTION_DIFF_CMD
169 assert_nil(config.get(section, option))
170 config.set(section, option, value)
171 assert_equal(value, config.get(section, option))
175 config = Svn::Core::Config.read(@config_file)
176 section = Svn::Core::CONFIG_SECTION_MISCELLANY
177 option = Svn::Core::CONFIG_OPTION_ENABLE_AUTO_PROPS
179 assert(config.get_bool(section, option, true))
180 config.set_bool(section, option, false)
181 assert(!config.get_bool(section, option, true))
185 config = Svn::Core::Config.read(@config_file)
186 section = Svn::Core::CONFIG_SECTION_HELPERS
188 Svn::Core::CONFIG_OPTION_DIFF_CMD => "diff",
189 Svn::Core::CONFIG_OPTION_DIFF3_CMD => "diff3",
193 config.each_option(section) do |name, value|
197 assert_equal({}, infos)
200 config.each_section do |name|
201 section_names << name
204 assert_equal([], section_names)
206 options.each do |option, value|
207 config.set(section, option, value)
210 config.each_option(section) do |name, value|
214 assert_equal(options, infos)
216 config.each_section do |name|
217 section_names << name
220 assert_equal([section], section_names)
222 infos = options.collect {|key, value| [section, key, value]}
224 config.each do |section, name, value|
225 config_infos << [section, name, value]
227 assert_equal(infos.sort, config_infos.sort)
228 assert_equal(infos.sort, config.collect {|args| args}.sort)
231 def test_config_find_group
232 config = Svn::Core::Config.read(@config_file)
233 section = Svn::Core::CONFIG_SECTION_HELPERS
234 option = Svn::Core::CONFIG_OPTION_DIFF_CMD
237 assert_nil(config.find_group(value, section))
238 config.set(section, option, value)
239 assert_equal(option, config.find_group(value, section))
242 def test_config_get_server_setting
244 host_prop_name = "http-proxy-host"
245 host_prop_value = "*.example.com"
246 default_host_value = "example.net"
247 port_prop_name = "http-proxy-port"
248 port_prop_value = 8080
249 default_port_value = 1818
251 File.open(@servers_file, "w") do |f|
255 config = Svn::Core::Config.read(@servers_file)
256 assert_equal(default_host_value,
257 config.get_server_setting(group,
260 assert_equal(default_port_value,
261 config.get_server_setting_int(group,
265 File.open(@servers_file, "w") do |f|
267 f.puts("#{host_prop_name} = #{host_prop_value}")
268 f.puts("#{port_prop_name} = #{port_prop_value}")
271 config = Svn::Core::Config.read(@servers_file)
272 assert_equal(host_prop_value,
273 config.get_server_setting(group,
276 assert_equal(port_prop_value,
277 config.get_server_setting_int(group,
282 def test_config_auth_data
283 cred_kind = Svn::Core::AUTH_CRED_SIMPLE
284 realm_string = "sample"
285 assert_nil(Svn::Core::Config.read_auth_data(cred_kind,
288 Svn::Core::Config.write_auth_data({},
292 assert_equal({Svn::Core::CONFIG_REALMSTRING_KEY => realm_string},
293 Svn::Core::Config.read_auth_data(cred_kind,
299 config = Svn::Core::Config.read(@config_file)
300 section = Svn::Core::CONFIG_SECTION_HELPERS
302 Svn::Core::CONFIG_OPTION_DIFF_CMD => "diff",
303 Svn::Core::CONFIG_OPTION_DIFF3_CMD => "diff3",
306 options.each do |option, value|
307 config[section, option] = value
310 temp_config = Tempfile.new("svn-test-config")
312 temp_config.print(config.to_s)
315 parsed_config = Svn::Core::Config.read(temp_config.path)
316 assert_equal({section => options}, parsed_config.to_hash)
319 def test_config_to_hash
320 config = Svn::Core::Config.read(@config_file)
321 section = Svn::Core::CONFIG_SECTION_HELPERS
323 Svn::Core::CONFIG_OPTION_DIFF_CMD => "diff",
324 Svn::Core::CONFIG_OPTION_DIFF3_CMD => "diff3",
327 assert_equal({}, config.to_hash)
329 options.each do |option, value|
330 config[section, option] = value
333 assert_equal({section => options}, config.to_hash)
336 def test_diff_version
337 assert_equal(Svn::Core.subr_version, Svn::Core::Diff.version)
340 def test_diff_unified
341 original = Tempfile.new("original")
342 modified = Tempfile.new("modified")
343 original_src = <<-EOS
348 modified_src = <<-EOS
353 original_header = "(orig)"
354 modified_header = "(mod)"
357 original.print(original_src)
360 modified.print(modified_src)
364 --- #{original_header}
365 +++ #{modified_header}
374 diff = Svn::Core::Diff.file_diff(original.path, modified.path)
375 assert_equal(normalize_line_break(expected),
376 diff.unified(original_header, modified_header))
378 options = Svn::Core::DiffFileOptions.parse("--ignore-space-change")
380 --- #{original_header}
381 +++ #{modified_header}
389 diff = Svn::Core::Diff.file_diff(original.path, modified.path, options)
390 assert_equal(normalize_line_break(expected),
391 diff.unified(original_header, modified_header))
393 options = Svn::Core::DiffFileOptions.parse("--ignore-all-space")
395 --- #{original_header}
396 +++ #{modified_header}
403 diff = Svn::Core::Diff.file_diff(original.path, modified.path, options)
404 assert_equal(normalize_line_break(expected),
405 diff.unified(original_header, modified_header))
409 original = Tempfile.new("original")
410 modified = Tempfile.new("modified")
411 latest = Tempfile.new("latest")
412 original_src = <<-EOS
419 modified_src = <<-EOS
435 original.print(original_src)
438 modified.print(modified_src)
441 latest.print(latest_src)
451 diff = Svn::Core::Diff.file_diff3(original.path,
454 assert_equal(normalize_line_break(expected), diff.merge)
456 options = Svn::Core::DiffFileOptions.parse("--ignore-space-change")
464 diff = Svn::Core::Diff.file_diff3(original.path,
468 assert_equal(normalize_line_break(expected), diff.merge)
470 options = Svn::Core::DiffFileOptions.parse("--ignore-all-space")
478 diff = Svn::Core::Diff.file_diff3(original.path,
482 assert_equal(normalize_line_break(expected), diff.merge)
485 def test_diff_file_options
486 args = ["--ignore-all-space"]
487 options = Svn::Core::DiffFileOptions.parse(*args)
488 assert_equal(Svn::Core::DIFF_FILE_IGNORE_SPACE_ALL,
489 options.ignore_space)
490 assert_false(options.ignore_eol_style)
492 args = ["--ignore-space-change"]
493 options = Svn::Core::DiffFileOptions.parse(*args)
494 assert_equal(Svn::Core::DIFF_FILE_IGNORE_SPACE_CHANGE,
495 options.ignore_space)
496 assert_false(options.ignore_eol_style)
498 args = ["--ignore-space-change", "--ignore-eol-style"]
499 options = Svn::Core::DiffFileOptions.parse(*args)
500 assert_equal(Svn::Core::DIFF_FILE_IGNORE_SPACE_CHANGE,
501 options.ignore_space)
502 assert_true(options.ignore_eol_style)
504 options = Svn::Core::DiffFileOptions.parse(args)
505 assert_equal(Svn::Core::DIFF_FILE_IGNORE_SPACE_CHANGE,
506 options.ignore_space)
507 assert_true(options.ignore_eol_style)
510 def test_create_commit_info
511 info = Svn::Core::CommitInfo.new
512 now = Time.now.gmtime
513 date_str = now.strftime("%Y-%m-%dT%H:%M:%S")
514 date_str << ".#{now.usec}Z"
516 assert_equal(now, info.date)
520 assert(Svn::Core::Property.svn_prop?("svn:mime-type"))
521 assert(!Svn::Core::Property.svn_prop?("my-mime-type"))
523 assert(Svn::Core::Property.has_svn_prop?({"svn:mime-type" => "text/plain"}))
524 assert(!Svn::Core::Property.has_svn_prop?({"my-mime-type" => "text/plain"}))
526 assert(Svn::Core::Property.have_svn_prop?({"svn:mime-type" => "text/plain"}))
527 assert(!Svn::Core::Property.have_svn_prop?({"my-mime-type" => "text/plain"}))
530 def test_valid_prop_name
531 assert(Svn::Core::Property.valid_name?("svn:mime-type"))
532 assert(Svn::Core::Property.valid_name?("my-mime-type"))
533 assert(!Svn::Core::Property.valid_name?("プãƒãƒ‘ティ"))
536 def test_depth_conversion
537 %w(unknown empty files immediates infinity).each do |depth|
538 depth_value = Svn::Core.const_get("DEPTH_#{depth.upcase}")
539 assert_equal(depth_value, Svn::Core::Depth.from_string(depth))
540 assert_equal(depth, Svn::Core::Depth.to_string(depth_value))
545 depth_infinity = Svn::Core::DEPTH_INFINITY
546 assert_equal("infinity", Svn::Core::Depth.to_string(depth_infinity))
547 assert_equal("infinity", Svn::Core::Depth.to_string("infinity"))
548 assert_equal("infinity", Svn::Core::Depth.to_string(:infinity))
549 assert_equal("unknown", Svn::Core::Depth.to_string("XXX"))
550 assert_raises(ArgumentError) do
551 Svn::Core::Depth.to_string([])
557 original = StringIO.new(source)
558 copied = StringIO.new("")
559 original_stream = Svn::Core::Stream.new(original)
560 copied_stream = Svn::Core::Stream.new(copied)
563 original_stream.copy(copied_stream)
566 assert_equal("", original.read)
567 assert_equal(source, copied.read)
572 assert_raises(Svn::Error::Cancelled) do
573 original_stream.copy(copied_stream) do
574 raise Svn::Error::Cancelled
579 assert_equal(source, original.read)
580 assert_equal("", copied.read)
583 def test_mime_type_parse
585 "html" => "text/html",
586 "htm" => "text/html",
587 "png" => "image/png",
589 mime_types_source = <<-EOM
591 application/octet-stream
596 mime_types = Tempfile.new("svn-ruby-mime-type")
597 mime_types.puts(mime_types_source)
600 assert_equal(type_map, Svn::Core::MimeType.parse_file(mime_types.path))
601 assert_equal(type_map, Svn::Core::MimeType.parse(mime_types_source))
604 def test_mime_type_detect
605 empty_file = Tempfile.new("svn-ruby-mime-type")
606 assert_equal(nil, Svn::Core::MimeType.detect(empty_file.path))
608 binary_file = Tempfile.new("svn-ruby-mime-type")
609 binary_file.print("\0\1\2")
611 assert_equal("application/octet-stream",
612 Svn::Core::MimeType.detect(binary_file.path))
614 text_file = Tempfile.new("svn-ruby-mime-type")
615 text_file.print("abcde")
617 assert_equal(nil, Svn::Core::MimeType.detect(text_file.path))
620 def test_mime_type_detect_with_type_map
622 "html" => "text/html",
623 "htm" => "text/html",
624 "png" => "image/png",
627 nonexistent_html_file = File.join(@tmp_path, "nonexistent.html")
628 assert_raises(Svn::Error::BadFilename) do
629 Svn::Core::MimeType.detect(nonexistent_html_file)
631 assert_raises(Svn::Error::BadFilename) do
632 Svn::Core::MimeType.detect(nonexistent_html_file, type_map)
635 empty_html_file = File.join(@tmp_path, "empty.html")
636 FileUtils.touch(empty_html_file)
637 assert_equal(nil, Svn::Core::MimeType.detect(empty_html_file))
638 assert_equal("text/html",
639 Svn::Core::MimeType.detect(empty_html_file, type_map))
641 empty_htm_file = File.join(@tmp_path, "empty.htm")
642 FileUtils.touch(empty_htm_file)
643 assert_equal(nil, Svn::Core::MimeType.detect(empty_htm_file))
644 assert_equal("text/html",
645 Svn::Core::MimeType.detect(empty_htm_file, type_map))
648 dummy_png_file = File.join(@tmp_path, "dummy.png")
649 File.open(dummy_png_file, "wb") do |png|
650 png.print("\211PNG\r\n\032\n")
652 assert_equal(nil, Svn::Core::MimeType.detect(dummy_png_file))
653 assert_equal("image/png",
654 Svn::Core::MimeType.detect(dummy_png_file, type_map))
656 empty_png_file = File.join(@tmp_path, "empty.png")
657 FileUtils.touch(empty_png_file)
658 assert_equal(nil, Svn::Core::MimeType.detect(empty_png_file))
659 assert_equal("image/png",
660 Svn::Core::MimeType.detect(empty_png_file, type_map))
662 invalid_png_file = File.join(@tmp_path, "invalid.png")
663 File.open(invalid_png_file, "w") do |png|
666 assert_equal(nil, Svn::Core::MimeType.detect(invalid_png_file))
667 assert_equal("image/png",
668 Svn::Core::MimeType.detect(invalid_png_file, type_map))
671 def test_prop_categorize
672 name = "svn:mime-type"
674 entry_name = "svn:entry:XXX"
677 props = [Svn::Core::Prop.new(name, value),
678 Svn::Core::Prop.new(entry_name, entry_value)]
680 [Svn::Core::Prop.new(entry_name, entry_value)],
682 [Svn::Core::Prop.new(name, value)],
684 Svn::Core::Property.categorize(props))
686 props = {name => value, entry_name => entry_value}
688 {entry_name => entry_value },
692 Svn::Core::Property.categorize2(props))
695 def test_mergeinfo_parse
696 assert_equal({}, Svn::Core::MergeInfo.parse(""))
698 input = "/trunk: 5,7-9,10,11,13,14"
699 result = Svn::Core::MergeInfo.parse(input)
700 assert_equal(["/trunk"], result.keys)
701 assert_equal([[4, 5, true], [6, 11, true], [12, 14, true]],
702 result["/trunk"].collect {|range| range.to_a})
704 input = "/trunk: 5*,7-9,10,11,13,14"
705 result = Svn::Core::MergeInfo.parse(input)
706 assert_equal(["/trunk"], result.keys)
707 assert_equal([[4, 5, false], [6, 11, true], [12, 14, true]],
708 result["/trunk"].collect {|range| range.to_a})
711 def test_mergeinfo_diff
712 input1 = "/trunk: 5,7-9,10,11,13,14"
713 input2 = "/trunk: 5,6,7-9,10,11"
715 info1 = Svn::Core::MergeInfo.parse(input1)
716 info2 = Svn::Core::MergeInfo.parse(input2)
717 result = info1.diff(info2)
718 deleted, added = result
719 assert_equal(["/trunk"], deleted.keys)
720 assert_equal(["/trunk"], added.keys)
721 assert_equal([[12, 14, true]],
722 deleted["/trunk"].collect {|range| range.to_a})
723 assert_equal([[5, 6, true]],
724 added["/trunk"].collect {|range| range.to_a})
727 def test_mergeinfo_merge
728 info = Svn::Core::MergeInfo.parse("/trunk: 5,7-9")
729 assert_equal(["/trunk"], info.keys)
730 assert_equal([[4, 5, true], [6, 9, true]],
731 info["/trunk"].collect {|range| range.to_a})
733 changes = Svn::Core::MergeInfo.parse("/trunk: 6-13")
734 merged = info.merge(changes)
735 assert_equal(["/trunk"], merged.keys)
736 assert_equal([[4, 13, true]],
737 merged["/trunk"].collect {|range| range.to_a})
740 def test_mergeinfo_remove
741 info = Svn::Core::MergeInfo.parse("/trunk: 5-13")
742 assert_equal(["/trunk"], info.keys)
743 assert_equal([[4, 13, true]],
744 info["/trunk"].collect {|range| range.to_a})
746 eraser = Svn::Core::MergeInfo.parse("/trunk: 7,9-11")
747 removed = info.remove(eraser)
748 assert_equal(["/trunk"], removed.keys)
749 assert_equal([[4, 6, true], [7, 8, true], [11, 13, true]],
750 removed["/trunk"].collect {|range| range.to_a})
753 def test_mergeinfo_to_s
754 info = Svn::Core::MergeInfo.parse("/trunk: 5,7,9-13")
755 assert_equal("/trunk:5,7,9-13", info.to_s)
756 assert_not_equal(info.to_s, info.inspect)
758 info = Svn::Core::MergeInfo.parse("/trunk: 5*,7,9-13")
759 assert_equal("/trunk:5*,7,9-13", info.to_s)
760 assert_not_equal(info.to_s, info.inspect)
763 def test_mergeinfo_sort
764 info = Svn::Core::MergeInfo.parse("/trunk: 5,7,9-13")
766 info["/trunk"] = info["/trunk"].reverse
767 assert_equal(["/trunk"], info.keys)
768 assert_equal([[13, 8, true], [7, 6, true], [5, 4, true]],
769 info["/trunk"].collect {|range| range.to_a})
771 sorted_info = info.sort
772 assert_equal(["/trunk"], sorted_info.keys)
773 assert_equal([[5, 4, true], [7, 6, true], [13, 8, true]],
774 sorted_info["/trunk"].collect {|range| range.to_a})
777 def test_range_list_diff
778 range_list1 = Svn::Core::RangeList.new([5, 5, true], [9, 13, true])
779 range_list2 = Svn::Core::RangeList.new([7, 11, true])
781 deleted, added = range_list1.diff(range_list2)
782 assert_equal([[7, 9, true]], added.collect {|range| range.to_a})
783 assert_equal([[5, 5, true], [11, 13, true]],
784 deleted.collect {|range| range.to_a})
787 def test_range_list_merge
788 range_list1 = Svn::Core::RangeList.new([5, 5, true],
789 [7, 7, true], [9, 13, true])
790 range_list2 = Svn::Core::RangeList.new([5, 9, true])
792 merged = range_list1.merge(range_list2)
793 assert_equal([[5, 13, true]], merged.collect {|range| range.to_a})
796 def test_range_list_remove
797 range_list1 = Svn::Core::RangeList.new([5, 5, true],
798 [7, 7, true], [9, 13, true])
799 range_list2 = Svn::Core::RangeList.new([5, 9, true])
801 removed = range_list1.remove(range_list2)
802 assert_equal([[9, 13, true]], removed.collect {|range| range.to_a})
805 def test_range_list_intersect
806 range_list1 = Svn::Core::RangeList.new([5, 9, true])
807 range_list2 = Svn::Core::RangeList.new([5, 5, true],
808 [7, 7, true], [9, 13, true])
810 intersected = range_list1.intersect(range_list2)
811 assert_equal([[5, 5, true], [7, 7, true]],
812 intersected.collect {|range| range.to_a})
815 def test_range_list_reverse
816 range_list = Svn::Core::RangeList.new([5, 5, true],
817 [7, 7, true], [9, 13, true])
819 reversed = range_list.reverse
820 assert_equal([[13, 9, true], [7, 7, true], [5, 5, true]],
821 reversed.collect {|range| range.to_a})
824 def test_range_list_to_s
825 range_list = Svn::Core::RangeList.new([5, 5, true],
826 [7, 7, true], [9, 13, true])
827 assert_equal("6-5,8-7,10-13", range_list.to_s)
828 assert_not_equal("6-5,8-7,10-13", range_list.inspect)
831 def test_mergerange_equality
832 mergerange1 = Svn::Core::MergeRange.new(1,2,true)
833 mergerange2 = Svn::Core::MergeRange.new(1,2,true)
834 mergerange3 = Svn::Core::MergeRange.new(1,2,false)
835 mergerange4 = Svn::Core::MergeRange.new(1,4,true)
837 assert_equal(mergerange1, mergerange2)
838 assert_not_equal(mergerange1, mergerange3)
839 assert_not_equal(mergerange1, mergerange4)
844 pool = Svn::Core::Pool.new
845 now = Time.now.gmtime
846 Svn::Core.time_to_human_cstring(now.to_apr_time, pool)