activesupport 4.0.13 → 4.1.0.beta1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of activesupport might be problematic. Click here for more details.

Files changed (124) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +283 -508
  3. data/README.rdoc +1 -1
  4. data/lib/active_support.rb +7 -1
  5. data/lib/active_support/backtrace_cleaner.rb +5 -5
  6. data/lib/active_support/benchmarkable.rb +0 -10
  7. data/lib/active_support/cache.rb +62 -26
  8. data/lib/active_support/cache/file_store.rb +27 -22
  9. data/lib/active_support/cache/mem_cache_store.rb +2 -2
  10. data/lib/active_support/cache/memory_store.rb +1 -0
  11. data/lib/active_support/cache/strategy/local_cache.rb +3 -0
  12. data/lib/active_support/callbacks.rb +416 -245
  13. data/lib/active_support/concern.rb +13 -5
  14. data/lib/active_support/core_ext.rb +0 -1
  15. data/lib/active_support/core_ext/array.rb +0 -1
  16. data/lib/active_support/core_ext/array/access.rb +2 -0
  17. data/lib/active_support/core_ext/array/conversions.rb +2 -17
  18. data/lib/active_support/core_ext/array/grouping.rb +24 -12
  19. data/lib/active_support/core_ext/array/prepend_and_append.rb +2 -2
  20. data/lib/active_support/core_ext/class.rb +0 -1
  21. data/lib/active_support/core_ext/class/attribute.rb +1 -2
  22. data/lib/active_support/core_ext/class/attribute_accessors.rb +5 -169
  23. data/lib/active_support/core_ext/date/calculations.rb +10 -0
  24. data/lib/active_support/core_ext/date/conversions.rb +5 -6
  25. data/lib/active_support/core_ext/date/zones.rb +2 -33
  26. data/lib/active_support/core_ext/date_and_time/calculations.rb +30 -11
  27. data/lib/active_support/core_ext/date_and_time/zones.rb +41 -0
  28. data/lib/active_support/core_ext/date_time/calculations.rb +12 -25
  29. data/lib/active_support/core_ext/date_time/conversions.rb +2 -0
  30. data/lib/active_support/core_ext/date_time/zones.rb +3 -21
  31. data/lib/active_support/core_ext/hash.rb +0 -1
  32. data/lib/active_support/core_ext/hash/conversions.rb +6 -3
  33. data/lib/active_support/core_ext/hash/deep_merge.rb +11 -22
  34. data/lib/active_support/core_ext/hash/indifferent_access.rb +1 -0
  35. data/lib/active_support/core_ext/hash/keys.rb +27 -47
  36. data/lib/active_support/core_ext/kernel/reporting.rb +2 -6
  37. data/lib/active_support/core_ext/module.rb +1 -0
  38. data/lib/active_support/core_ext/module/attribute_accessors.rb +160 -14
  39. data/lib/active_support/core_ext/module/concerning.rb +135 -0
  40. data/lib/active_support/core_ext/module/delegation.rb +14 -4
  41. data/lib/active_support/core_ext/module/deprecation.rb +0 -2
  42. data/lib/active_support/core_ext/module/introspection.rb +0 -16
  43. data/lib/active_support/core_ext/module/method_transplanting.rb +11 -0
  44. data/lib/active_support/core_ext/numeric/time.rb +8 -0
  45. data/lib/active_support/core_ext/object.rb +1 -1
  46. data/lib/active_support/core_ext/object/blank.rb +1 -1
  47. data/lib/active_support/core_ext/object/deep_dup.rb +6 -6
  48. data/lib/active_support/core_ext/object/inclusion.rb +4 -15
  49. data/lib/active_support/core_ext/object/json.rb +197 -0
  50. data/lib/active_support/core_ext/object/to_json.rb +4 -26
  51. data/lib/active_support/core_ext/object/to_param.rb +58 -1
  52. data/lib/active_support/core_ext/object/to_query.rb +7 -56
  53. data/lib/active_support/core_ext/object/try.rb +1 -1
  54. data/lib/active_support/core_ext/range/each.rb +2 -1
  55. data/lib/active_support/core_ext/string/access.rb +31 -31
  56. data/lib/active_support/core_ext/string/conversions.rb +9 -8
  57. data/lib/active_support/core_ext/string/exclude.rb +3 -3
  58. data/lib/active_support/core_ext/string/filters.rb +14 -4
  59. data/lib/active_support/core_ext/string/inflections.rb +11 -9
  60. data/lib/active_support/core_ext/string/output_safety.rb +65 -24
  61. data/lib/active_support/core_ext/string/zones.rb +1 -0
  62. data/lib/active_support/core_ext/thread.rb +4 -4
  63. data/lib/active_support/core_ext/time/calculations.rb +10 -57
  64. data/lib/active_support/core_ext/time/conversions.rb +3 -1
  65. data/lib/active_support/core_ext/time/zones.rb +2 -21
  66. data/lib/active_support/dependencies.rb +29 -13
  67. data/lib/active_support/deprecation.rb +4 -4
  68. data/lib/active_support/deprecation/behaviors.rb +3 -3
  69. data/lib/active_support/duration.rb +5 -7
  70. data/lib/active_support/file_update_checker.rb +1 -1
  71. data/lib/active_support/hash_with_indifferent_access.rb +4 -9
  72. data/lib/active_support/i18n.rb +4 -4
  73. data/lib/active_support/i18n_railtie.rb +2 -6
  74. data/lib/active_support/inflections.rb +0 -1
  75. data/lib/active_support/inflector/inflections.rb +17 -17
  76. data/lib/active_support/inflector/methods.rb +34 -17
  77. data/lib/active_support/json/decoding.rb +14 -21
  78. data/lib/active_support/json/encoding.rb +113 -285
  79. data/lib/active_support/key_generator.rb +1 -1
  80. data/lib/active_support/lazy_load_hooks.rb +1 -1
  81. data/lib/active_support/log_subscriber/test_helper.rb +1 -1
  82. data/lib/active_support/logger.rb +1 -1
  83. data/lib/active_support/message_encryptor.rb +3 -3
  84. data/lib/active_support/message_verifier.rb +6 -1
  85. data/lib/active_support/multibyte/chars.rb +1 -2
  86. data/lib/active_support/multibyte/unicode.rb +27 -39
  87. data/lib/active_support/notifications.rb +3 -3
  88. data/lib/active_support/notifications/instrumenter.rb +2 -1
  89. data/lib/active_support/number_helper.rb +20 -311
  90. data/lib/active_support/number_helper/number_converter.rb +182 -0
  91. data/lib/active_support/number_helper/number_to_currency_converter.rb +46 -0
  92. data/lib/active_support/number_helper/number_to_delimited_converter.rb +21 -0
  93. data/lib/active_support/number_helper/number_to_human_converter.rb +66 -0
  94. data/lib/active_support/number_helper/number_to_human_size_converter.rb +58 -0
  95. data/lib/active_support/number_helper/number_to_percentage_converter.rb +12 -0
  96. data/lib/active_support/number_helper/number_to_phone_converter.rb +49 -0
  97. data/lib/active_support/number_helper/number_to_rounded_converter.rb +62 -0
  98. data/lib/active_support/option_merger.rb +1 -1
  99. data/lib/active_support/ordered_hash.rb +0 -8
  100. data/lib/active_support/ordered_options.rb +8 -0
  101. data/lib/active_support/per_thread_registry.rb +9 -8
  102. data/lib/active_support/subscriber.rb +26 -3
  103. data/lib/active_support/test_case.rb +9 -10
  104. data/lib/active_support/testing/assertions.rb +0 -30
  105. data/lib/active_support/testing/autorun.rb +2 -2
  106. data/lib/active_support/testing/declarative.rb +18 -8
  107. data/lib/active_support/testing/isolation.rb +13 -65
  108. data/lib/active_support/testing/setup_and_teardown.rb +17 -2
  109. data/lib/active_support/testing/tagged_logging.rb +1 -1
  110. data/lib/active_support/testing/time_helpers.rb +55 -0
  111. data/lib/active_support/time_with_zone.rb +4 -4
  112. data/lib/active_support/values/time_zone.rb +18 -15
  113. data/lib/active_support/version.rb +1 -1
  114. data/lib/active_support/xml_mini.rb +2 -4
  115. metadata +71 -61
  116. data/lib/active_support/basic_object.rb +0 -11
  117. data/lib/active_support/buffered_logger.rb +0 -21
  118. data/lib/active_support/core_ext/array/uniq_by.rb +0 -19
  119. data/lib/active_support/core_ext/hash/diff.rb +0 -14
  120. data/lib/active_support/core_ext/logger.rb +0 -67
  121. data/lib/active_support/core_ext/proc.rb +0 -17
  122. data/lib/active_support/core_ext/string/encoding.rb +0 -8
  123. data/lib/active_support/json/variable.rb +0 -18
  124. data/lib/active_support/testing/pending.rb +0 -14
