1require 'test/unit' 2require 'pp' 3require_relative 'envutil' 4 5$m0 = Module.nesting 6 7class TestModule < Test::Unit::TestCase 8 def _wrap_assertion 9 yield 10 end 11 12 def assert_method_defined?(klass, mid, message="") 13 message = build_message(message, "#{klass}\##{mid} expected to be defined.") 14 _wrap_assertion do 15 klass.method_defined?(mid) or 16 raise Test::Unit::AssertionFailedError, message, caller(3) 17 end 18 end 19 20 def assert_method_not_defined?(klass, mid, message="") 21 message = build_message(message, "#{klass}\##{mid} expected to not be defined.") 22 _wrap_assertion do 23 klass.method_defined?(mid) and 24 raise Test::Unit::AssertionFailedError, message, caller(3) 25 end 26 end 27 28 def setup 29 @verbose = $VERBOSE 30 $VERBOSE = nil 31 end 32 33 def teardown 34 $VERBOSE = @verbose 35 end 36 37 def test_LT_0 38 assert_equal true, String < Object 39 assert_equal false, Object < String 40 assert_nil String < Array 41 assert_equal true, Array < Enumerable 42 assert_equal false, Enumerable < Array 43 assert_nil Proc < Comparable 44 assert_nil Comparable < Proc 45 end 46 47 def test_GT_0 48 assert_equal false, String > Object 49 assert_equal true, Object > String 50 assert_nil String > Array 51 assert_equal false, Array > Enumerable 52 assert_equal true, Enumerable > Array 53 assert_nil Comparable > Proc 54 assert_nil Proc > Comparable 55 end 56 57 def test_CMP_0 58 assert_equal(-1, (String <=> Object)) 59 assert_equal 1, (Object <=> String) 60 assert_nil(Array <=> String) 61 end 62 63 ExpectedException = NoMethodError 64 65 # Support stuff 66 67 module Mixin 68 MIXIN = 1 69 def mixin 70 end 71 end 72 73 module User 74 USER = 2 75 include Mixin 76 def user 77 end 78 end 79 80 module Other 81 def other 82 end 83 end 84 85 class AClass 86 def AClass.cm1 87 "cm1" 88 end 89 def AClass.cm2 90 cm1 + "cm2" + cm3 91 end 92 def AClass.cm3 93 "cm3" 94 end 95 96 private_class_method :cm1, "cm3" 97 98 def aClass 99 :aClass 100 end 101 102 def aClass1 103 :aClass1 104 end 105 106 def aClass2 107 :aClass2 108 end 109 110 private :aClass1 111 protected :aClass2 112 end 113 114 class BClass < AClass 115 def bClass1 116 :bClass1 117 end 118 119 private 120 121 def bClass2 122 :bClass2 123 end 124 125 protected 126 def bClass3 127 :bClass3 128 end 129 end 130 131 class CClass < BClass 132 def self.cClass 133 end 134 end 135 136 MyClass = AClass.clone 137 class MyClass 138 public_class_method :cm1 139 end 140 141 # ----------------------------------------------------------- 142 143 def test_CMP # '<=>' 144 assert_equal( 0, Mixin <=> Mixin) 145 assert_equal(-1, User <=> Mixin) 146 assert_equal( 1, Mixin <=> User) 147 148 assert_equal( 0, Object <=> Object) 149 assert_equal(-1, String <=> Object) 150 assert_equal( 1, Object <=> String) 151 end 152 153 def test_GE # '>=' 154 assert(Mixin >= User) 155 assert(Mixin >= Mixin) 156 assert(!(User >= Mixin)) 157 158 assert(Object >= String) 159 assert(String >= String) 160 assert(!(String >= Object)) 161 end 162 163 def test_GT # '>' 164 assert(Mixin > User) 165 assert(!(Mixin > Mixin)) 166 assert(!(User > Mixin)) 167 168 assert(Object > String) 169 assert(!(String > String)) 170 assert(!(String > Object)) 171 end 172 173 def test_LE # '<=' 174 assert(User <= Mixin) 175 assert(Mixin <= Mixin) 176 assert(!(Mixin <= User)) 177 178 assert(String <= Object) 179 assert(String <= String) 180 assert(!(Object <= String)) 181 end 182 183 def test_LT # '<' 184 assert(User < Mixin) 185 assert(!(Mixin < Mixin)) 186 assert(!(Mixin < User)) 187 188 assert(String < Object) 189 assert(!(String < String)) 190 assert(!(Object < String)) 191 end 192 193 def test_VERY_EQUAL # '===' 194 assert(Object === self) 195 assert(Test::Unit::TestCase === self) 196 assert(TestModule === self) 197 assert(!(String === self)) 198 end 199 200 def test_ancestors 201 assert_equal([User, Mixin], User.ancestors) 202 assert_equal([Mixin], Mixin.ancestors) 203 204 ancestors = Object.ancestors 205 mixins = ancestors - [Object, Kernel, BasicObject] 206 mixins << JSON::Ext::Generator::GeneratorMethods::String if defined?(JSON::Ext::Generator::GeneratorMethods::String) 207 assert_equal([Object, Kernel, BasicObject], ancestors - mixins) 208 assert_equal([String, Comparable, Object, Kernel, BasicObject], String.ancestors - mixins) 209 end 210 211 CLASS_EVAL = 2 212 @@class_eval = 'b' 213 214 def test_class_eval 215 Other.class_eval("CLASS_EVAL = 1") 216 assert_equal(1, Other::CLASS_EVAL) 217 assert(Other.constants.include?(:CLASS_EVAL)) 218 assert_equal(2, Other.class_eval { CLASS_EVAL }) 219 220 Other.class_eval("@@class_eval = 'a'") 221 assert_equal('a', Other.class_variable_get(:@@class_eval)) 222 assert_equal('b', Other.class_eval { @@class_eval }) 223 224 Other.class_eval do 225 module_function 226 227 def class_eval_test 228 "foo" 229 end 230 end 231 assert_equal("foo", Other.class_eval_test) 232 233 assert_equal([Other], Other.class_eval { |*args| args }) 234 end 235 236 def test_const_defined? 237 assert(Math.const_defined?(:PI)) 238 assert(Math.const_defined?("PI")) 239 assert(!Math.const_defined?(:IP)) 240 assert(!Math.const_defined?("IP")) 241 end 242 243 def test_bad_constants 244 [ 245 "#<Class:0x7b8b718b>", 246 ":Object", 247 "", 248 ":", 249 ["String::", "[Bug #7573]"], 250 ].each do |name, msg| 251 e = assert_raises(NameError, "#{msg}#{': ' if msg}wrong constant name #{name.dump}") { 252 Object.const_get name 253 } 254 assert_equal("wrong constant name %s" % name, e.message) 255 end 256 end 257 258 def test_leading_colons 259 assert_equal Object, AClass.const_get('::Object') 260 end 261 262 def test_const_get 263 assert_equal(Math::PI, Math.const_get("PI")) 264 assert_equal(Math::PI, Math.const_get(:PI)) 265 end 266 267 def test_nested_get 268 assert_equal Other, Object.const_get([self.class, Other].join('::')) 269 assert_equal User::USER, self.class.const_get([User, 'USER'].join('::')) 270 end 271 272 def test_nested_get_symbol 273 const = [self.class, Other].join('::').to_sym 274 assert_raise(NameError) {Object.const_get(const)} 275 276 const = [User, 'USER'].join('::').to_sym 277 assert_raise(NameError) {self.class.const_get(const)} 278 end 279 280 def test_nested_get_const_missing 281 classes = [] 282 klass = Class.new { 283 define_singleton_method(:const_missing) { |name| 284 classes << name 285 klass 286 } 287 } 288 klass.const_get("Foo::Bar::Baz") 289 assert_equal [:Foo, :Bar, :Baz], classes 290 end 291 292 def test_nested_bad_class 293 assert_raises(TypeError) do 294 self.class.const_get([User, 'USER', 'Foo'].join('::')) 295 end 296 end 297 298 def test_const_set 299 assert(!Other.const_defined?(:KOALA)) 300 Other.const_set(:KOALA, 99) 301 assert(Other.const_defined?(:KOALA)) 302 assert_equal(99, Other::KOALA) 303 Other.const_set("WOMBAT", "Hi") 304 assert_equal("Hi", Other::WOMBAT) 305 end 306 307 def test_constants 308 assert_equal([:MIXIN], Mixin.constants) 309 assert_equal([:MIXIN, :USER], User.constants.sort) 310 end 311 312 def test_self_initialize_copy 313 bug9535 = '[ruby-dev:47989] [Bug #9535]' 314 m = Module.new do 315 def foo 316 :ok 317 end 318 initialize_copy(self) 319 end 320 assert_equal(:ok, Object.new.extend(m).foo, bug9535) 321 end 322 323 def test_dup 324 bug6454 = '[ruby-core:45132]' 325 326 a = Module.new 327 Other.const_set :BUG6454, a 328 329 original = Other::BUG6454.inspect 330 331 b = a.dup 332 Other.const_set :BUG6454_dup, b 333 334 assert_equal "TestModule::Other::BUG6454_dup", b.inspect, bug6454 335 end 336 337 def test_dup_anonymous 338 bug6454 = '[ruby-core:45132]' 339 340 a = Module.new 341 original = a.inspect 342 343 b = a.dup 344 345 refute_equal original, b.inspect, bug6454 346 end 347 348 def test_included_modules 349 assert_equal([], Mixin.included_modules) 350 assert_equal([Mixin], User.included_modules) 351 352 mixins = Object.included_modules - [Kernel] 353 mixins << JSON::Ext::Generator::GeneratorMethods::String if defined?(JSON::Ext::Generator::GeneratorMethods::String) 354 assert_equal([Kernel], Object.included_modules - mixins) 355 assert_equal([Comparable, Kernel], String.included_modules - mixins) 356 end 357 358 def test_instance_methods 359 assert_equal([:user], User.instance_methods(false)) 360 assert_equal([:user, :mixin].sort, User.instance_methods(true).sort) 361 assert_equal([:mixin], Mixin.instance_methods) 362 assert_equal([:mixin], Mixin.instance_methods(true)) 363 assert_equal([:cClass], (class << CClass; self; end).instance_methods(false)) 364 assert_equal([], (class << BClass; self; end).instance_methods(false)) 365 assert_equal([:cm2], (class << AClass; self; end).instance_methods(false)) 366 # Ruby 1.8 feature change: 367 # #instance_methods includes protected methods. 368 #assert_equal([:aClass], AClass.instance_methods(false)) 369 assert_equal([:aClass, :aClass2], AClass.instance_methods(false).sort) 370 assert_equal([:aClass, :aClass2], 371 (AClass.instance_methods(true) - Object.instance_methods(true)).sort) 372 end 373 374 def test_method_defined? 375 assert_method_not_defined?(User, :wombat) 376 assert_method_defined?(User, :user) 377 assert_method_defined?(User, :mixin) 378 assert_method_not_defined?(User, :wombat) 379 assert_method_defined?(User, :user) 380 assert_method_defined?(User, :mixin) 381 end 382 383 def module_exec_aux 384 Proc.new do 385 def dynamically_added_method_3; end 386 end 387 end 388 def module_exec_aux_2(&block) 389 User.module_exec(&block) 390 end 391 392 def test_module_exec 393 User.module_exec do 394 def dynamically_added_method_1; end 395 end 396 assert_method_defined?(User, :dynamically_added_method_1) 397 398 block = Proc.new do 399 def dynamically_added_method_2; end 400 end 401 User.module_exec(&block) 402 assert_method_defined?(User, :dynamically_added_method_2) 403 404 User.module_exec(&module_exec_aux) 405 assert_method_defined?(User, :dynamically_added_method_3) 406 407 module_exec_aux_2 do 408 def dynamically_added_method_4; end 409 end 410 assert_method_defined?(User, :dynamically_added_method_4) 411 end 412 413 def test_module_eval 414 User.module_eval("MODULE_EVAL = 1") 415 assert_equal(1, User::MODULE_EVAL) 416 assert(User.constants.include?(:MODULE_EVAL)) 417 User.instance_eval("remove_const(:MODULE_EVAL)") 418 assert(!User.constants.include?(:MODULE_EVAL)) 419 end 420 421 def test_name 422 assert_equal("Fixnum", Fixnum.name) 423 assert_equal("TestModule::Mixin", Mixin.name) 424 assert_equal("TestModule::User", User.name) 425 end 426 427 def test_classpath 428 m = Module.new 429 n = Module.new 430 m.const_set(:N, n) 431 assert_nil(m.name) 432 assert_nil(n.name) 433 assert_equal([:N], m.constants) 434 m.module_eval("module O end") 435 assert_equal([:N, :O], m.constants) 436 m.module_eval("class C; end") 437 assert_equal([:N, :O, :C], m.constants) 438 assert_nil(m::N.name) 439 assert_match(/\A#<Module:.*>::O\z/, m::O.name) 440 assert_match(/\A#<Module:.*>::C\z/, m::C.name) 441 self.class.const_set(:M, m) 442 prefix = self.class.name + "::M::" 443 assert_equal(prefix+"N", m.const_get(:N).name) 444 assert_equal(prefix+"O", m.const_get(:O).name) 445 assert_equal(prefix+"C", m.const_get(:C).name) 446 end 447 448 def test_private_class_method 449 assert_raise(ExpectedException) { AClass.cm1 } 450 assert_raise(ExpectedException) { AClass.cm3 } 451 assert_equal("cm1cm2cm3", AClass.cm2) 452 end 453 454 def test_private_instance_methods 455 assert_equal([:aClass1], AClass.private_instance_methods(false)) 456 assert_equal([:bClass2], BClass.private_instance_methods(false)) 457 assert_equal([:aClass1, :bClass2], 458 (BClass.private_instance_methods(true) - 459 Object.private_instance_methods(true)).sort) 460 end 461 462 def test_protected_instance_methods 463 assert_equal([:aClass2], AClass.protected_instance_methods) 464 assert_equal([:bClass3], BClass.protected_instance_methods(false)) 465 assert_equal([:bClass3, :aClass2].sort, 466 (BClass.protected_instance_methods(true) - 467 Object.protected_instance_methods(true)).sort) 468 end 469 470 def test_public_class_method 471 assert_equal("cm1", MyClass.cm1) 472 assert_equal("cm1cm2cm3", MyClass.cm2) 473 assert_raise(ExpectedException) { eval "MyClass.cm3" } 474 end 475 476 def test_public_instance_methods 477 assert_equal([:aClass], AClass.public_instance_methods(false)) 478 assert_equal([:bClass1], BClass.public_instance_methods(false)) 479 end 480 481 def test_s_constants 482 c1 = Module.constants 483 Object.module_eval "WALTER = 99" 484 c2 = Module.constants 485 assert_equal([:WALTER], c2 - c1) 486 487 assert_equal([], Module.constants(true)) 488 assert_equal([], Module.constants(false)) 489 490 src = <<-INPUT 491 ary = Module.constants 492 module M 493 WALTER = 99 494 end 495 class Module 496 include M 497 end 498 p Module.constants - ary, Module.constants(true), Module.constants(false) 499 INPUT 500 assert_in_out_err([], src, %w([:M] [:WALTER] []), []) 501 502 klass = Class.new do 503 const_set(:X, 123) 504 end 505 assert_equal(false, klass.class_eval { Module.constants }.include?(:X)) 506 end 507 508 module M1 509 $m1 = Module.nesting 510 module M2 511 $m2 = Module.nesting 512 end 513 end 514 515 def test_s_nesting 516 assert_equal([], $m0) 517 assert_equal([TestModule::M1, TestModule], $m1) 518 assert_equal([TestModule::M1::M2, 519 TestModule::M1, TestModule], $m2) 520 end 521 522 def test_s_new 523 m = Module.new 524 assert_instance_of(Module, m) 525 end 526 527 def test_freeze 528 m = Module.new 529 m.freeze 530 assert_raise(RuntimeError) do 531 m.module_eval do 532 def foo; end 533 end 534 end 535 end 536 537 def test_attr_obsoleted_flag 538 c = Class.new 539 c.class_eval do 540 def initialize 541 @foo = :foo 542 @bar = :bar 543 end 544 attr :foo, true 545 attr :bar, false 546 end 547 o = c.new 548 assert_equal(true, o.respond_to?(:foo)) 549 assert_equal(true, o.respond_to?(:foo=)) 550 assert_equal(true, o.respond_to?(:bar)) 551 assert_equal(false, o.respond_to?(:bar=)) 552 end 553 554 def test_const_get_evaled 555 c1 = Class.new 556 c2 = Class.new(c1) 557 558 eval("c1::Foo = :foo") 559 assert_equal(:foo, c1::Foo) 560 assert_equal(:foo, c2::Foo) 561 assert_equal(:foo, c2.const_get(:Foo)) 562 assert_raise(NameError) { c2.const_get(:Foo, false) } 563 564 eval("c1::Foo = :foo") 565 assert_raise(NameError) { c1::Bar } 566 assert_raise(NameError) { c2::Bar } 567 assert_raise(NameError) { c2.const_get(:Bar) } 568 assert_raise(NameError) { c2.const_get(:Bar, false) } 569 assert_raise(NameError) { c2.const_get("Bar", false) } 570 assert_raise(NameError) { c2.const_get("BaR11", false) } 571 assert_raise(NameError) { Object.const_get("BaR11", false) } 572 573 c1.instance_eval do 574 def const_missing(x) 575 x 576 end 577 end 578 579 assert_equal(:Bar, c1::Bar) 580 assert_equal(:Bar, c2::Bar) 581 assert_equal(:Bar, c2.const_get(:Bar)) 582 assert_equal(:Bar, c2.const_get(:Bar, false)) 583 assert_equal(:Bar, c2.const_get("Bar")) 584 assert_equal(:Bar, c2.const_get("Bar", false)) 585 586 v = c2.const_get("Bar11", false) 587 assert_equal("Bar11".to_sym, v) 588 589 assert_raise(NameError) { c1.const_get(:foo) } 590 end 591 592 def test_const_set_invalid_name 593 c1 = Class.new 594 assert_raise(NameError) { c1.const_set(:foo, :foo) } 595 end 596 597 def test_const_get_invalid_name 598 c1 = Class.new 599 assert_raise(NameError) { c1.const_get(:foo) } 600 bug5084 = '[ruby-dev:44200]' 601 assert_raise(TypeError, bug5084) { c1.const_get(1) } 602 bug7574 = '[ruby-dev:46749]' 603 e = assert_raise(NameError) { Object.const_get("String\0") } 604 assert_equal("wrong constant name \"String\\u0000\"", e.message, bug7574) 605 end 606 607 def test_const_defined_invalid_name 608 c1 = Class.new 609 assert_raise(NameError) { c1.const_defined?(:foo) } 610 bug5084 = '[ruby-dev:44200]' 611 assert_raise(TypeError, bug5084) { c1.const_defined?(1) } 612 bug7574 = '[ruby-dev:46749]' 613 e = assert_raise(NameError) { Object.const_defined?("String\0") } 614 assert_equal("wrong constant name \"String\\u0000\"", e.message, bug7574) 615 end 616 617 def test_const_get_no_inherited 618 bug3422 = '[ruby-core:30719]' 619 assert_in_out_err([], <<-INPUT, %w[1 NameError A], [], bug3422) 620 BasicObject::A = 1 621 puts [true, false].map {|inh| 622 begin 623 Object.const_get(:A, inh) 624 rescue NameError => e 625 [e.class, e.name] 626 end 627 } 628 INPUT 629 end 630 631 def test_const_get_inherited 632 bug3423 = '[ruby-core:30720]' 633 assert_in_out_err([], <<-INPUT, %w[NameError A NameError A], [], bug3423) 634 module Foo; A = 1; end 635 class Object; include Foo; end 636 class Bar; include Foo; end 637 638 puts [Object, Bar].map {|klass| 639 begin 640 klass.const_get(:A, false) 641 rescue NameError => e 642 [e.class, e.name] 643 end 644 } 645 INPUT 646 end 647 648 def test_const_in_module 649 bug3423 = '[ruby-core:37698]' 650 assert_in_out_err([], <<-INPUT, %w[ok], [], bug3423) 651 module LangModuleSpecInObject 652 module LangModuleTop 653 end 654 end 655 include LangModuleSpecInObject 656 module LangModuleTop 657 end 658 puts "ok" if LangModuleSpecInObject::LangModuleTop == LangModuleTop 659 INPUT 660 661 bug5264 = '[ruby-core:39227]' 662 assert_in_out_err([], <<-'INPUT', [], [], bug5264) 663 class A 664 class X; end 665 end 666 class B < A 667 module X; end 668 end 669 INPUT 670 end 671 672 def test_class_variable_get 673 c = Class.new 674 c.class_eval('@@foo = :foo') 675 assert_equal(:foo, c.class_variable_get(:@@foo)) 676 assert_raise(NameError) { c.class_variable_get(:@@bar) } # c.f. instance_variable_get 677 assert_raise(NameError) { c.class_variable_get(:'@@') } 678 assert_raise(NameError) { c.class_variable_get('@@') } 679 assert_raise(NameError) { c.class_variable_get(:foo) } 680 end 681 682 def test_class_variable_set 683 c = Class.new 684 c.class_variable_set(:@@foo, :foo) 685 assert_equal(:foo, c.class_eval('@@foo')) 686 assert_raise(NameError) { c.class_variable_set(:'@@', 1) } 687 assert_raise(NameError) { c.class_variable_set('@@', 1) } 688 assert_raise(NameError) { c.class_variable_set(:foo, 1) } 689 end 690 691 def test_class_variable_defined 692 c = Class.new 693 c.class_eval('@@foo = :foo') 694 assert_equal(true, c.class_variable_defined?(:@@foo)) 695 assert_equal(false, c.class_variable_defined?(:@@bar)) 696 assert_raise(NameError) { c.class_variable_defined?(:'@@') } 697 assert_raise(NameError) { c.class_variable_defined?('@@') } 698 assert_raise(NameError) { c.class_variable_defined?(:foo) } 699 end 700 701 def test_remove_class_variable 702 c = Class.new 703 c.class_eval('@@foo = :foo') 704 c.class_eval { remove_class_variable(:@@foo) } 705 assert_equal(false, c.class_variable_defined?(:@@foo)) 706 end 707 708 def test_export_method 709 m = Module.new 710 assert_raise(NameError) do 711 m.instance_eval { public(:foo) } 712 end 713 end 714 715 def test_attr 716 assert_in_out_err([], <<-INPUT, %w(:ok nil), /warning: private attribute\?$/) 717 $VERBOSE = true 718 c = Class.new 719 c.instance_eval do 720 private 721 attr_reader :foo 722 end 723 o = c.new 724 o.foo rescue p(:ok) 725 p(o.instance_eval { foo }) 726 INPUT 727 728 c = Class.new 729 assert_raise(NameError) do 730 c.instance_eval { attr_reader :"." } 731 end 732 end 733 734 def test_undef 735 assert_raise(SecurityError) do 736 Thread.new do 737 $SAFE = 4 738 Class.instance_eval { undef_method(:foo) } 739 end.join 740 end 741 742 c = Class.new 743 assert_raise(NameError) do 744 c.instance_eval { undef_method(:foo) } 745 end 746 747 m = Module.new 748 assert_raise(NameError) do 749 m.instance_eval { undef_method(:foo) } 750 end 751 752 o = Object.new 753 assert_raise(NameError) do 754 class << o; self; end.instance_eval { undef_method(:foo) } 755 end 756 757 %w(object_id __send__ initialize).each do |n| 758 assert_in_out_err([], <<-INPUT, [], %r"warning: undefining `#{n}' may cause serious problems$") 759 $VERBOSE = false 760 Class.new.instance_eval { undef_method(:#{n}) } 761 INPUT 762 end 763 end 764 765 def test_alias 766 m = Module.new 767 assert_raise(NameError) do 768 m.class_eval { alias foo bar } 769 end 770 771 assert_in_out_err([], <<-INPUT, %w(2), /discarding old foo$/) 772 $VERBOSE = true 773 c = Class.new 774 c.class_eval do 775 def foo; 1; end 776 def bar; 2; end 777 end 778 c.class_eval { alias foo bar } 779 p c.new.foo 780 INPUT 781 end 782 783 def test_mod_constants 784 m = Module.new 785 m.const_set(:Foo, :foo) 786 assert_equal([:Foo], m.constants(true)) 787 assert_equal([:Foo], m.constants(false)) 788 m.instance_eval { remove_const(:Foo) } 789 end 790 791 class Bug9413 792 class << self 793 Foo = :foo 794 end 795 end 796 797 def test_singleton_constants 798 bug9413 = '[ruby-core:59763] [Bug #9413]' 799 c = Bug9413.singleton_class 800 assert_include(c.constants(true), :Foo, bug9413) 801 assert_include(c.constants(false), :Foo, bug9413) 802 end 803 804 def test_frozen_class 805 m = Module.new 806 m.freeze 807 assert_raise(RuntimeError) do 808 m.instance_eval { undef_method(:foo) } 809 end 810 811 c = Class.new 812 c.freeze 813 assert_raise(RuntimeError) do 814 c.instance_eval { undef_method(:foo) } 815 end 816 817 o = Object.new 818 c = class << o; self; end 819 c.freeze 820 assert_raise(RuntimeError) do 821 c.instance_eval { undef_method(:foo) } 822 end 823 end 824 825 def test_method_defined 826 c = Class.new 827 c.class_eval do 828 def foo; end 829 def bar; end 830 def baz; end 831 public :foo 832 protected :bar 833 private :baz 834 end 835 836 assert_equal(true, c.public_method_defined?(:foo)) 837 assert_equal(false, c.public_method_defined?(:bar)) 838 assert_equal(false, c.public_method_defined?(:baz)) 839 840 assert_equal(false, c.protected_method_defined?(:foo)) 841 assert_equal(true, c.protected_method_defined?(:bar)) 842 assert_equal(false, c.protected_method_defined?(:baz)) 843 844 assert_equal(false, c.private_method_defined?(:foo)) 845 assert_equal(false, c.private_method_defined?(:bar)) 846 assert_equal(true, c.private_method_defined?(:baz)) 847 end 848 849 def test_change_visibility_under_safe4 850 c = Class.new 851 c.class_eval do 852 def foo; end 853 end 854 assert_raise(SecurityError) do 855 Thread.new do 856 $SAFE = 4 857 c.class_eval { private :foo } 858 end.join 859 end 860 end 861 862 def test_top_public_private 863 assert_in_out_err([], <<-INPUT, %w([:foo] [:bar]), []) 864 private 865 def foo; :foo; end 866 public 867 def bar; :bar; end 868 p self.private_methods.grep(/^foo$|^bar$/) 869 p self.methods.grep(/^foo$|^bar$/) 870 INPUT 871 end 872 873 def test_append_features 874 t = nil 875 m = Module.new 876 m.module_eval do 877 def foo; :foo; end 878 end 879 class << m; self; end.class_eval do 880 define_method(:append_features) do |mod| 881 t = mod 882 super(mod) 883 end 884 end 885 886 m2 = Module.new 887 m2.module_eval { include(m) } 888 assert_equal(m2, t) 889 890 o = Object.new 891 o.extend(m2) 892 assert_equal(true, o.respond_to?(:foo)) 893 end 894 895 def test_append_features_raise 896 m = Module.new 897 m.module_eval do 898 def foo; :foo; end 899 end 900 class << m; self; end.class_eval do 901 define_method(:append_features) {|mod| raise } 902 end 903 904 m2 = Module.new 905 assert_raise(RuntimeError) do 906 m2.module_eval { include(m) } 907 end 908 909 o = Object.new 910 o.extend(m2) 911 assert_equal(false, o.respond_to?(:foo)) 912 end 913 914 def test_append_features_type_error 915 assert_raise(TypeError) do 916 Module.new.instance_eval { append_features(1) } 917 end 918 end 919 920 def test_included 921 m = Module.new 922 m.module_eval do 923 def foo; :foo; end 924 end 925 class << m; self; end.class_eval do 926 define_method(:included) {|mod| raise } 927 end 928 929 m2 = Module.new 930 assert_raise(RuntimeError) do 931 m2.module_eval { include(m) } 932 end 933 934 o = Object.new 935 o.extend(m2) 936 assert_equal(true, o.respond_to?(:foo)) 937 end 938 939 def test_cyclic_include 940 m1 = Module.new 941 m2 = Module.new 942 m1.instance_eval { include(m2) } 943 assert_raise(ArgumentError) do 944 m2.instance_eval { include(m1) } 945 end 946 end 947 948 def test_include_p 949 m = Module.new 950 c1 = Class.new 951 c1.instance_eval { include(m) } 952 c2 = Class.new(c1) 953 assert_equal(true, c1.include?(m)) 954 assert_equal(true, c2.include?(m)) 955 assert_equal(false, m.include?(m)) 956 end 957 958 def test_include_under_safe4 959 m = Module.new 960 c1 = Class.new 961 assert_raise(SecurityError) do 962 lambda { 963 $SAFE = 4 964 c1.instance_eval { include(m) } 965 }.call 966 end 967 assert_nothing_raised do 968 lambda { 969 $SAFE = 4 970 c2 = Class.new 971 c2.instance_eval { include(m) } 972 }.call 973 end 974 end 975 976 def test_send 977 a = AClass.new 978 assert_equal(:aClass, a.__send__(:aClass)) 979 assert_equal(:aClass1, a.__send__(:aClass1)) 980 assert_equal(:aClass2, a.__send__(:aClass2)) 981 b = BClass.new 982 assert_equal(:aClass, b.__send__(:aClass)) 983 assert_equal(:aClass1, b.__send__(:aClass1)) 984 assert_equal(:aClass2, b.__send__(:aClass2)) 985 assert_equal(:bClass1, b.__send__(:bClass1)) 986 assert_equal(:bClass2, b.__send__(:bClass2)) 987 assert_equal(:bClass3, b.__send__(:bClass3)) 988 end 989 990 991 def test_nonascii_name 992 c = eval("class ::C\u{df}; self; end") 993 assert_equal("C\u{df}", c.name, '[ruby-core:24600]') 994 c = eval("class C\u{df}; self; end") 995 assert_equal("TestModule::C\u{df}", c.name, '[ruby-core:24600]') 996 end 997 998 def test_method_added 999 memo = [] 1000 mod = Module.new do 1001 mod = self 1002 (class << self ; self ; end).class_eval do 1003 define_method :method_added do |sym| 1004 memo << sym 1005 memo << mod.instance_methods(false) 1006 memo << (mod.instance_method(sym) rescue nil) 1007 end 1008 end 1009 def f 1010 end 1011 alias g f 1012 attr_reader :a 1013 attr_writer :a 1014 end 1015 assert_equal :f, memo.shift 1016 assert_equal [:f], memo.shift, '[ruby-core:25536]' 1017 assert_equal mod.instance_method(:f), memo.shift 1018 assert_equal :g, memo.shift 1019 assert_equal [:f, :g], memo.shift 1020 assert_equal mod.instance_method(:f), memo.shift 1021 assert_equal :a, memo.shift 1022 assert_equal [:f, :g, :a], memo.shift 1023 assert_equal mod.instance_method(:a), memo.shift 1024 assert_equal :a=, memo.shift 1025 assert_equal [:f, :g, :a, :a=], memo.shift 1026 assert_equal mod.instance_method(:a=), memo.shift 1027 end 1028 1029 def test_method_undefined 1030 added = [] 1031 undefed = [] 1032 removed = [] 1033 mod = Module.new do 1034 mod = self 1035 def f 1036 end 1037 (class << self ; self ; end).class_eval do 1038 define_method :method_added do |sym| 1039 added << sym 1040 end 1041 define_method :method_undefined do |sym| 1042 undefed << sym 1043 end 1044 define_method :method_removed do |sym| 1045 removed << sym 1046 end 1047 end 1048 end 1049 assert_method_defined?(mod, :f) 1050 mod.module_eval do 1051 undef :f 1052 end 1053 assert_equal [], added 1054 assert_equal [:f], undefed 1055 assert_equal [], removed 1056 end 1057 1058 def test_method_removed 1059 added = [] 1060 undefed = [] 1061 removed = [] 1062 mod = Module.new do 1063 mod = self 1064 def f 1065 end 1066 (class << self ; self ; end).class_eval do 1067 define_method :method_added do |sym| 1068 added << sym 1069 end 1070 define_method :method_undefined do |sym| 1071 undefed << sym 1072 end 1073 define_method :method_removed do |sym| 1074 removed << sym 1075 end 1076 end 1077 end 1078 assert_method_defined?(mod, :f) 1079 mod.module_eval do 1080 remove_method :f 1081 end 1082 assert_equal [], added 1083 assert_equal [], undefed 1084 assert_equal [:f], removed 1085 end 1086 1087 def test_method_redefinition 1088 feature2155 = '[ruby-dev:39400]' 1089 1090 line = __LINE__+4 1091 stderr = EnvUtil.verbose_warning do 1092 Module.new do 1093 def foo; end 1094 def foo; end 1095 end 1096 end 1097 assert_match(/:#{line}: warning: method redefined; discarding old foo/, stderr) 1098 assert_match(/:#{line-1}: warning: previous definition of foo/, stderr, feature2155) 1099 1100 stderr = EnvUtil.verbose_warning do 1101 Module.new do 1102 def foo; end 1103 alias bar foo 1104 def foo; end 1105 end 1106 end 1107 assert_equal("", stderr) 1108 1109 stderr = EnvUtil.verbose_warning do 1110 Module.new do 1111 def foo; end 1112 alias bar foo 1113 alias bar foo 1114 end 1115 end 1116 assert_equal("", stderr) 1117 1118 line = __LINE__+4 1119 stderr = EnvUtil.verbose_warning do 1120 Module.new do 1121 define_method(:foo) do end 1122 def foo; end 1123 end 1124 end 1125 assert_match(/:#{line}: warning: method redefined; discarding old foo/, stderr) 1126 assert_match(/:#{line-1}: warning: previous definition of foo/, stderr, feature2155) 1127 1128 stderr = EnvUtil.verbose_warning do 1129 Module.new do 1130 define_method(:foo) do end 1131 alias bar foo 1132 alias bar foo 1133 end 1134 end 1135 assert_equal("", stderr) 1136 1137 stderr = EnvUtil.verbose_warning do 1138 Module.new do 1139 module_function 1140 def foo; end 1141 module_function :foo 1142 end 1143 end 1144 assert_equal("", stderr, '[ruby-dev:39397]') 1145 1146 stderr = EnvUtil.verbose_warning do 1147 Module.new do 1148 def foo; end 1149 undef foo 1150 end 1151 end 1152 assert_equal("", stderr) 1153 end 1154 1155 def test_protected_singleton_method 1156 klass = Class.new 1157 x = klass.new 1158 class << x 1159 protected 1160 1161 def foo 1162 end 1163 end 1164 assert_raise(NoMethodError) do 1165 x.foo 1166 end 1167 klass.send(:define_method, :bar) do 1168 x.foo 1169 end 1170 assert_nothing_raised do 1171 x.bar 1172 end 1173 y = klass.new 1174 assert_raise(NoMethodError) do 1175 y.bar 1176 end 1177 end 1178 1179 def test_uninitialized_toplevel_constant 1180 bug3123 = '[ruby-dev:40951]' 1181 e = assert_raise(NameError) {eval("Bug3123", TOPLEVEL_BINDING)} 1182 assert_not_match(/Object::/, e.message, bug3123) 1183 end 1184 1185 def test_attr_inherited_visibility 1186 bug3406 = '[ruby-core:30638]' 1187 c = Class.new do 1188 class << self 1189 private 1190 def attr_accessor(*); super; end 1191 end 1192 attr_accessor :x 1193 end.new 1194 assert_nothing_raised(bug3406) {c.x = 1} 1195 assert_equal(1, c.x, bug3406) 1196 end 1197 1198 def test_attr_writer_with_no_arguments 1199 bug8540 = "[ruby-core:55543]" 1200 c = Class.new do 1201 attr_writer :foo 1202 end 1203 assert_raise(ArgumentError) { c.new.send :foo= } 1204 end 1205 1206 def test_private_constant 1207 c = Class.new 1208 c.const_set(:FOO, "foo") 1209 assert_equal("foo", c::FOO) 1210 c.private_constant(:FOO) 1211 assert_raise(NameError) { c::FOO } 1212 assert_equal("foo", c.class_eval("FOO")) 1213 assert_equal("foo", c.const_get("FOO")) 1214 $VERBOSE, verbose = nil, $VERBOSE 1215 c.const_set(:FOO, "foo") 1216 $VERBOSE = verbose 1217 assert_raise(NameError) { c::FOO } 1218 end 1219 1220 def test_private_constant2 1221 c = Class.new 1222 c.const_set(:FOO, "foo") 1223 c.const_set(:BAR, "bar") 1224 assert_equal("foo", c::FOO) 1225 assert_equal("bar", c::BAR) 1226 c.private_constant(:FOO, :BAR) 1227 assert_raise(NameError) { c::FOO } 1228 assert_raise(NameError) { c::BAR } 1229 assert_equal("foo", c.class_eval("FOO")) 1230 assert_equal("bar", c.class_eval("BAR")) 1231 end 1232 1233 def test_private_constant_with_no_args 1234 assert_in_out_err([], <<-RUBY, [], ["-:3: warning: private_constant with no argument is just ignored"]) 1235 $-w = true 1236 class X 1237 private_constant 1238 end 1239 RUBY 1240 end 1241 1242 class PrivateClass 1243 end 1244 private_constant :PrivateClass 1245 1246 def test_define_module_under_private_constant 1247 assert_raise(NameError) do 1248 eval %q{class TestModule::PrivateClass; end} 1249 end 1250 assert_raise(NameError) do 1251 eval %q{module TestModule::PrivateClass::TestModule; end} 1252 end 1253 eval %q{class PrivateClass; end} 1254 eval %q{module PrivateClass::TestModule; end} 1255 assert_instance_of(Module, PrivateClass::TestModule) 1256 PrivateClass.class_eval { remove_const(:TestModule) } 1257 end 1258 1259 def test_public_constant 1260 c = Class.new 1261 c.const_set(:FOO, "foo") 1262 assert_equal("foo", c::FOO) 1263 c.private_constant(:FOO) 1264 assert_raise(NameError) { c::FOO } 1265 assert_equal("foo", c.class_eval("FOO")) 1266 c.public_constant(:FOO) 1267 assert_equal("foo", c::FOO) 1268 end 1269 1270 def test_constants_with_private_constant 1271 assert(!(::TestModule).constants.include?(:PrivateClass)) 1272 end 1273 1274 def test_toplevel_private_constant 1275 src = <<-INPUT 1276 class Object 1277 private_constant :Object 1278 end 1279 p Object 1280 begin 1281 p ::Object 1282 rescue 1283 p :ok 1284 end 1285 INPUT 1286 assert_in_out_err([], src, %w(Object :ok), []) 1287 end 1288 1289 def test_private_constants_clear_inlinecache 1290 bug5702 = '[ruby-dev:44929]' 1291 src = <<-INPUT 1292 class A 1293 C = :Const 1294 def self.get_C 1295 A::C 1296 end 1297 # fill cache 1298 A.get_C 1299 private_constant :C, :D rescue nil 1300 begin 1301 A.get_C 1302 rescue NameError 1303 puts "A.get_C" 1304 end 1305 end 1306 INPUT 1307 assert_in_out_err([], src, %w(A.get_C), [], bug5702) 1308 end 1309 1310 def test_constant_lookup_in_method_defined_by_class_eval 1311 src = <<-INPUT 1312 class A 1313 B = 42 1314 end 1315 1316 A.class_eval do 1317 def self.f 1318 B 1319 end 1320 1321 def f 1322 B 1323 end 1324 end 1325 1326 begin 1327 A.f 1328 rescue NameError 1329 puts "A.f" 1330 end 1331 begin 1332 A.new.f 1333 rescue NameError 1334 puts "A.new.f" 1335 end 1336 INPUT 1337 assert_in_out_err([], src, %w(A.f A.new.f), []) 1338 end 1339 1340 def test_constant_lookup_in_toplevel_class_eval 1341 src = <<-INPUT 1342 module X 1343 A = 123 1344 end 1345 begin 1346 X.class_eval { A } 1347 rescue NameError => e 1348 puts e 1349 end 1350 INPUT 1351 assert_in_out_err([], src, ["uninitialized constant A"], []) 1352 end 1353 1354 def test_constant_lookup_in_module_in_class_eval 1355 src = <<-INPUT 1356 class A 1357 B = 42 1358 end 1359 1360 A.class_eval do 1361 module C 1362 begin 1363 B 1364 rescue NameError 1365 puts "NameError" 1366 end 1367 end 1368 end 1369 INPUT 1370 assert_in_out_err([], src, ["NameError"], []) 1371 end 1372 1373 module M0 1374 def m1; [:M0] end 1375 end 1376 module M1 1377 def m1; [:M1, *super] end 1378 end 1379 module M2 1380 def m1; [:M2, *super] end 1381 end 1382 M3 = Module.new do 1383 def m1; [:M3, *super] end 1384 end 1385 module M4 1386 def m1; [:M4, *super] end 1387 end 1388 class C 1389 def m1; end 1390 end 1391 class C0 < C 1392 include M0 1393 prepend M1 1394 def m1; [:C0, *super] end 1395 end 1396 class C1 < C0 1397 prepend M2, M3 1398 include M4 1399 def m1; [:C1, *super] end 1400 end 1401 1402 def test_prepend 1403 obj = C0.new 1404 expected = [:M1,:C0,:M0] 1405 assert_equal(expected, obj.m1) 1406 obj = C1.new 1407 expected = [:M2,:M3,:C1,:M4,:M1,:C0,:M0] 1408 assert_equal(expected, obj.m1) 1409 end 1410 1411 def test_prepend_inheritance 1412 bug6654 = '[ruby-core:45914]' 1413 a = labeled_module("a") 1414 b = labeled_module("b") {include a} 1415 c = labeled_class("c") {prepend b} 1416 assert_operator(c, :<, b, bug6654) 1417 assert_operator(c, :<, a, bug6654) 1418 bug8357 = '[ruby-core:54736] [Bug #8357]' 1419 b = labeled_module("b") {prepend a} 1420 c = labeled_class("c") {include b} 1421 assert_operator(c, :<, b, bug8357) 1422 assert_operator(c, :<, a, bug8357) 1423 bug8357 = '[ruby-core:54742] [Bug #8357]' 1424 assert_kind_of(b, c.new, bug8357) 1425 end 1426 1427 def test_prepend_instance_methods 1428 bug6655 = '[ruby-core:45915]' 1429 assert_equal(Object.instance_methods, Class.new {prepend Module.new}.instance_methods, bug6655) 1430 end 1431 1432 def test_prepend_singleton_methods 1433 o = Object.new 1434 o.singleton_class.class_eval {prepend Module.new} 1435 assert_equal([], o.singleton_methods) 1436 end 1437 1438 def test_prepend_remove_method 1439 c = Class.new do 1440 prepend Module.new {def foo; end} 1441 end 1442 assert_raise(NameError) do 1443 c.class_eval do 1444 remove_method(:foo) 1445 end 1446 end 1447 c.class_eval do 1448 def foo; end 1449 end 1450 removed = nil 1451 c.singleton_class.class_eval do 1452 define_method(:method_removed) {|id| removed = id} 1453 end 1454 assert_nothing_raised(NoMethodError, NameError, '[Bug #7843]') do 1455 c.class_eval do 1456 remove_method(:foo) 1457 end 1458 end 1459 assert_equal(:foo, removed) 1460 end 1461 1462 def test_prepend_class_ancestors 1463 bug6658 = '[ruby-core:45919]' 1464 m = labeled_module("m") 1465 c = labeled_class("c") {prepend m} 1466 assert_equal([m, c], c.ancestors[0, 2], bug6658) 1467 1468 bug6662 = '[ruby-dev:45868]' 1469 c2 = labeled_class("c2", c) 1470 anc = c2.ancestors 1471 assert_equal([c2, m, c, Object], anc[0..anc.index(Object)], bug6662) 1472 end 1473 1474 def test_prepend_module_ancestors 1475 bug6659 = '[ruby-dev:45861]' 1476 m0 = labeled_module("m0") {def x; [:m0, *super] end} 1477 m1 = labeled_module("m1") {def x; [:m1, *super] end; prepend m0} 1478 m2 = labeled_module("m2") {def x; [:m2, *super] end; prepend m1} 1479 c0 = labeled_class("c0") {def x; [:c0] end} 1480 c1 = labeled_class("c1") {def x; [:c1] end; prepend m2} 1481 c2 = labeled_class("c2", c0) {def x; [:c2, *super] end; include m2} 1482 1483 assert_equal([m0, m1], m1.ancestors, bug6659) 1484 1485 bug6662 = '[ruby-dev:45868]' 1486 assert_equal([m0, m1, m2], m2.ancestors, bug6662) 1487 assert_equal([m0, m1, m2, c1], c1.ancestors[0, 4], bug6662) 1488 assert_equal([:m0, :m1, :m2, :c1], c1.new.x) 1489 assert_equal([c2, m0, m1, m2, c0], c2.ancestors[0, 5], bug6662) 1490 assert_equal([:c2, :m0, :m1, :m2, :c0], c2.new.x) 1491 1492 m3 = labeled_module("m3") {include m1; prepend m1} 1493 assert_equal([m3, m0, m1], m3.ancestors) 1494 m3 = labeled_module("m3") {prepend m1; include m1} 1495 assert_equal([m0, m1, m3], m3.ancestors) 1496 m3 = labeled_module("m3") {prepend m1; prepend m1} 1497 assert_equal([m0, m1, m3], m3.ancestors) 1498 m3 = labeled_module("m3") {include m1; include m1} 1499 assert_equal([m3, m0, m1], m3.ancestors) 1500 end 1501 1502 def labeled_module(name, &block) 1503 EnvUtil.labeled_module(name, &block) 1504 end 1505 1506 def labeled_class(name, superclass = Object, &block) 1507 EnvUtil.labeled_class(name, superclass, &block) 1508 end 1509 1510 def test_prepend_instance_methods_false 1511 bug6660 = '[ruby-dev:45863]' 1512 assert_equal([:m1], Class.new{ prepend Module.new; def m1; end }.instance_methods(false), bug6660) 1513 assert_equal([:m1], Class.new(Class.new{def m2;end}){ prepend Module.new; def m1; end }.instance_methods(false), bug6660) 1514 end 1515 1516 def test_cyclic_prepend 1517 bug7841 = '[ruby-core:52205] [Bug #7841]' 1518 m1 = Module.new 1519 m2 = Module.new 1520 m1.instance_eval { prepend(m2) } 1521 assert_raise(ArgumentError, bug7841) do 1522 m2.instance_eval { prepend(m1) } 1523 end 1524 end 1525 1526 def test_prepend_optmethod 1527 bug7983 = '[ruby-dev:47124] [Bug #7983]' 1528 assert_separately [], %{ 1529 module M 1530 def /(other) 1531 to_f / other 1532 end 1533 end 1534 Fixnum.send(:prepend, M) 1535 assert_equal(0.5, 1 / 2, "#{bug7983}") 1536 } 1537 assert_equal(0, 1 / 2) 1538 end 1539 1540 def test_prepend_visibility 1541 bug8005 = '[ruby-core:53106] [Bug #8005]' 1542 c = Class.new do 1543 prepend Module.new {} 1544 def foo() end 1545 protected :foo 1546 end 1547 a = c.new 1548 assert_respond_to a, [:foo, true] 1549 assert_nothing_raised(NoMethodError) {a.send :foo} 1550 end 1551 1552 def test_prepend_visibility_inherited 1553 bug8238 = '[ruby-core:54105] [Bug #8238]' 1554 assert_separately [], <<-"end;", timeout: 3 1555 class A 1556 def foo() A; end 1557 private :foo 1558 end 1559 class B < A 1560 public :foo 1561 prepend Module.new 1562 end 1563 assert_equal(A, B.new.foo, "#{bug8238}") 1564 end; 1565 end 1566 1567 def test_prepend_included_modules 1568 bug8025 = '[ruby-core:53158] [Bug #8025]' 1569 mixin = labeled_module("mixin") 1570 c = labeled_module("c") {prepend mixin} 1571 im = c.included_modules 1572 assert_not_include(im, c, bug8025) 1573 assert_include(im, mixin, bug8025) 1574 c1 = labeled_class("c1") {prepend mixin} 1575 c2 = labeled_class("c2", c1) 1576 im = c2.included_modules 1577 assert_not_include(im, c1, bug8025) 1578 assert_not_include(im, c2, bug8025) 1579 assert_include(im, mixin, bug8025) 1580 end 1581 1582 def test_prepend_super_in_alias 1583 bug7842 = '[Bug #7842]' 1584 1585 p = labeled_module("P") do 1586 def m; "P"+super; end 1587 end 1588 a = labeled_class("A") do 1589 def m; "A"; end 1590 end 1591 b = labeled_class("B", a) do 1592 def m; "B"+super; end 1593 alias m2 m 1594 prepend p 1595 alias m3 m 1596 end 1597 assert_equal("BA", b.new.m2, bug7842) 1598 assert_equal("PBA", b.new.m3, bug7842) 1599 end 1600 1601 def test_include_super_in_alias 1602 bug9236 = '[Bug #9236]' 1603 1604 fun = labeled_module("Fun") do 1605 def hello 1606 orig_hello 1607 end 1608 end 1609 1610 m1 = labeled_module("M1") do 1611 def hello 1612 'hello!' 1613 end 1614 end 1615 1616 m2 = labeled_module("M2") do 1617 def hello 1618 super 1619 end 1620 end 1621 1622 foo = labeled_class("Foo") do 1623 include m1 1624 include m2 1625 1626 alias orig_hello hello 1627 include fun 1628 end 1629 1630 assert_equal('hello!', foo.new.hello, bug9236) 1631 end 1632 1633 def test_class_variables 1634 m = Module.new 1635 m.class_variable_set(:@@foo, 1) 1636 m2 = Module.new 1637 m2.send(:include, m) 1638 m2.class_variable_set(:@@bar, 2) 1639 assert_equal([:@@foo], m.class_variables) 1640 assert_equal([:@@bar, :@@foo], m2.class_variables) 1641 assert_equal([:@@bar, :@@foo], m2.class_variables(true)) 1642 assert_equal([:@@bar], m2.class_variables(false)) 1643 end 1644 1645 Bug6891 = '[ruby-core:47241]' 1646 1647 def test_extend_module_with_protected_method 1648 list = [] 1649 1650 x = Class.new { 1651 @list = list 1652 1653 extend Module.new { 1654 protected 1655 1656 def inherited(klass) 1657 @list << "protected" 1658 super(klass) 1659 end 1660 } 1661 1662 extend Module.new { 1663 def inherited(klass) 1664 @list << "public" 1665 super(klass) 1666 end 1667 } 1668 } 1669 1670 assert_nothing_raised(NoMethodError, Bug6891) {Class.new(x)} 1671 assert_equal(['public', 'protected'], list) 1672 end 1673 1674 def test_extend_module_with_protected_bmethod 1675 list = [] 1676 1677 x = Class.new { 1678 extend Module.new { 1679 protected 1680 1681 define_method(:inherited) do |klass| 1682 list << "protected" 1683 super(klass) 1684 end 1685 } 1686 1687 extend Module.new { 1688 define_method(:inherited) do |klass| 1689 list << "public" 1690 super(klass) 1691 end 1692 } 1693 } 1694 1695 assert_nothing_raised(NoMethodError, Bug6891) {Class.new(x)} 1696 assert_equal(['public', 'protected'], list) 1697 end 1698 1699 def test_invalid_attr 1700 %w[ 1701 foo? 1702 @foo 1703 @@foo 1704 $foo 1705 ].each do |name| 1706 assert_raises(NameError) do 1707 Module.new { attr_accessor name.to_sym } 1708 end 1709 end 1710 end 1711 1712 class AttrTest 1713 class << self 1714 attr_accessor :cattr 1715 end 1716 attr_accessor :iattr 1717 def ivar 1718 @ivar 1719 end 1720 end 1721 1722 def test_uninitialized_instance_variable 1723 a = AttrTest.new 1724 stderr = EnvUtil.verbose_warning do 1725 assert_nil(a.ivar) 1726 end 1727 assert_match(/instance variable @ivar not initialized/, stderr) 1728 a.instance_variable_set(:@ivar, 42) 1729 stderr = EnvUtil.verbose_warning do 1730 assert_equal(42, a.ivar) 1731 end 1732 assert_equal("", stderr) 1733 end 1734 1735 def test_uninitialized_attr 1736 a = AttrTest.new 1737 stderr = EnvUtil.verbose_warning do 1738 assert_nil(a.iattr) 1739 end 1740 assert_equal("", stderr) 1741 a.iattr = 42 1742 stderr = EnvUtil.verbose_warning do 1743 assert_equal(42, a.iattr) 1744 end 1745 assert_equal("", stderr) 1746 end 1747 1748 def test_uninitialized_attr_class 1749 stderr = EnvUtil.verbose_warning do 1750 assert_nil(AttrTest.cattr) 1751 end 1752 assert_equal("", stderr) 1753 AttrTest.cattr = 42 1754 stderr = EnvUtil.verbose_warning do 1755 assert_equal(42, AttrTest.cattr) 1756 end 1757 assert_equal("", stderr) 1758 end 1759 1760 def test_uninitialized_attr_non_object 1761 a = Class.new(Array) do 1762 attr_accessor :iattr 1763 end.new 1764 stderr = EnvUtil.verbose_warning do 1765 assert_nil(a.iattr) 1766 end 1767 assert_equal("", stderr) 1768 a.iattr = 42 1769 stderr = EnvUtil.verbose_warning do 1770 assert_equal(42, a.iattr) 1771 end 1772 assert_equal("", stderr) 1773 end 1774 1775 def test_remove_const 1776 m = Module.new 1777 assert_raise(NameError){ m.instance_eval { remove_const(:__FOO__) } } 1778 end 1779 1780 def test_private_top_methods 1781 assert_top_method_is_private(:include) 1782 assert_top_method_is_private(:public) 1783 assert_top_method_is_private(:private) 1784 assert_top_method_is_private(:define_method) 1785 end 1786 1787 module PrivateConstantReopen 1788 PRIVATE_CONSTANT = true 1789 private_constant :PRIVATE_CONSTANT 1790 end 1791 1792 def test_private_constant_reopen 1793 assert_raise(NameError) do 1794 eval <<-EOS, TOPLEVEL_BINDING 1795 module TestModule::PrivateConstantReopen::PRIVATE_CONSTANT 1796 end 1797 EOS 1798 end 1799 assert_raise(NameError) do 1800 eval <<-EOS, TOPLEVEL_BINDING 1801 class TestModule::PrivateConstantReopen::PRIVATE_CONSTANT 1802 end 1803 EOS 1804 end 1805 end 1806 1807 def test_anonymous_module_public_class_method 1808 bug8284 = '[ruby-core:54404] [Bug #8284]' 1809 assert_raise(NoMethodError) {Object.define_method} 1810 Module.new.public_class_method(:define_method) 1811 assert_raise(NoMethodError, bug8284) {Object.define_method} 1812 end 1813 1814 def test_include_module_with_constants_invalidates_method_cache 1815 assert_in_out_err([], <<-RUBY, %w(123 456), []) 1816 A = 123 1817 1818 class Foo 1819 def self.a 1820 A 1821 end 1822 end 1823 1824 module M 1825 A = 456 1826 end 1827 1828 puts Foo.a 1829 Foo.send(:include, M) 1830 puts Foo.a 1831 RUBY 1832 end 1833 1834 private 1835 1836 def assert_top_method_is_private(method) 1837 top = eval("self", TOPLEVEL_BINDING) 1838 methods = top.singleton_class.private_instance_methods(false) 1839 assert(methods.include?(method), "#{method} should be private") 1840 1841 assert_in_out_err([], <<-INPUT, [], /private method `#{method}' called for main:Object \(NoMethodError\)/) 1842 self.#{method} 1843 INPUT 1844 end 1845end 1846