Changeset 444
- Timestamp:
- 01/17/05 02:30:07 (3 years ago)
- Files:
-
- tags/rel_0-9-4 (copied) (copied from trunk)
- tags/rel_0-9-4/actionmailer/CHANGELOG (copied) (copied from trunk/actionmailer/CHANGELOG)
- tags/rel_0-9-4/actionmailer/Rakefile (copied) (copied from trunk/actionmailer/Rakefile)
- tags/rel_0-9-4/actionpack (copied) (copied from trunk/actionpack)
- tags/rel_0-9-4/activerecord (copied) (copied from trunk/activerecord)
- tags/rel_0-9-4/activesupport/lib/binding_of_caller.rb (copied) (copied from trunk/activesupport/lib/binding_of_caller.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/hash.rb (copied) (copied from trunk/activesupport/lib/core_ext/hash.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/hash/keys.rb (copied) (copied from trunk/activesupport/lib/core_ext/hash/keys.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/numeric.rb (copied) (copied from trunk/activesupport/lib/core_ext/numeric.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/numeric/bytes.rb (copied) (copied from trunk/activesupport/lib/core_ext/numeric/bytes.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/numeric/time.rb (copied) (copied from trunk/activesupport/lib/core_ext/numeric/time.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/string.rb (copied) (copied from trunk/activesupport/lib/core_ext/string.rb)
- tags/rel_0-9-4/activesupport/lib/core_ext/string/inflections.rb (copied) (copied from trunk/activesupport/lib/core_ext/string/inflections.rb)
- tags/rel_0-9-4/activesupport/lib/dependencies.rb (copied) (copied from trunk/activesupport/lib/dependencies.rb)
- tags/rel_0-9-4/railties/CHANGELOG (copied) (copied from trunk/railties/CHANGELOG)
- tags/rel_0-9-4/railties/environments/development.rb (copied) (copied from trunk/railties/environments/development.rb)
- tags/rel_0-9-4/railties/environments/production.rb (copied) (copied from trunk/railties/environments/production.rb)
- tags/rel_0-9-4/railties/environments/test.rb (copied) (copied from trunk/railties/environments/test.rb)
- tags/rel_0-9-4/railties/lib/binding_of_caller.rb (copied) (copied from trunk/railties/lib/binding_of_caller.rb) (1 diff)
- tags/rel_0-9-4/railties/Rakefile (copied) (copied from trunk/railties/Rakefile)
- trunk/railties/lib/binding_of_caller.rb (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
tags/rel_0-9-4/railties/lib/binding_of_caller.rb
r441 r444 2 2 require 'simplecc' 3 3 rescue LoadError 4 def Continuation.create(*args, &block) #:nodoc: 5 cc = nil; result = callcc {|c| cc = c; block.call(cc) if block and args.empty?} 6 result ||= args 7 return *[cc, *result] 4 class Continuation #:nodoc: 5 def create(*args, &block) 6 cc = nil; result = callcc {|c| cc = c; block.call(cc) if block and args.empty?} 7 result ||= args 8 return *[cc, *result] 9 end 8 10 end 9 11 end 10 12 11 # This method returns the binding of the method that called your 12 # method. It will raise an Exception when you're not inside a method. 13 # 14 # It's used like this: 15 # def inc_counter(amount = 1) 16 # Binding.of_caller do |binding| 17 # # Create a lambda that will increase the variable 'counter' 18 # # in the caller of this method when called. 19 # inc = eval("lambda { |arg| counter += arg }", binding) 20 # # We can refer to amount from inside this block safely. 21 # inc.call(amount) 22 # end 23 # # No other statements can go here. Put them inside the block. 24 # end 25 # counter = 0 26 # 2.times { inc_counter } 27 # counter # => 2 28 # 29 # Binding.of_caller must be the last statement in the method. 30 # This means that you will have to put everything you want to 31 # do after the call to Binding.of_caller into the block of it. 32 # This should be no problem however, because Ruby has closures. 33 # If you don't do this an Exception will be raised. Because of 34 # the way that Binding.of_caller is implemented it has to be 35 # done this way. 36 def Binding.of_caller(&block) #:nodoc: 37 old_critical = Thread.critical 38 Thread.critical = true 39 count = 0 40 cc, result, error, extra_data = Continuation.create(nil, nil) 41 error.call if error 13 class Binding #:nodoc: 14 # This method returns the binding of the method that called your 15 # method. It will raise an Exception when you're not inside a method. 16 # 17 # It's used like this: 18 # def inc_counter(amount = 1) 19 # Binding.of_caller do |binding| 20 # # Create a lambda that will increase the variable 'counter' 21 # # in the caller of this method when called. 22 # inc = eval("lambda { |arg| counter += arg }", binding) 23 # # We can refer to amount from inside this block safely. 24 # inc.call(amount) 25 # end 26 # # No other statements can go here. Put them inside the block. 27 # end 28 # counter = 0 29 # 2.times { inc_counter } 30 # counter # => 2 31 # 32 # Binding.of_caller must be the last statement in the method. 33 # This means that you will have to put everything you want to 34 # do after the call to Binding.of_caller into the block of it. 35 # This should be no problem however, because Ruby has closures. 36 # If you don't do this an Exception will be raised. Because of 37 # the way that Binding.of_caller is implemented it has to be 38 # done this way. 39 def of_caller(&block) 40 old_critical = Thread.critical 41 Thread.critical = true 42 count = 0 43 cc, result, error, extra_data = Continuation.create(nil, nil) 44 error.call if error 42 45 43 tracer = lambda do |*args| 44 type, context, extra_data = args[0], args[4], args 45 if type == "return" 46 count += 1 47 # First this method and then calling one will return -- 48 # the trace event of the second event gets the context 49 # of the method which called the method that called this 50 # method. 51 if count == 2 52 # It would be nice if we could restore the trace_func 53 # that was set before we swapped in our own one, but 54 # this is impossible without overloading set_trace_func 55 # in current Ruby. 46 tracer = lambda do |*args| 47 type, context, extra_data = args[0], args[4], args 48 if type == "return" 49 count += 1 50 # First this method and then calling one will return -- 51 # the trace event of the second event gets the context 52 # of the method which called the method that called this 53 # method. 54 if count == 2 55 # It would be nice if we could restore the trace_func 56 # that was set before we swapped in our own one, but 57 # this is impossible without overloading set_trace_func 58 # in current Ruby. 59 set_trace_func(nil) 60 cc.call(eval("binding", context), nil, extra_data) 61 end 62 elsif type == "line" then 63 nil 64 elsif type == "c-return" and extra_data[3] == :set_trace_func then 65 nil 66 else 56 67 set_trace_func(nil) 57 cc.call(eval("binding", context), nil, extra_data) 68 error_msg = "Binding.of_caller used in non-method context or " + 69 "trailing statements of method using it aren't in the block." 70 cc.call(nil, lambda { raise(ArgumentError, error_msg) }, nil) 58 71 end 59 elsif type == "line" then 60 nil 61 elsif type == "c-return" and extra_data[3] == :set_trace_func then 62 nil 72 end 73 74 unless result 75 set_trace_func(tracer) 76 return nil 63 77 else 64 set_trace_func(nil) 65 error_msg = "Binding.of_caller used in non-method context or " + 66 "trailing statements of method using it aren't in the block." 67 cc.call(nil, lambda { raise(ArgumentError, error_msg) }, nil) 68 end 69 end 70 71 unless result 72 set_trace_func(tracer) 73 return nil 74 else 75 Thread.critical = old_critical 76 case block.arity 77 when 1 then yield(result) 78 else yield(result, extra_data) 78 Thread.critical = old_critical 79 case block.arity 80 when 1 then yield(result) 81 else yield(result, extra_data) 82 end 79 83 end 80 84 end trunk/railties/lib/binding_of_caller.rb
r441 r444 2 2 require 'simplecc' 3 3 rescue LoadError 4 def Continuation.create(*args, &block) #:nodoc: 5 cc = nil; result = callcc {|c| cc = c; block.call(cc) if block and args.empty?} 6 result ||= args 7 return *[cc, *result] 4 class Continuation #:nodoc: 5 def create(*args, &block) 6 cc = nil; result = callcc {|c| cc = c; block.call(cc) if block and args.empty?} 7 result ||= args 8 return *[cc, *result] 9 end 8 10 end 9 11 end 10 12 11 # This method returns the binding of the method that called your 12 # method. It will raise an Exception when you're not inside a method. 13 # 14 # It's used like this: 15 # def inc_counter(amount = 1) 16 # Binding.of_caller do |binding| 17 # # Create a lambda that will increase the variable 'counter' 18 # # in the caller of this method when called. 19 # inc = eval("lambda { |arg| counter += arg }", binding) 20 # # We can refer to amount from inside this block safely. 21 # inc.call(amount) 22 # end 23 # # No other statements can go here. Put them inside the block. 24 # end 25 # counter = 0 26 # 2.times { inc_counter } 27 # counter # => 2 28 # 29 # Binding.of_caller must be the last statement in the method. 30 # This means that you will have to put everything you want to 31 # do after the call to Binding.of_caller into the block of it. 32 # This should be no problem however, because Ruby has closures. 33 # If you don't do this an Exception will be raised. Because of 34 # the way that Binding.of_caller is implemented it has to be 35 # done this way. 36 def Binding.of_caller(&block) #:nodoc: 37 old_critical = Thread.critical 38 Thread.critical = true 39 count = 0 40 cc, result, error, extra_data = Continuation.create(nil, nil) 41 error.call if error 13 class Binding #:nodoc: 14 # This method returns the binding of the method that called your 15 # method. It will raise an Exception when you're not inside a method. 16 # 17 # It's used like this: 18 # def inc_counter(amount = 1) 19 # Binding.of_caller do |binding| 20 # # Create a lambda that will increase the variable 'counter' 21 # # in the caller of this method when called. 22 # inc = eval("lambda { |arg| counter += arg }", binding) 23 # # We can refer to amount from inside this block safely. 24 # inc.call(amount) 25 # end 26 # # No other statements can go here. Put them inside the block. 27 # end 28 # counter = 0 29 # 2.times { inc_counter } 30 # counter # => 2 31 # 32 # Binding.of_caller must be the last statement in the method. 33 # This means that you will have to put everything you want to 34 # do after the call to Binding.of_caller into the block of it. 35 # This should be no problem however, because Ruby has closures. 36 # If you don't do this an Exception will be raised. Because of 37 # the way that Binding.of_caller is implemented it has to be 38 # done this way. 39 def of_caller(&block) 40 old_critical = Thread.critical 41 Thread.critical = true 42 count = 0 43 cc, result, error, extra_data = Continuation.create(nil, nil) 44 error.call if error 42 45 43 tracer = lambda do |*args| 44 type, context, extra_data = args[0], args[4], args 45 if type == "return" 46 count += 1 47 # First this method and then calling one will return -- 48 # the trace event of the second event gets the context 49 # of the method which called the method that called this 50 # method. 51 if count == 2 52 # It would be nice if we could restore the trace_func 53 # that was set before we swapped in our own one, but 54 # this is impossible without overloading set_trace_func 55 # in current Ruby. 46 tracer = lambda do |*args| 47 type, context, extra_data = args[0], args[4], args 48 if type == "return" 49 count += 1 50 # First this method and then calling one will return -- 51 # the trace event of the second event gets the context 52 # of the method which called the method that called this 53 # method. 54 if count == 2 55 # It would be nice if we could restore the trace_func 56 # that was set before we swapped in our own one, but 57 # this is impossible without overloading set_trace_func 58 # in current Ruby. 59 set_trace_func(nil) 60 cc.call(eval("binding", context), nil, extra_data) 61 end 62 elsif type == "line" then 63 nil 64 elsif type == "c-return" and extra_data[3] == :set_trace_func then 65 nil 66 else 56 67 set_trace_func(nil) 57 cc.call(eval("binding", context), nil, extra_data) 68 error_msg = "Binding.of_caller used in non-method context or " + 69 "trailing statements of method using it aren't in the block." 70 cc.call(nil, lambda { raise(ArgumentError, error_msg) }, nil) 58 71 end 59 elsif type == "line" then 60 nil 61 elsif type == "c-return" and extra_data[3] == :set_trace_func then 62 nil 72 end 73 74 unless result 75 set_trace_func(tracer) 76 return nil 63 77 else 64 set_trace_func(nil) 65 error_msg = "Binding.of_caller used in non-method context or " + 66 "trailing statements of method using it aren't in the block." 67 cc.call(nil, lambda { raise(ArgumentError, error_msg) }, nil) 68 end 69 end 70 71 unless result 72 set_trace_func(tracer) 73 return nil 74 else 75 Thread.critical = old_critical 76 case block.arity 77 when 1 then yield(result) 78 else yield(result, extra_data) 78 Thread.critical = old_critical 79 case block.arity 80 when 1 then yield(result) 81 else yield(result, extra_data) 82 end 79 83 end 80 84 end