@@ -41,8 +41,6 @@ module Kernel
41
41
  # end
42
42
  #
43
43
  # puts 'But this will'
44
- #
45
- # This method is not thread-safe.
46
44
  def silence_stream(stream)
47
45
  old_stream = stream.dup
48
46
  stream.reopen(RbConfig::CONFIG['host_os'] =~ /mswin|mingw/ ? 'NUL:' : '/dev/null')
@@ -63,8 +61,7 @@ module Kernel
63
61
  # puts 'This code gets executed and nothing related to ZeroDivisionError was seen'
64
62
  def suppress(*exception_classes)
65
63
  yield
66
- rescue Exception => e
67
- raise unless exception_classes.any? { |cls| e.kind_of?(cls) }
64
+ rescue *exception_classes
68
65
  end
69
66
 
70
67
  # Captures the given stream and returns it:
@@ -94,6 +91,7 @@ module Kernel
94
91
  stream_io.rewind
95
92
  return captured_stream.read
96
93
  ensure
94
+ captured_stream.close
97
95
  captured_stream.unlink
98
96
  stream_io.reopen(origin_stream)
99
97
  end
@@ -102,8 +100,6 @@ module Kernel
102
100
  # Silences both STDOUT and STDERR, even for subprocesses.
103
101
  #
104
102
  # quietly { system 'bundle install' }
105
- #
106
- # This method is not thread-safe.
107
103
  def quietly
108
104
  silence_stream(STDOUT) do
109
105
  silence_stream(STDERR) do
@@ -4,6 +4,7 @@ require 'active_support/core_ext/module/anonymous'
4
4
  require 'active_support/core_ext/module/reachable'
5
5
  require 'active_support/core_ext/module/attribute_accessors'
6
6
  require 'active_support/core_ext/module/attr_internal'
7
+ require 'active_support/core_ext/module/concerning'
7
8
  require 'active_support/core_ext/module/delegation'
8
9
  require 'active_support/core_ext/module/deprecation'
9
10
  require 'active_support/core_ext/module/remove_method'
@@ -1,10 +1,59 @@
1
1
  require 'active_support/core_ext/array/extract_options'
2
2
 
3
+ # Extends the module object with class/module and instance accessors for
4
+ # class/module attributes, just like the native attr* accessors for instance
5
+ # attributes.
3
6
  class Module
7
+ # Defines a class attribute and creates a class and instance reader methods.
8
+ # The underlying the class variable is set to +nil+, if it is not previously
9
+ # defined.
10
+ #
11
+ # module HairColors
12
+ # mattr_reader :hair_colors
13
+ # end
14
+ #
15
+ # HairColors.hair_colors # => nil
16
+ # HairColors.class_variable_set("@@hair_colors", [:brown, :black])
17
+ # HairColors.hair_colors # => [:brown, :black]
18
+ #
19
+ # The attribute name must be a valid method name in Ruby.
20
+ #
21
+ # module Foo
22
+ # mattr_reader :"1_Badname "
23
+ # end
24
+ # # => NameError: invalid attribute name
25
+ #
26
+ # If you want to opt out the creation on the instance reader method, pass
27
+ # <tt>instance_reader: false</tt> or <tt>instance_accessor: false</tt>.
28
+ #
29
+ # module HairColors
30
+ # mattr_writer :hair_colors, instance_reader: false
31
+ # end
32
+ #
33
+ # class Person
34
+ # include HairColors
35
+ # end
36
+ #
37
+ # Person.new.hair_colors # => NoMethodError
38
+ #
39
+ #
40
+ # Also, you can pass a block to set up the attribute with a default value.
41
+ #
42
+ # module HairColors
43
+ # cattr_reader :hair_colors do
44
+ # [:brown, :black, :blonde, :red]
45
+ # end
46
+ # end
47
+ #
48
+ # class Person
49
+ # include HairColors
50
+ # end
51
+ #
52
+ # Person.hair_colors # => [:brown, :black, :blonde, :red]
4
53
  def mattr_reader(*syms)
5
54
  options = syms.extract_options!
6
55
  syms.each do |sym|
7
- raise NameError.new('invalid attribute name') unless sym =~ /^[_A-Za-z]\w*$/
56
+ raise NameError.new("invalid attribute name: #{sym}") unless sym =~ /^[_A-Za-z]\w*$/
8
57
  class_eval(<<-EOS, __FILE__, __LINE__ + 1)
9
58
  @@#{sym} = nil unless defined? @@#{sym}
10
59
 
@@ -20,14 +69,60 @@ class Module
20
69
  end
21
70
  EOS
22
71
  end
72
+ class_variable_set("@@#{sym}", yield) if block_given?
23
73
  end
24
74
  end
75
+ alias :cattr_reader :mattr_reader
25
76
 
77
+ # Defines a class attribute and creates a class and instance writer methods to
78
+ # allow assignment to the attribute.
79
+ #
80
+ # module HairColors
81
+ # mattr_writer :hair_colors
82
+ # end
83
+ #
84
+ # class Person
85
+ # include HairColors
86
+ # end
87
+ #
88
+ # HairColors.hair_colors = [:brown, :black]
89
+ # Person.class_variable_get("@@hair_colors") # => [:brown, :black]
90
+ # Person.new.hair_colors = [:blonde, :red]
91
+ # HairColors.class_variable_get("@@hair_colors") # => [:blonde, :red]
92
+ #
93
+ # If you want to opt out the instance writer method, pass
94
+ # <tt>instance_writer: false</tt> or <tt>instance_accessor: false</tt>.
95
+ #
96
+ # module HairColors
97
+ # mattr_writer :hair_colors, instance_writer: false
98
+ # end
99
+ #
100
+ # class Person
101
+ # include HairColors
102
+ # end
103
+ #
104
+ # Person.new.hair_colors = [:blonde, :red] # => NoMethodError
105
+ #
106
+ # Also, you can pass a block to set up the attribute with a default value.
107
+ #
108
+ # class HairColors
109
+ # mattr_writer :hair_colors do
110
+ # [:brown, :black, :blonde, :red]
111
+ # end
112
+ # end
113
+ #
114
+ # class Person
115
+ # include HairColors
116
+ # end
117
+ #
118
+ # Person.class_variable_get("@@hair_colors") # => [:brown, :black, :blonde, :red]
26
119
  def mattr_writer(*syms)
27
120
  options = syms.extract_options!
28
121
  syms.each do |sym|
29
- raise NameError.new('invalid attribute name') unless sym =~ /^[_A-Za-z]\w*$/
122
+ raise NameError.new("invalid attribute name: #{sym}") unless sym =~ /^[_A-Za-z]\w*$/
30
123
  class_eval(<<-EOS, __FILE__, __LINE__ + 1)
124
+ @@#{sym} = nil unless defined? @@#{sym}
125
+
31
126
  def self.#{sym}=(obj)
32
127
  @@#{sym} = obj
33
128
  end
@@ -40,27 +135,78 @@ class Module
40
135
  end
41
136
  EOS
42
137
  end
138
+ send("#{sym}=", yield) if block_given?
43
139
  end
44
140
  end
141
+ alias :cattr_writer :mattr_writer
45
142
 
46
- # Extends the module object with module and instance accessors for class attributes,
47
- # just like the native attr* accessors for instance attributes.
143
+ # Defines both class and instance accessors for class attributes.
48
144
  #
49
- # module AppConfiguration
50
- # mattr_accessor :google_api_key
145
+ # module HairColors
146
+ # mattr_accessor :hair_colors
147
+ # end
51
148
  #
52
- # self.google_api_key = "123456789"
149
+ # class Person
150
+ # include HairColors
53
151
  # end
54
152
  #
55
- # AppConfiguration.google_api_key # => "123456789"
56
- # AppConfiguration.google_api_key = "overriding the api key!"
57
- # AppConfiguration.google_api_key # => "overriding the api key!"
153
+ # Person.hair_colors = [:brown, :black, :blonde, :red]
154
+ # Person.hair_colors # => [:brown, :black, :blonde, :red]
155
+ # Person.new.hair_colors # => [:brown, :black, :blonde, :red]
156
+ #
157
+ # If a subclass changes the value then that would also change the value for
158
+ # parent class. Similarly if parent class changes the value then that would
159
+ # change the value of subclasses too.
160
+ #
161
+ # class Male < Person
162
+ # end
163
+ #
164
+ # Male.hair_colors << :blue
165
+ # Person.hair_colors # => [:brown, :black, :blonde, :red, :blue]
58
166
  #
59
167
  # To opt out of the instance writer method, pass <tt>instance_writer: false</tt>.
60
168
  # To opt out of the instance reader method, pass <tt>instance_reader: false</tt>.
61
- # To opt out of both instance methods, pass <tt>instance_accessor: false</tt>.
62
- def mattr_accessor(*syms)
63
- mattr_reader(*syms)
64
- mattr_writer(*syms)
169
+ #
170
+ # module HairColors
171
+ # mattr_accessor :hair_colors, instance_writer: false, instance_reader: false
172
+ # end
173
+ #
174
+ # class Person
175
+ # include HairColors
176
+ # end
177
+ #
178
+ # Person.new.hair_colors = [:brown] # => NoMethodError
179
+ # Person.new.hair_colors # => NoMethodError
180
+ #
181
+ # Or pass <tt>instance_accessor: false</tt>, to opt out both instance methods.
182
+ #
183
+ # module HairColors
184
+ # mattr_accessor :hair_colors, instance_accessor: false
185
+ # end
186
+ #
187
+ # class Person
188
+ # include HairColors
189
+ # end
190
+ #
191
+ # Person.new.hair_colors = [:brown] # => NoMethodError
192
+ # Person.new.hair_colors # => NoMethodError
193
+ #
194
+ # Also you can pass a block to set up the attribute with a default value.
195
+ #
196
+ # module HairColors
197
+ # mattr_accessor :hair_colors do
198
+ # [:brown, :black, :blonde, :red]
199
+ # end
200
+ # end
201
+ #
202
+ # class Person
203
+ # include HairColors
204
+ # end
205
+ #
206
+ # Person.class_variable_get("@@hair_colors") #=> [:brown, :black, :blonde, :red]
207
+ def mattr_accessor(*syms, &blk)
208
+ mattr_reader(*syms, &blk)
209
+ mattr_writer(*syms, &blk)
65
210
  end
211
+ alias :cattr_accessor :mattr_accessor
66
212
  end
@@ -0,0 +1,135 @@
1
+ require 'active_support/concern'
2
+
3
+ class Module
4
+ # = Bite-sized separation of concerns
5
+ #
6
+ # We often find ourselves with a medium-sized chunk of behavior that we'd
7
+ # like to extract, but only mix in to a single class.
8
+ #
9
+ # Extracting a plain old Ruby object to encapsulate it and collaborate or
10
+ # delegate to the original object is often a good choice, but when there's
11
+ # no additional state to encapsulate or we're making DSL-style declarations
12
+ # about the parent class, introducing new collaborators can obfuscate rather
13
+ # than simplify.
14
+ #
15
+ # The typical route is to just dump everything in a monolithic class, perhaps
16
+ # with a comment, as a least-bad alternative. Using modules in separate files
17
+ # means tedious sifting to get a big-picture view.
18
+ #
19
+ # = Dissatisfying ways to separate small concerns
20
+ #
21
+ # == Using comments:
22
+ #
23
+ # class Todo
24
+ # # Other todo implementation
25
+ # # ...
26
+ #
27
+ # ## Event tracking
28
+ # has_many :events
29
+ #
30
+ # before_create :track_creation
31
+ # after_destroy :track_deletion
32
+ #
33
+ # private
34
+ # def track_creation
35
+ # # ...
36
+ # end
37
+ # end
38
+ #
39
+ # == With an inline module:
40
+ #
41
+ # Noisy syntax.
42
+ #
43
+ # class Todo
44
+ # # Other todo implementation
45
+ # # ...
46
+ #
47
+ # module EventTracking
48
+ # extend ActiveSupport::Concern
49
+ #
50
+ # included do
51
+ # has_many :events
52
+ # before_create :track_creation
53
+ # after_destroy :track_deletion
54
+ # end
55
+ #
56
+ # private
57
+ # def track_creation
58
+ # # ...
59
+ # end
60
+ # end
61
+ # include EventTracking
62
+ # end
63
+ #
64
+ # == Mix-in noise exiled to its own file:
65
+ #
66
+ # Once our chunk of behavior starts pushing the scroll-to-understand it
67
+ # boundary, we give in and move it to a separate file. At this size, the
68
+ # overhead feels in good proportion to the size of our extraction, despite
69
+ # diluting our at-a-glance sense of how things really work.
70
+ #
71
+ # class Todo
72
+ # # Other todo implementation
73
+ # # ...
74
+ #
75
+ # include TodoEventTracking
76
+ # end
77
+ #
78
+ # = Introducing Module#concerning
79
+ #
80
+ # By quieting the mix-in noise, we arrive at a natural, low-ceremony way to
81
+ # separate bite-sized concerns.
82
+ #
83
+ # class Todo
84
+ # # Other todo implementation
85
+ # # ...
86
+ #
87
+ # concerning :EventTracking do
88
+ # included do
89
+ # has_many :events
90
+ # before_create :track_creation
91
+ # after_destroy :track_deletion
92
+ # end
93
+ #
94
+ # private
95
+ # def track_creation
96
+ # # ...
97
+ # end
98
+ # end
99
+ # end
100
+ #
101
+ # Todo.ancestors
102
+ # # => Todo, Todo::EventTracking, Object
103
+ #
104
+ # This small step has some wonderful ripple effects. We can
105
+ # * grok the behavior of our class in one glance,
106
+ # * clean up monolithic junk-drawer classes by separating their concerns, and
107
+ # * stop leaning on protected/private for crude "this is internal stuff" modularity.
108
+ module Concerning
109
+ # Define a new concern and mix it in.
110
+ def concerning(topic, &block)
111
+ include concern(topic, &block)
112
+ end
113
+
114
+ # A low-cruft shortcut to define a concern.
115
+ #
116
+ # concern :EventTracking do
117
+ # ...
118
+ # end
119
+ #
120
+ # is equivalent to
121
+ #
122
+ # module EventTracking
123
+ # extend ActiveSupport::Concern
124
+ #
125
+ # ...
126
+ # end
127
+ def concern(topic, &module_definition)
128
+ const_set topic, Module.new {
129
+ extend ::ActiveSupport::Concern
130
+ module_eval(&module_definition)
131
+ }
132
+ end
133
+ end
134
+ include Concerning
135
+ end
@@ -1,7 +1,16 @@
1
1
  class Module
2
+ # Error generated by +delegate+ when a method is called on +nil+ and +allow_nil+
3
+ # option is not used.
4
+ class DelegationError < NoMethodError; end
5
+
2
6
  # Provides a +delegate+ class method to easily expose contained objects'
3
7
  # public methods as your own.
4
8
  #
9
+ # ==== Options
10
+ # * <tt>:to</tt> - Specifies the target object
11
+ # * <tt>:prefix</tt> - Prefixes the new method with the target name or a custom prefix
12
+ # * <tt>:allow_nil</tt> - if set to true, prevents a +NoMethodError+ to be raised
13
+ #
5
14
  # The macro receives one or more method names (specified as symbols or
6
15
  # strings) and the name of the target object via the <tt>:to</tt> option
7
16
  # (also a symbol or string).
@@ -129,6 +138,8 @@ class Module
129
138
  #
130
139
  # Foo.new("Bar").name # raises NoMethodError: undefined method `name'
131
140
  #
141
+ # The target method must be public, otherwise it will raise +NoMethodError+.
142
+ #
132
143
  def delegate(*methods)
133
144
  options = methods.pop
134
145
  unless options.is_a?(Hash) && to = options[:to]
@@ -164,7 +175,7 @@ class Module
164
175
  #
165
176
  # Reason is twofold: On one hand doing less calls is in general better.
166
177
  # On the other hand it could be that the target has side-effects,
167
- # whereas conceptualy, from the user point of view, the delegator should
178
+ # whereas conceptually, from the user point of view, the delegator should
168
179
  # be doing one call.
169
180
  if allow_nil
170
181
  module_eval(<<-EOS, file, line - 3)
@@ -176,15 +187,14 @@ class Module
176
187
  end # end
177
188
  EOS
178
189
  else
179
- exception = %(raise "#{self}##{method_prefix}#{method} delegated to #{to}.#{method}, but #{to} is nil: \#{self.inspect}")
190
+ exception = %(raise DelegationError, "#{self}##{method_prefix}#{method} delegated to #{to}.#{method}, but #{to} is nil: \#{self.inspect}")
180
191
 
181
192
  module_eval(<<-EOS, file, line - 2)
182
193
  def #{method_prefix}#{method}(#{definition}) # def customer_name(*args, &block)
183
194
  _ = #{to} # _ = client
184
195
  _.#{method}(#{definition}) # _.name(*args, &block)
185
196
  rescue NoMethodError => e # rescue NoMethodError => e
186
- location = "%s:%d:in `%s'" % [__FILE__, __LINE__ - 2, '#{method_prefix}#{method}'] # location = "%s:%d:in `%s'" % [__FILE__, __LINE__ - 2, 'customer_name']
187
- if _.nil? && e.backtrace.first == location # if _.nil? && e.backtrace.first == location
197
+ if _.nil? && e.name == :#{method} # if _.nil? && e.name == :name
188
198
  #{exception} # # add helpful message to the exception
189
199
  else # else
190
200
  raise # raise
@@ -1,5 +1,3 @@
1
- require 'active_support/deprecation/method_wrappers'
2
-
3
1
  class Module
4
2
  # deprecate :foo
5
3
  # deprecate bar: 'message'